Merge remote-tracking branch 'origin/4.12'

Change-Id: I25baa2e1dc0a06fac6e16471ca70ba2000588797
This commit is contained in:
Eike Ziller
2020-02-19 07:40:32 +01:00
51 changed files with 471 additions and 371 deletions

View File

@@ -13,6 +13,8 @@ sourcedirs = . \
../../../src/libs/aggregation \ ../../../src/libs/aggregation \
../../../src/libs/extensionsystem ../../../src/libs/extensionsystem
excludedirs = ../../../src/libs/aggregation/examples
# -- Uncomment following option to generate complete documentation # -- Uncomment following option to generate complete documentation
# instead of public API documentation only. # instead of public API documentation only.
#showinternal = true #showinternal = true

View File

@@ -91,7 +91,8 @@ def copytree(src, dst, symlinks=False, ignore=None):
def get_qt_install_info(qmake_bin): def get_qt_install_info(qmake_bin):
output = subprocess.check_output([qmake_bin, '-query']) output = subprocess.check_output([qmake_bin, '-query'])
lines = output.decode(encoding).strip().split('\n') decoded_output = output.decode(encoding) if encoding else output
lines = decoded_output.strip().split('\n')
info = {} info = {}
for line in lines: for line in lines:
(var, sep, value) = line.partition(':') (var, sep, value) = line.partition(':')
@@ -178,28 +179,37 @@ def is_not_debug(path, filenames):
files = [fn for fn in filenames if os.path.isfile(os.path.join(path, fn))] files = [fn for fn in filenames if os.path.isfile(os.path.join(path, fn))]
return [fn for fn in files if not is_debug_file(os.path.join(path, fn))] return [fn for fn in files if not is_debug_file(os.path.join(path, fn))]
def codesign(app_path): def codesign_call():
signing_identity = os.environ.get('SIGNING_IDENTITY') signing_identity = os.environ.get('SIGNING_IDENTITY')
if is_mac_platform() and signing_identity: if not signing_identity:
return None
codesign_call = ['codesign', '-o', 'runtime', '--force', '-s', signing_identity, codesign_call = ['codesign', '-o', 'runtime', '--force', '-s', signing_identity,
'-v'] '-v']
signing_flags = os.environ.get('SIGNING_FLAGS') signing_flags = os.environ.get('SIGNING_FLAGS')
if signing_flags: if signing_flags:
codesign_call.extend(signing_flags.split()) codesign_call.extend(signing_flags.split())
return codesign_call
def conditional_sign_recursive(path, filter): def os_walk(path, filter, function):
for r, _, fs in os.walk(path): for r, _, fs in os.walk(path):
for f in fs: for f in fs:
ff = os.path.join(r, f) ff = os.path.join(r, f)
if filter(ff): if filter(ff):
print('codesign "' + ff + '"') function(ff)
subprocess.check_call(codesign_call + [ff])
def conditional_sign_recursive(path, filter):
codesign = codesign_call()
if is_mac_platform() and codesign:
os_walk(path, filter, lambda fp: subprocess.check_call(codesign + [fp]))
def codesign(app_path):
# sign all executables in Resources # sign all executables in Resources
conditional_sign_recursive(os.path.join(app_path, 'Contents', 'Resources'), conditional_sign_recursive(os.path.join(app_path, 'Contents', 'Resources'),
lambda ff: os.access(ff, os.X_OK)) lambda ff: os.access(ff, os.X_OK))
# sign all libraries in Imports # sign all libraries in Imports
conditional_sign_recursive(os.path.join(app_path, 'Contents', 'Imports'), conditional_sign_recursive(os.path.join(app_path, 'Contents', 'Imports'),
lambda ff: ff.endswith('.dylib')) lambda ff: ff.endswith('.dylib'))
codesign = codesign_call()
if is_mac_platform() and codesign:
# sign the whole bundle # sign the whole bundle
subprocess.check_call(codesign_call + ['--deep', app_path]) subprocess.check_call(codesign + ['--deep', app_path])

View File

@@ -33,8 +33,7 @@ import tempfile
import common import common
def parse_arguments(): def parse_arguments():
parser = argparse.ArgumentParser(description="Create Qt Creator package, filtering out debug information files.", parser = argparse.ArgumentParser(description="Create Qt Creator package, filtering out debug information files.")
epilog="To sign the contents before packaging on macOS, set the SIGNING_IDENTITY and optionally the SIGNING_FLAGS environment variables.")
parser.add_argument('--7z', help='path to 7z binary', parser.add_argument('--7z', help='path to 7z binary',
default='7z.exe' if common.is_windows_platform() else '7z', default='7z.exe' if common.is_windows_platform() else '7z',
metavar='<7z_binary>', dest='sevenzip') metavar='<7z_binary>', dest='sevenzip')
@@ -53,9 +52,6 @@ def main():
try: try:
common.copytree(arguments.source_directory, tempdir, symlinks=True, common.copytree(arguments.source_directory, tempdir, symlinks=True,
ignore=(common.is_not_debug if arguments.debug else common.is_debug)) ignore=(common.is_not_debug if arguments.debug else common.is_debug))
# on macOS we might have to codesign (again) to account for removed debug info
if not arguments.debug:
common.codesign(tempdir)
# package # package
zip_source = os.path.join(tempdir, '*') if arguments.exclude_toplevel else tempdir zip_source = os.path.join(tempdir, '*') if arguments.exclude_toplevel else tempdir
subprocess.check_call([arguments.sevenzip, 'a', '-mmt2', subprocess.check_call([arguments.sevenzip, 'a', '-mmt2',

View File

@@ -28,7 +28,6 @@
import argparse import argparse
import os import os
import subprocess import subprocess
import sys
import common import common
@@ -45,10 +44,16 @@ def parse_arguments():
if __name__ == "__main__": if __name__ == "__main__":
arguments = parse_arguments() arguments = parse_arguments()
if common.is_linux_platform():
qt_install_info = common.get_qt_install_info(arguments.qmake_binary) qt_install_info = common.get_qt_install_info(arguments.qmake_binary)
if common.is_linux_platform():
common.fix_rpaths(arguments.source_directory, common.fix_rpaths(arguments.source_directory,
os.path.join(arguments.source_directory, 'lib', 'Qt', 'lib'), os.path.join(arguments.source_directory, 'lib', 'Qt', 'lib'),
qt_install_info) qt_install_info)
if common.is_mac_platform():
# remove Qt rpath
lib_path = qt_install_info['QT_INSTALL_LIBS']
common.os_walk(arguments.source_directory,
lambda fp: fp.endswith('.dylib'),
lambda fp: subprocess.call(['install_name_tool', '-delete_rpath', lib_path, fp]))
subprocess.check_call([arguments.sevenzip, 'a', '-mx9', arguments.target_file, subprocess.check_call([arguments.sevenzip, 'a', '-mx9', arguments.target_file,
os.path.join(arguments.source_directory, '*')]) os.path.join(arguments.source_directory, '*')])

View File

@@ -104,7 +104,7 @@
*/ */
/*! /*!
\fn T *Aggregate::component() \fn template <typename T> T *Aggregation::Aggregate::component()
Template function that returns the component with the given type, if there is one. Template function that returns the component with the given type, if there is one.
If there are multiple components with that type, a random one is returned. If there are multiple components with that type, a random one is returned.
@@ -113,26 +113,16 @@
*/ */
/*! /*!
\fn QList<T *> Aggregate::components() \fn template <typename T> QList<T *> Aggregation::Aggregate::components()
Template function that returns all components with the given type, if there are any. Template function that returns all components with the given type, if there are any.
\sa Aggregate::component(), add() \sa Aggregate::component(), add()
*/ */
/*!
\fn T *Aggregation::query<T *>(Aggregate *obj)
\internal
*/
/*!
\fn QList<T *> Aggregation::query_all<T *>(Aggregate *obj)
\internal
*/
/*! /*!
\relates Aggregation::Aggregate \relates Aggregation::Aggregate
\fn T *Aggregation::query<T *>(QObject *obj) \fn template <typename T> T *Aggregation::query<T *>(QObject *obj)
Performs a dynamic cast that is aware of a possible aggregate that \a obj Performs a dynamic cast that is aware of a possible aggregate that \a obj
might belong to. If \a obj itself is of the requested type, it is simply cast might belong to. If \a obj itself is of the requested type, it is simply cast
@@ -144,7 +134,7 @@
/*! /*!
\relates Aggregation::Aggregate \relates Aggregation::Aggregate
\fn QList<T *> Aggregation::query_all<T *>(QObject *obj) \fn template <typename T> QList<T *> Aggregation::query_all<T *>(QObject *obj)
If \a obj belongs to an aggregate, all components that can be cast to the given If \a obj belongs to an aggregate, all components that can be cast to the given
type are returned. Otherwise, \a obj is returned if it is of the requested type. type are returned. Otherwise, \a obj is returned if it is of the requested type.

View File

@@ -531,10 +531,14 @@ void AndroidBuildApkStep::setBuildTargetSdk(const QString &sdk)
QVariant AndroidBuildApkStep::data(Core::Id id) const QVariant AndroidBuildApkStep::data(Core::Id id) const
{ {
if (id == Constants::AndroidNdkPlatform) QtSupport::BaseQtVersion *qtVersion = QtSupport::QtKitAspect::qtVersion(target()->kit());
return AndroidConfigurations::currentConfig().bestNdkPlatformMatch(AndroidManager::minimumSDK(target())).mid(8);
if (id == Constants::AndroidNdkPlatform) {
return AndroidConfigurations::currentConfig()
.bestNdkPlatformMatch(AndroidManager::minimumSDK(target()), qtVersion).mid(8);
}
if (id == Constants::NdkLocation) if (id == Constants::NdkLocation)
return QVariant::fromValue(AndroidConfigurations::currentConfig().ndkLocation()); return QVariant::fromValue(AndroidConfigurations::currentConfig().ndkLocation(qtVersion));
if (id == Constants::SdkLocation) if (id == Constants::SdkLocation)
return QVariant::fromValue(AndroidConfigurations::currentConfig().sdkLocation()); return QVariant::fromValue(AndroidConfigurations::currentConfig().sdkLocation());
if (id == Constants::AndroidABIs) if (id == Constants::AndroidABIs)

View File

@@ -102,7 +102,6 @@ namespace {
const QLatin1String SDKLocationKey("SDKLocation"); const QLatin1String SDKLocationKey("SDKLocation");
const QLatin1String SdkFullyConfiguredKey("AllEssentialsInstalled"); const QLatin1String SdkFullyConfiguredKey("AllEssentialsInstalled");
const QLatin1String SDKManagerToolArgsKey("SDKManagerToolArgs"); const QLatin1String SDKManagerToolArgsKey("SDKManagerToolArgs");
const QLatin1String NDKLocationKey("NDKLocation");
const QLatin1String OpenJDKLocationKey("OpenJDKLocation"); const QLatin1String OpenJDKLocationKey("OpenJDKLocation");
const QLatin1String KeystoreLocationKey("KeystoreLocation"); const QLatin1String KeystoreLocationKey("KeystoreLocation");
const QLatin1String AutomaticKitCreationKey("AutomatiKitCreation"); const QLatin1String AutomaticKitCreationKey("AutomatiKitCreation");
@@ -237,10 +236,8 @@ void AndroidConfig::load(const QSettings &settings)
m_partitionSize = settings.value(PartitionSizeKey, 1024).toInt(); m_partitionSize = settings.value(PartitionSizeKey, 1024).toInt();
m_sdkLocation = FilePath::fromString(settings.value(SDKLocationKey).toString()); m_sdkLocation = FilePath::fromString(settings.value(SDKLocationKey).toString());
m_sdkManagerToolArgs = settings.value(SDKManagerToolArgsKey).toStringList(); m_sdkManagerToolArgs = settings.value(SDKManagerToolArgsKey).toStringList();
m_ndkLocation = FilePath::fromString(settings.value(NDKLocationKey).toString());
m_openJDKLocation = FilePath::fromString(settings.value(OpenJDKLocationKey).toString()); m_openJDKLocation = FilePath::fromString(settings.value(OpenJDKLocationKey).toString());
m_keystoreLocation = FilePath::fromString(settings.value(KeystoreLocationKey).toString()); m_keystoreLocation = FilePath::fromString(settings.value(KeystoreLocationKey).toString());
m_toolchainHost = settings.value(ToolchainHostKey).toString();
m_automaticKitCreation = settings.value(AutomaticKitCreationKey, true).toBool(); m_automaticKitCreation = settings.value(AutomaticKitCreationKey, true).toBool();
m_sdkFullyConfigured = settings.value(SdkFullyConfiguredKey, false).toBool(); m_sdkFullyConfigured = settings.value(SdkFullyConfiguredKey, false).toBool();
@@ -250,16 +247,12 @@ void AndroidConfig::load(const QSettings &settings)
// persisten settings // persisten settings
m_sdkLocation = FilePath::fromString(reader.restoreValue(SDKLocationKey, m_sdkLocation.toString()).toString()); m_sdkLocation = FilePath::fromString(reader.restoreValue(SDKLocationKey, m_sdkLocation.toString()).toString());
m_sdkManagerToolArgs = reader.restoreValue(SDKManagerToolArgsKey, m_sdkManagerToolArgs).toStringList(); m_sdkManagerToolArgs = reader.restoreValue(SDKManagerToolArgsKey, m_sdkManagerToolArgs).toStringList();
m_ndkLocation = FilePath::fromString(reader.restoreValue(NDKLocationKey, m_ndkLocation.toString()).toString());
m_openJDKLocation = FilePath::fromString(reader.restoreValue(OpenJDKLocationKey, m_openJDKLocation.toString()).toString()); m_openJDKLocation = FilePath::fromString(reader.restoreValue(OpenJDKLocationKey, m_openJDKLocation.toString()).toString());
m_keystoreLocation = FilePath::fromString(reader.restoreValue(KeystoreLocationKey, m_keystoreLocation.toString()).toString());
m_toolchainHost = reader.restoreValue(ToolchainHostKey, m_toolchainHost).toString();
m_automaticKitCreation = reader.restoreValue(AutomaticKitCreationKey, m_automaticKitCreation).toBool(); m_automaticKitCreation = reader.restoreValue(AutomaticKitCreationKey, m_automaticKitCreation).toBool();
m_sdkFullyConfigured = reader.restoreValue(SdkFullyConfiguredKey, m_sdkFullyConfigured).toBool(); m_sdkFullyConfigured = reader.restoreValue(SdkFullyConfiguredKey, m_sdkFullyConfigured).toBool();
// persistent settings // persistent settings
} }
parseDependenciesJson(); parseDependenciesJson();
m_NdkInformationUpToDate = false;
} }
void AndroidConfig::save(QSettings &settings) const void AndroidConfig::save(QSettings &settings) const
@@ -271,51 +264,13 @@ void AndroidConfig::save(QSettings &settings) const
// user settings // user settings
settings.setValue(SDKLocationKey, m_sdkLocation.toString()); settings.setValue(SDKLocationKey, m_sdkLocation.toString());
settings.setValue(SDKManagerToolArgsKey, m_sdkManagerToolArgs); settings.setValue(SDKManagerToolArgsKey, m_sdkManagerToolArgs);
settings.setValue(NDKLocationKey, m_ndkLocation.toString());
settings.setValue(OpenJDKLocationKey, m_openJDKLocation.toString()); settings.setValue(OpenJDKLocationKey, m_openJDKLocation.toString());
settings.setValue(KeystoreLocationKey, m_keystoreLocation.toString()); settings.setValue(KeystoreLocationKey, m_keystoreLocation.toString());
settings.setValue(PartitionSizeKey, m_partitionSize); settings.setValue(PartitionSizeKey, m_partitionSize);
settings.setValue(AutomaticKitCreationKey, m_automaticKitCreation); settings.setValue(AutomaticKitCreationKey, m_automaticKitCreation);
settings.setValue(ToolchainHostKey, m_toolchainHost);
settings.setValue(SdkFullyConfiguredKey, m_sdkFullyConfigured); settings.setValue(SdkFullyConfiguredKey, m_sdkFullyConfigured);
} }
void AndroidConfig::updateNdkInformation() const
{
if (m_NdkInformationUpToDate)
return;
m_availableNdkPlatforms.clear();
QDirIterator it(m_ndkLocation.pathAppended("platforms").toString(), QStringList("android-*"), QDir::Dirs);
while (it.hasNext()) {
const QString &fileName = it.next();
m_availableNdkPlatforms.push_back(fileName.midRef(fileName.lastIndexOf(QLatin1Char('-')) + 1).toInt());
}
Utils::sort(m_availableNdkPlatforms, std::greater<>());
// detect toolchain host
QStringList hostPatterns;
switch (HostOsInfo::hostOs()) {
case OsTypeLinux:
hostPatterns << QLatin1String("linux*");
break;
case OsTypeWindows:
hostPatterns << QLatin1String("windows*");
break;
case OsTypeMac:
hostPatterns << QLatin1String("darwin*");
break;
default: /* unknown host */ return;
}
QDirIterator jt(m_ndkLocation.pathAppended("prebuilt").toString(), hostPatterns, QDir::Dirs);
if (jt.hasNext()) {
jt.next();
m_toolchainHost = jt.fileName();
}
m_NdkInformationUpToDate = true;
}
void AndroidConfig::parseDependenciesJson() void AndroidConfig::parseDependenciesJson()
{ {
QString sdkConfigFile(Core::ICore::resourcePath() + JsonFilePath); QString sdkConfigFile(Core::ICore::resourcePath() + JsonFilePath);
@@ -382,6 +337,22 @@ void AndroidConfig::parseDependenciesJson()
} }
} }
QVector<int> AndroidConfig::availableNdkPlatforms(const BaseQtVersion *qtVersion) const
{
QVector<int> availableNdkPlatforms;
QDirIterator it(ndkLocation(qtVersion).pathAppended("platforms").toString(),
QStringList("android-*"),
QDir::Dirs);
while (it.hasNext()) {
const QString &fileName = it.next();
availableNdkPlatforms.push_back(
fileName.midRef(fileName.lastIndexOf(QLatin1Char('-')) + 1).toInt());
}
Utils::sort(availableNdkPlatforms, std::greater<>());
return availableNdkPlatforms;
}
QStringList AndroidConfig::apiLevelNamesFor(const SdkPlatformList &platforms) QStringList AndroidConfig::apiLevelNamesFor(const SdkPlatformList &platforms)
{ {
return Utils::transform(platforms, AndroidConfig::apiLevelNameFor); return Utils::transform(platforms, AndroidConfig::apiLevelNameFor);
@@ -444,9 +415,9 @@ FilePath AndroidConfig::aaptToolPath() const
return aaptToolPath.pathAppended(toolPath); return aaptToolPath.pathAppended(toolPath);
} }
FilePath AndroidConfig::toolchainPath() const FilePath AndroidConfig::toolchainPath(const BaseQtVersion *qtVersion) const
{ {
const FilePath toolchainPath = m_ndkLocation.pathAppended("toolchains/llvm/prebuilt/"); const FilePath toolchainPath = ndkLocation(qtVersion).pathAppended("toolchains/llvm/prebuilt/");
// detect toolchain host // detect toolchain host
QStringList hostPatterns; QStringList hostPatterns;
@@ -472,29 +443,34 @@ FilePath AndroidConfig::toolchainPath() const
return {}; return {};
} }
FilePath AndroidConfig::clangPath() const FilePath AndroidConfig::clangPath(const BaseQtVersion *qtVersion) const
{ {
const FilePath path = toolchainPath(); const FilePath path = toolchainPath(qtVersion);
if (path.isEmpty()) if (path.isEmpty())
return {}; return {};
return path.pathAppended(HostOsInfo::withExecutableSuffix("bin/clang")); return path.pathAppended(HostOsInfo::withExecutableSuffix("bin/clang"));
} }
FilePath AndroidConfig::gdbPath(const ProjectExplorer::Abi &abi) const FilePath AndroidConfig::gdbPath(const ProjectExplorer::Abi &abi, const BaseQtVersion *qtVersion) const
{ {
const FilePath path = m_ndkLocation.pathAppended( const FilePath path = ndkLocation(qtVersion).pathAppended(
QString("prebuilt/%1/bin/gdb%2").arg(toolchainHost(), QTC_HOST_EXE_SUFFIX)); QString("prebuilt/%1/bin/gdb%2").arg(toolchainHost(qtVersion), QTC_HOST_EXE_SUFFIX));
if (path.exists()) if (path.exists())
return path; return path;
// fallback for old NDKs (e.g. 10e) // fallback for old NDKs (e.g. 10e)
return m_ndkLocation.pathAppended(QString("toolchains/%1-4.9/prebuilt/%2/bin/%3-gdb%4") return ndkLocation(qtVersion).pathAppended(QString("toolchains/%1-4.9/prebuilt/%2/bin/%3-gdb%4")
.arg(toolchainPrefix(abi), toolchainHost(), toolsPrefix(abi), QTC_HOST_EXE_SUFFIX)); .arg(toolchainPrefix(abi), toolchainHost(qtVersion), toolsPrefix(abi), QTC_HOST_EXE_SUFFIX));
} }
FilePath AndroidConfig::makePath() const FilePath AndroidConfig::makePath(const BaseQtVersion *qtVersion) const
{ {
return m_ndkLocation.pathAppended( return makePathFromNdk(ndkLocation(qtVersion));
QString("prebuilt/%1/bin/make%2").arg(toolchainHost(), QTC_HOST_EXE_SUFFIX)); }
FilePath AndroidConfig::makePathFromNdk(const FilePath &ndkLocation) const
{
return ndkLocation.pathAppended(
QString("prebuilt/%1/bin/make%2").arg(toolchainHostFromNdk(ndkLocation), QTC_HOST_EXE_SUFFIX));
} }
FilePath AndroidConfig::openJDKBinPath() const FilePath AndroidConfig::openJDKBinPath() const
@@ -757,11 +733,10 @@ bool AndroidConfig::useNativeUiTools() const
return !version.isNull() && version <= QVersionNumber(25, 3 ,0); return !version.isNull() && version <= QVersionNumber(25, 3 ,0);
} }
QString AndroidConfig::bestNdkPlatformMatch(int target) const QString AndroidConfig::bestNdkPlatformMatch(int target, const BaseQtVersion *qtVersion) const
{ {
target = std::max(AndroidManager::apiLevelRange().first, target); target = std::max(AndroidManager::apiLevelRange().first, target);
updateNdkInformation(); foreach (int apiLevel, availableNdkPlatforms(qtVersion)) {
foreach (int apiLevel, m_availableNdkPlatforms) {
if (apiLevel <= target) if (apiLevel <= target)
return QString::fromLatin1("android-%1").arg(apiLevel); return QString::fromLatin1("android-%1").arg(apiLevel);
} }
@@ -812,9 +787,9 @@ void AndroidConfig::setSdkManagerToolArgs(const QStringList &args)
m_sdkManagerToolArgs = args; m_sdkManagerToolArgs = args;
} }
FilePath AndroidConfig::ndkLocation() const FilePath AndroidConfig::ndkLocation(const BaseQtVersion *qtVersion) const
{ {
return m_ndkLocation; return sdkLocation().pathAppended(ndkPathFromQtVersion(*qtVersion));
} }
FilePath AndroidConfig::defaultNdkLocation() const FilePath AndroidConfig::defaultNdkLocation() const
@@ -837,9 +812,9 @@ static inline QString gdbServerArch(const QString &androidAbi)
} }
} }
FilePath AndroidConfig::gdbServer(const QString &androidAbi) const FilePath AndroidConfig::gdbServer(const QString &androidAbi, const BaseQtVersion *qtVersion) const
{ {
const FilePath path = AndroidConfigurations::currentConfig().ndkLocation() const FilePath path = AndroidConfigurations::currentConfig().ndkLocation(qtVersion)
.pathAppended(QString("prebuilt/android-%1/gdbserver/gdbserver") .pathAppended(QString("prebuilt/android-%1/gdbserver/gdbserver")
.arg(gdbServerArch(androidAbi))); .arg(gdbServerArch(androidAbi)));
if (path.exists()) if (path.exists())
@@ -847,16 +822,21 @@ FilePath AndroidConfig::gdbServer(const QString &androidAbi) const
return {}; return {};
} }
QVersionNumber AndroidConfig::ndkVersion() const QVersionNumber AndroidConfig::ndkVersion(const BaseQtVersion *qtVersion) const
{
return ndkVersion(ndkLocation(qtVersion));
}
QVersionNumber AndroidConfig::ndkVersion(const FilePath &ndkPath) const
{ {
QVersionNumber version; QVersionNumber version;
if (!m_ndkLocation.exists()) { if (!ndkPath.exists()) {
qCDebug(avdConfigLog) << "Cannot find ndk version. Check NDK path." qCDebug(avdConfigLog) << "Cannot find ndk version. Check NDK path."
<< m_ndkLocation.toString(); << ndkPath.toString();
return version; return version;
} }
const FilePath ndkPropertiesPath = m_ndkLocation.pathAppended("source.properties"); const FilePath ndkPropertiesPath = ndkPath.pathAppended("source.properties");
if (ndkPropertiesPath.exists()) { if (ndkPropertiesPath.exists()) {
// source.properties files exists in NDK version > 11 // source.properties files exists in NDK version > 11
QSettings settings(ndkPropertiesPath.toString(), QSettings::IniFormat); QSettings settings(ndkPropertiesPath.toString(), QSettings::IniFormat);
@@ -864,7 +844,7 @@ QVersionNumber AndroidConfig::ndkVersion() const
version = QVersionNumber::fromString(versionStr); version = QVersionNumber::fromString(versionStr);
} else { } else {
// No source.properties. There should be a file named RELEASE.TXT // No source.properties. There should be a file named RELEASE.TXT
const FilePath ndkReleaseTxtPath = m_ndkLocation.pathAppended("RELEASE.TXT"); const FilePath ndkReleaseTxtPath = ndkPath.pathAppended("RELEASE.TXT");
Utils::FileReader reader; Utils::FileReader reader;
QString errorString; QString errorString;
if (reader.fetch(ndkReleaseTxtPath.toString(), &errorString)) { if (reader.fetch(ndkReleaseTxtPath.toString(), &errorString)) {
@@ -892,12 +872,6 @@ QVersionNumber AndroidConfig::ndkVersion() const
return version; return version;
} }
void AndroidConfig::setNdkLocation(const FilePath &ndkLocation)
{
m_ndkLocation = ndkLocation;
m_NdkInformationUpToDate = false;
}
QStringList AndroidConfig::allEssentials() const QStringList AndroidConfig::allEssentials() const
{ {
QList<BaseQtVersion *> installedVersions = QtVersionManager::versions( QList<BaseQtVersion *> installedVersions = QtVersionManager::versions(
@@ -925,7 +899,7 @@ QStringList AndroidConfig::essentialsFromQtVersion(const BaseQtVersion &version)
QString AndroidConfig::ndkPathFromQtVersion(const BaseQtVersion &version) const QString AndroidConfig::ndkPathFromQtVersion(const BaseQtVersion &version) const
{ {
QtVersionNumber qtVersion = version.qtVersion(); QtVersionNumber qtVersion(version.qtVersionString());
for (const SdkForQtVersions &item : m_specificQtVersions) for (const SdkForQtVersions &item : m_specificQtVersions)
if (item.containsVersion(qtVersion)) if (item.containsVersion(qtVersion))
return item.ndkPath; return item.ndkPath;
@@ -969,10 +943,39 @@ void AndroidConfig::setKeystoreLocation(const FilePath &keystoreLocation)
m_keystoreLocation = keystoreLocation; m_keystoreLocation = keystoreLocation;
} }
QString AndroidConfig::toolchainHost() const QString AndroidConfig::toolchainHost(const BaseQtVersion *qtVersion) const
{ {
updateNdkInformation(); return toolchainHostFromNdk(ndkLocation(qtVersion));
return m_toolchainHost; }
QString AndroidConfig::toolchainHostFromNdk(const FilePath &ndkPath) const
{
// detect toolchain host
QString toolchainHost;
QStringList hostPatterns;
switch (HostOsInfo::hostOs()) {
case OsTypeLinux:
hostPatterns << QLatin1String("linux*");
break;
case OsTypeWindows:
hostPatterns << QLatin1String("windows*");
break;
case OsTypeMac:
hostPatterns << QLatin1String("darwin*");
break;
default: /* unknown host */
return toolchainHost;
}
QDirIterator jt(ndkPath.pathAppended("prebuilt").toString(),
hostPatterns,
QDir::Dirs);
if (jt.hasNext()) {
jt.next();
toolchainHost = jt.fileName();
}
return toolchainHost;
} }
unsigned AndroidConfig::partitionSize() const unsigned AndroidConfig::partitionSize() const
@@ -1087,9 +1090,9 @@ void AndroidConfigurations::removeOldToolChains()
} }
} }
static QVariant findOrRegisterDebugger(ToolChain *tc) static QVariant findOrRegisterDebugger(ToolChain *tc, const BaseQtVersion *qtVersion)
{ {
const FilePath command = AndroidConfigurations::currentConfig().gdbPath(tc->targetAbi()); const FilePath command = AndroidConfigurations::currentConfig().gdbPath(tc->targetAbi(), qtVersion);
// check if the debugger is already registered, but ignoring the display name // check if the debugger is already registered, but ignoring the display name
const Debugger::DebuggerItem *existing = Debugger::DebuggerItemManager::findByCommand(command); const Debugger::DebuggerItem *existing = Debugger::DebuggerItemManager::findByCommand(command);
if (existing && existing->engineType() == Debugger::GdbEngineType && existing->isAutoDetected() if (existing && existing->engineType() == Debugger::GdbEngineType && existing->isAutoDetected()
@@ -1116,7 +1119,7 @@ void AndroidConfigurations::updateAutomaticKitList()
for (auto k: androidKits) { for (auto k: androidKits) {
if (k->value(Constants::ANDROID_KIT_NDK).isNull() || k->value(Constants::ANDROID_KIT_SDK).isNull()) { if (k->value(Constants::ANDROID_KIT_NDK).isNull() || k->value(Constants::ANDROID_KIT_SDK).isNull()) {
k->setValueSilently(Constants::ANDROID_KIT_NDK, currentConfig().ndkLocation().toString()); k->setValueSilently(Constants::ANDROID_KIT_NDK, currentConfig().ndkLocation(QtSupport::QtKitAspect::qtVersion(k)).toString());
k->setValue(Constants::ANDROID_KIT_SDK, currentConfig().sdkLocation().toString()); k->setValue(Constants::ANDROID_KIT_SDK, currentConfig().sdkLocation().toString());
} }
} }
@@ -1163,16 +1166,22 @@ void AndroidConfigurations::updateAutomaticKitList()
for (ToolChain *tc : toolchains) { for (ToolChain *tc : toolchains) {
if (tc->language() != Core::Id(ProjectExplorer::Constants::CXX_LANGUAGE_ID)) if (tc->language() != Core::Id(ProjectExplorer::Constants::CXX_LANGUAGE_ID))
continue; continue;
const QList<ToolChain *> allLanguages = Utils::filtered(toolchains,
[tc](ToolChain *otherTc) { for (const QtSupport::BaseQtVersion *qt : qtVersionsForArch.value(tc->targetAbi())) {
return tc->targetAbi() == otherTc->targetAbi(); FilePath tcNdk = static_cast<const AndroidToolChain *>(tc)->ndkLocation();
if (tcNdk != currentConfig().ndkLocation(qt))
continue;
const QList<ToolChain *> allLanguages
= Utils::filtered(toolchains, [tc, tcNdk](ToolChain *otherTc) {
FilePath otherNdk = static_cast<const AndroidToolChain *>(otherTc)->ndkLocation();
return tc->targetAbi() == otherTc->targetAbi() && tcNdk == otherNdk;
}); });
QHash<Core::Id, ToolChain *> toolChainForLanguage; QHash<Core::Id, ToolChain *> toolChainForLanguage;
for (ToolChain *tc : allLanguages) for (ToolChain *tc : allLanguages)
toolChainForLanguage[tc->language()] = tc; toolChainForLanguage[tc->language()] = tc;
for (const QtSupport::BaseQtVersion *qt : qtVersionsForArch.value(tc->targetAbi())) {
Kit *existingKit = Utils::findOrDefault(existingKits, [&](const Kit *b) { Kit *existingKit = Utils::findOrDefault(existingKits, [&](const Kit *b) {
if (qt != QtSupport::QtKitAspect::qtVersion(b)) if (qt != QtSupport::QtKitAspect::qtVersion(b))
return false; return false;
@@ -1190,12 +1199,12 @@ void AndroidConfigurations::updateAutomaticKitList()
ToolChainKitAspect::setToolChain(k, tc); ToolChainKitAspect::setToolChain(k, tc);
QtSupport::QtKitAspect::setQtVersion(k, qt); QtSupport::QtKitAspect::setQtVersion(k, qt);
DeviceKitAspect::setDevice(k, device); DeviceKitAspect::setDevice(k, device);
Debugger::DebuggerKitAspect::setDebugger(k, findOrRegisterDebugger(tc)); Debugger::DebuggerKitAspect::setDebugger(k, findOrRegisterDebugger(tc, QtKitAspect::qtVersion(k)));
k->makeSticky(); k->makeSticky();
k->setUnexpandedDisplayName(tr("Android for %1 (Clang %2)") k->setUnexpandedDisplayName(tr("Android for %1 (Clang %2)")
.arg(static_cast<const AndroidQtVersion *>(qt)->androidAbis().join(",")) .arg(static_cast<const AndroidQtVersion *>(qt)->androidAbis().join(","))
.arg(qt->displayName())); .arg(qt->displayName()));
k->setValueSilently(Constants::ANDROID_KIT_NDK, currentConfig().ndkLocation().toString()); k->setValueSilently(Constants::ANDROID_KIT_NDK, currentConfig().ndkLocation(qt).toString());
k->setValueSilently(Constants::ANDROID_KIT_SDK, currentConfig().sdkLocation().toString()); k->setValueSilently(Constants::ANDROID_KIT_SDK, currentConfig().sdkLocation().toString());
}; };

View File

@@ -122,11 +122,11 @@ public:
QStringList sdkManagerToolArgs() const; QStringList sdkManagerToolArgs() const;
void setSdkManagerToolArgs(const QStringList &args); void setSdkManagerToolArgs(const QStringList &args);
Utils::FilePath ndkLocation() const; Utils::FilePath ndkLocation(const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath defaultNdkLocation() const; Utils::FilePath defaultNdkLocation() const;
Utils::FilePath gdbServer(const QString &androidAbi) const; Utils::FilePath gdbServer(const QString &androidAbi, const QtSupport::BaseQtVersion *qtVersion) const;
QVersionNumber ndkVersion() const; QVersionNumber ndkVersion(const QtSupport::BaseQtVersion *qtVersion) const;
void setNdkLocation(const Utils::FilePath &ndkLocation); QVersionNumber ndkVersion(const Utils::FilePath &ndkPath) const;
QUrl sdkToolsUrl() const { return m_sdkToolsUrl; }; QUrl sdkToolsUrl() const { return m_sdkToolsUrl; };
QByteArray getSdkToolsSha256() const { return m_sdkToolsSha256; }; QByteArray getSdkToolsSha256() const { return m_sdkToolsSha256; };
@@ -143,7 +143,8 @@ public:
Utils::FilePath keystoreLocation() const; Utils::FilePath keystoreLocation() const;
void setKeystoreLocation(const Utils::FilePath &keystoreLocation); void setKeystoreLocation(const Utils::FilePath &keystoreLocation);
QString toolchainHost() const; QString toolchainHost(const QtSupport::BaseQtVersion *qtVersion) const;
QString toolchainHostFromNdk(const Utils::FilePath &ndkPath) const;
unsigned partitionSize() const; unsigned partitionSize() const;
void setPartitionSize(unsigned partitionSize); void setPartitionSize(unsigned partitionSize);
@@ -158,18 +159,19 @@ public:
Utils::FilePath avdManagerToolPath() const; Utils::FilePath avdManagerToolPath() const;
Utils::FilePath aaptToolPath() const; Utils::FilePath aaptToolPath() const;
Utils::FilePath toolchainPath() const; Utils::FilePath toolchainPath(const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath clangPath() const; Utils::FilePath clangPath(const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath gdbPath(const ProjectExplorer::Abi &abi) const; Utils::FilePath gdbPath(const ProjectExplorer::Abi &abi, const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath makePath() const; Utils::FilePath makePath(const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath makePathFromNdk(const Utils::FilePath &ndkLocation) const;
Utils::FilePath keytoolPath() const; Utils::FilePath keytoolPath() const;
QVector<AndroidDeviceInfo> connectedDevices(QString *error = nullptr) const; QVector<AndroidDeviceInfo> connectedDevices(QString *error = nullptr) const;
static QVector<AndroidDeviceInfo> connectedDevices(const Utils::FilePath &adbToolPath, QString *error = nullptr); static QVector<AndroidDeviceInfo> connectedDevices(const Utils::FilePath &adbToolPath, QString *error = nullptr);
QString bestNdkPlatformMatch(int target) const; QString bestNdkPlatformMatch(int target, const QtSupport::BaseQtVersion *qtVersion) const;
static ProjectExplorer::Abi abiForToolChainPrefix(const QString &toolchainPrefix); static ProjectExplorer::Abi abiForToolChainPrefix(const QString &toolchainPrefix);
static QLatin1String toolchainPrefix(const ProjectExplorer::Abi &abi); static QLatin1String toolchainPrefix(const ProjectExplorer::Abi &abi);
@@ -199,12 +201,12 @@ private:
bool isBootToQt(const QString &device) const; bool isBootToQt(const QString &device) const;
static QString getAvdName(const QString &serialnumber); static QString getAvdName(const QString &serialnumber);
void updateNdkInformation() const;
void parseDependenciesJson(); void parseDependenciesJson();
QVector<int> availableNdkPlatforms(const QtSupport::BaseQtVersion *qtVersion) const;
Utils::FilePath m_sdkLocation; Utils::FilePath m_sdkLocation;
QStringList m_sdkManagerToolArgs; QStringList m_sdkManagerToolArgs;
Utils::FilePath m_ndkLocation;
Utils::FilePath m_openJDKLocation; Utils::FilePath m_openJDKLocation;
Utils::FilePath m_keystoreLocation; Utils::FilePath m_keystoreLocation;
unsigned m_partitionSize = 1024; unsigned m_partitionSize = 1024;
@@ -217,10 +219,6 @@ private:
bool m_sdkFullyConfigured = false; bool m_sdkFullyConfigured = false;
//caches //caches
mutable bool m_NdkInformationUpToDate = false;
mutable QString m_toolchainHost;
mutable QVector<int> m_availableNdkPlatforms;
mutable QHash<QString, QString> m_serialNumberToDeviceName; mutable QHash<QString, QString> m_serialNumberToDeviceName;
}; };

View File

@@ -122,14 +122,13 @@ void AndroidDebugSupport::start()
qCDebug(androidDebugSupportLog) << "Start. Package name: " << packageName qCDebug(androidDebugSupportLog) << "Start. Package name: " << packageName
<< "PID: " << m_runner->pid().pid(); << "PID: " << m_runner->pid().pid();
QtSupport::BaseQtVersion *qtVersion = QtSupport::QtKitAspect::qtVersion(kit);
if (!Utils::HostOsInfo::isWindowsHost() && if (!Utils::HostOsInfo::isWindowsHost() &&
AndroidConfigurations::currentConfig().ndkVersion() >= QVersionNumber(11, 0, 0)) { AndroidConfigurations::currentConfig().ndkVersion(qtVersion) >= QVersionNumber(11, 0, 0)) {
qCDebug(androidDebugSupportLog) << "UseTargetAsync: " << true; qCDebug(androidDebugSupportLog) << "UseTargetAsync: " << true;
setUseTargetAsync(true); setUseTargetAsync(true);
} }
QtSupport::BaseQtVersion *qtVersion = QtSupport::QtKitAspect::qtVersion(kit);
if (isCppDebugging()) { if (isCppDebugging()) {
qCDebug(androidDebugSupportLog) << "C++ debugging enabled"; qCDebug(androidDebugSupportLog) << "C++ debugging enabled";
const ProjectNode *node = target->project()->findNodeForBuildKey(runControl()->buildKey()); const ProjectNode *node = target->project()->findNodeForBuildKey(runControl()->buildKey());
@@ -160,7 +159,7 @@ void AndroidDebugSupport::start()
// TODO find a way to use the new sysroot layout // TODO find a way to use the new sysroot layout
// instead ~/android/ndk-bundle/platforms/android-29/arch-arm64 // instead ~/android/ndk-bundle/platforms/android-29/arch-arm64
// use ~/android/ndk-bundle/toolchains/llvm/prebuilt/linux-x86_64/sysroot // use ~/android/ndk-bundle/toolchains/llvm/prebuilt/linux-x86_64/sysroot
Utils::FilePath sysRoot = AndroidConfigurations::currentConfig().ndkLocation() Utils::FilePath sysRoot = AndroidConfigurations::currentConfig().ndkLocation(qtVersion)
.pathAppended("platforms") .pathAppended("platforms")
.pathAppended(QString("android-%1").arg(sdkVersion)) .pathAppended(QString("android-%1").arg(sdkVersion))
.pathAppended(devicePreferredAbi); .pathAppended(devicePreferredAbi);

View File

@@ -293,22 +293,25 @@ QJsonObject AndroidManager::deploymentSettings(const Target *target)
QJsonObject settings; QJsonObject settings;
settings["_description"] = qtcSignature; settings["_description"] = qtcSignature;
settings["qt"] = qt->prefix().toString(); settings["qt"] = qt->prefix().toString();
settings["ndk"] = AndroidConfigurations::currentConfig().ndkLocation().toString(); settings["ndk"] = AndroidConfigurations::currentConfig().ndkLocation(qt).toString();
settings["sdk"] = AndroidConfigurations::currentConfig().sdkLocation().toString(); settings["sdk"] = AndroidConfigurations::currentConfig().sdkLocation().toString();
if (qt->qtVersion() < QtSupport::QtVersionNumber(5, 14, 0)) { if (qt->qtVersion() < QtSupport::QtVersionNumber(5, 14, 0)) {
const QStringList abis = applicationAbis(target); const QStringList abis = applicationAbis(target);
QTC_ASSERT(abis.size() == 1, return {}); QTC_ASSERT(abis.size() == 1, return {});
settings["stdcpp-path"] = AndroidConfigurations::currentConfig().toolchainPath() settings["stdcpp-path"] = AndroidConfigurations::currentConfig().toolchainPath(qt)
.pathAppended("sysroot/usr/lib/") .pathAppended("sysroot/usr/lib/")
.pathAppended(archTriplet(abis.first())) .pathAppended(archTriplet(abis.first()))
.pathAppended("libc++_shared.so").toString(); .pathAppended("libc++_shared.so").toString();
} else { } else {
settings["stdcpp-path"] = AndroidConfigurations::currentConfig().toolchainPath().pathAppended("sysroot/usr/lib/").toString(); settings["stdcpp-path"] = AndroidConfigurations::currentConfig()
.toolchainPath(qt)
.pathAppended("sysroot/usr/lib/")
.toString();
} }
settings["toolchain-prefix"] = "llvm"; settings["toolchain-prefix"] = "llvm";
settings["tool-prefix"] = "llvm"; settings["tool-prefix"] = "llvm";
settings["useLLVM"] = true; settings["useLLVM"] = true;
settings["ndk-host"] = AndroidConfigurations::currentConfig().toolchainHost(); settings["ndk-host"] = AndroidConfigurations::currentConfig().toolchainHost(qt);
return settings; return settings;
} }

View File

@@ -34,6 +34,8 @@
#include <coreplugin/infobar.h> #include <coreplugin/infobar.h>
#include <coreplugin/editormanager/ieditor.h> #include <coreplugin/editormanager/ieditor.h>
#include <qtsupport/qtkitinformation.h>
#include <projectexplorer/buildconfiguration.h> #include <projectexplorer/buildconfiguration.h>
#include <projectexplorer/project.h> #include <projectexplorer/project.h>
#include <projectexplorer/projectnodes.h> #include <projectexplorer/projectnodes.h>
@@ -612,8 +614,10 @@ void AndroidManifestEditorWidget::postSave()
const Utils::FilePath docPath = m_textEditorWidget->textDocument()->filePath(); const Utils::FilePath docPath = m_textEditorWidget->textDocument()->filePath();
if (Target *target = androidTarget(docPath)) { if (Target *target = androidTarget(docPath)) {
if (BuildConfiguration *bc = target->activeBuildConfiguration()) { if (BuildConfiguration *bc = target->activeBuildConfiguration()) {
QString androidNdkPlatform = AndroidConfigurations::currentConfig() QString androidNdkPlatform = AndroidConfigurations::currentConfig().bestNdkPlatformMatch(
.bestNdkPlatformMatch(AndroidManager::minimumSDK(target)); AndroidManager::minimumSDK(target),
QtSupport::QtKitAspect::qtVersion(
androidTarget(m_textEditorWidget->textDocument()->filePath())->kit()));
if (m_androidNdkPlatform != androidNdkPlatform) { if (m_androidNdkPlatform != androidNdkPlatform) {
m_androidNdkPlatform = androidNdkPlatform; m_androidNdkPlatform = androidNdkPlatform;
bc->updateCacheAndEmitEnvironmentChanged(); bc->updateCacheAndEmitEnvironmentChanged();

View File

@@ -178,6 +178,7 @@ void AndroidPlugin::kitsRestored()
} }
AndroidConfigurations::updateAutomaticKitList(); AndroidConfigurations::updateAutomaticKitList();
AndroidConfigurations::registerNewToolChains();
connect(QtSupport::QtVersionManager::instance(), &QtSupport::QtVersionManager::qtVersionsChanged, connect(QtSupport::QtVersionManager::instance(), &QtSupport::QtVersionManager::qtVersionsChanged,
AndroidConfigurations::instance(), &AndroidConfigurations::updateAutomaticKitList); AndroidConfigurations::instance(), &AndroidConfigurations::updateAutomaticKitList);
disconnect(KitManager::instance(), &KitManager::kitsLoaded, disconnect(KitManager::instance(), &KitManager::kitsLoaded,

View File

@@ -70,7 +70,7 @@ QString AndroidQtVersion::invalidReason() const
{ {
QString tmp = BaseQtVersion::invalidReason(); QString tmp = BaseQtVersion::invalidReason();
if (tmp.isEmpty()) { if (tmp.isEmpty()) {
if (AndroidConfigurations::currentConfig().ndkLocation().isEmpty()) if (AndroidConfigurations::currentConfig().ndkLocation(this).isEmpty())
return tr("NDK is not configured in Devices > Android."); return tr("NDK is not configured in Devices > Android.");
if (AndroidConfigurations::currentConfig().sdkLocation().isEmpty()) if (AndroidConfigurations::currentConfig().sdkLocation().isEmpty())
return tr("SDK is not configured in Devices > Android."); return tr("SDK is not configured in Devices > Android.");
@@ -126,16 +126,17 @@ void AndroidQtVersion::addToEnvironment(const Kit *k, Utils::Environment &env) c
{ {
const AndroidConfig &config =AndroidConfigurations::currentConfig(); const AndroidConfig &config =AndroidConfigurations::currentConfig();
// this env vars are used by qmake mkspecs to generate makefiles (check QTDIR/mkspecs/android-g++/qmake.conf for more info) // this env vars are used by qmake mkspecs to generate makefiles (check QTDIR/mkspecs/android-g++/qmake.conf for more info)
env.set(QLatin1String("ANDROID_NDK_HOST"), config.toolchainHost()); env.set(QLatin1String("ANDROID_NDK_HOST"), config.toolchainHost(this));
env.set(QLatin1String("ANDROID_NDK_ROOT"), config.ndkLocation().toUserOutput()); env.set(QLatin1String("ANDROID_NDK_ROOT"), config.ndkLocation(this).toUserOutput());
env.set(QLatin1String("ANDROID_NDK_PLATFORM"), env.set(QLatin1String("ANDROID_NDK_PLATFORM"),
config.bestNdkPlatformMatch(qMax(minimumNDK(), AndroidManager::minimumSDK(k)))); config.bestNdkPlatformMatch(qMax(minimumNDK(), AndroidManager::minimumSDK(k)), this));
} }
Utils::Environment AndroidQtVersion::qmakeRunEnvironment() const Utils::Environment AndroidQtVersion::qmakeRunEnvironment() const
{ {
Utils::Environment env = Utils::Environment::systemEnvironment(); Utils::Environment env = Utils::Environment::systemEnvironment();
env.set(QLatin1String("ANDROID_NDK_ROOT"), AndroidConfigurations::currentConfig().ndkLocation().toUserOutput()); env.set(QLatin1String("ANDROID_NDK_ROOT"),
AndroidConfigurations::currentConfig().ndkLocation(this).toUserOutput());
return env; return env;
} }

View File

@@ -225,10 +225,11 @@ AndroidRunnerWorker::AndroidRunnerWorker(RunWorker *runner, const QString &packa
<< "Extra Start Args:" << m_amStartExtraArgs << "Extra Start Args:" << m_amStartExtraArgs
<< "Before Start ADB cmds:" << m_beforeStartAdbCommands << "Before Start ADB cmds:" << m_beforeStartAdbCommands
<< "After finish ADB cmds:" << m_afterFinishAdbCommands; << "After finish ADB cmds:" << m_afterFinishAdbCommands;
QtSupport::BaseQtVersion *version = QtSupport::QtKitAspect::qtVersion(target->kit());
QString preferredAbi = AndroidManager::apkDevicePreferredAbi(target); QString preferredAbi = AndroidManager::apkDevicePreferredAbi(target);
if (!preferredAbi.isEmpty()) if (!preferredAbi.isEmpty())
m_gdbserverPath = AndroidConfigurations::instance()->currentConfig().gdbServer(preferredAbi).toString(); m_gdbserverPath = AndroidConfigurations::instance()
QtSupport::BaseQtVersion *version = QtSupport::QtKitAspect::qtVersion(target->kit()); ->currentConfig().gdbServer(preferredAbi, version).toString();
m_useAppParamsForQmlDebugger = version->qtVersion() >= QtSupport::QtVersionNumber(5, 12); m_useAppParamsForQmlDebugger = version->qtVersion() >= QtSupport::QtVersionNumber(5, 12);
} }

View File

@@ -336,10 +336,8 @@ Utils::FilePath AndroidSettingsWidget::getDefaultSdkPath()
void AndroidSettingsWidget::updateNdkList() void AndroidSettingsWidget::updateNdkList()
{ {
m_ui->ndkListComboBox->clear(); m_ui->ndkListComboBox->clear();
QString currentNdk = m_androidConfig.ndkLocation().toString();
for (const Ndk *ndk : m_sdkManager->installedNdkPackages()) for (const Ndk *ndk : m_sdkManager->installedNdkPackages())
m_ui->ndkListComboBox->addItem(ndk->installedLocation().toString()); m_ui->ndkListComboBox->addItem(ndk->installedLocation().toString());
m_ui->ndkListComboBox->setCurrentText(currentNdk);
} }
AndroidSettingsWidget::AndroidSettingsWidget() AndroidSettingsWidget::AndroidSettingsWidget()
@@ -584,7 +582,6 @@ Utils::FilePath AndroidSettingsWidget::findJdkInCommonPaths()
void AndroidSettingsWidget::validateNdk() void AndroidSettingsWidget::validateNdk()
{ {
auto ndkPath = Utils::FilePath::fromUserInput(m_ui->ndkListComboBox->currentText()); auto ndkPath = Utils::FilePath::fromUserInput(m_ui->ndkListComboBox->currentText());
m_androidConfig.setNdkLocation(ndkPath);
auto summaryWidget = static_cast<SummaryWidget *>(m_ui->androidDetailsWidget->widget()); auto summaryWidget = static_cast<SummaryWidget *>(m_ui->androidDetailsWidget->widget());
summaryWidget->setPointValid(NdkPathExistsRow, ndkPath.exists()); summaryWidget->setPointValid(NdkPathExistsRow, ndkPath.exists());
@@ -745,9 +742,10 @@ void AndroidSettingsWidget::updateUI()
m_ui->sdkManagerTab->setEnabled(sdkToolsOk); m_ui->sdkManagerTab->setEnabled(sdkToolsOk);
m_sdkManagerWidget->setSdkManagerControlsEnabled(!m_androidConfig.useNativeUiTools()); m_sdkManagerWidget->setSdkManagerControlsEnabled(!m_androidConfig.useNativeUiTools());
Utils::FilePath currentNdk = Utils::FilePath::fromString(m_ui->ndkListComboBox->currentText());
auto infoText = tr("(SDK Version: %1, NDK Bundle Version: %2)") auto infoText = tr("(SDK Version: %1, NDK Bundle Version: %2)")
.arg(m_androidConfig.sdkToolsVersion().toString()) .arg(m_androidConfig.sdkToolsVersion().toString())
.arg(m_androidConfig.ndkVersion().toString()); .arg(currentNdk.isEmpty() ? "" : m_androidConfig.ndkVersion(currentNdk).toString());
androidSummaryWidget->setInfoText(androidSetupOk ? infoText : ""); androidSummaryWidget->setInfoText(androidSetupOk ? infoText : "");
m_ui->javaDetailsWidget->setState(javaSetupOk ? Utils::DetailsWidget::Collapsed : m_ui->javaDetailsWidget->setState(javaSetupOk ? Utils::DetailsWidget::Collapsed :

View File

@@ -27,6 +27,7 @@
#include "androidconstants.h" #include "androidconstants.h"
#include "androidconfigurations.h" #include "androidconfigurations.h"
#include <projectexplorer/kitmanager.h>
#include <projectexplorer/toolchainmanager.h> #include <projectexplorer/toolchainmanager.h>
#include <projectexplorer/projectexplorer.h> #include <projectexplorer/projectexplorer.h>
@@ -78,22 +79,36 @@ AndroidToolChain::AndroidToolChain()
setTypeDisplayName(AndroidToolChainFactory::tr("Android Clang")); setTypeDisplayName(AndroidToolChainFactory::tr("Android Clang"));
} }
Utils::FilePath AndroidToolChain::ndkLocation() const
{
return m_ndkLocation;
}
void AndroidToolChain::setNdkLocation(const Utils::FilePath &ndkLocation)
{
m_ndkLocation = ndkLocation;
}
AndroidToolChain::~AndroidToolChain() = default; AndroidToolChain::~AndroidToolChain() = default;
bool AndroidToolChain::isValid() const bool AndroidToolChain::isValid() const
{ {
return ClangToolChain::isValid() const bool isChildofNdk = compilerCommand().isChildOf(m_ndkLocation);
&& typeId() == Constants::ANDROID_TOOLCHAIN_TYPEID // If we're restoring a toolchain we set NDK path ourselves so it's enough to check against SDK
const bool isChildofSdk = compilerCommand().isChildOf(
AndroidConfigurations::currentConfig().sdkLocation());
return ClangToolChain::isValid() && typeId() == Constants::ANDROID_TOOLCHAIN_TYPEID
&& targetAbi().isValid() && targetAbi().isValid()
&& compilerCommand().isChildOf(AndroidConfigurations::currentConfig().ndkLocation()) && (isChildofNdk || isChildofSdk)
&& !originalTargetTriple().isEmpty(); && !originalTargetTriple().isEmpty();
} }
void AndroidToolChain::addToEnvironment(Environment &env) const void AndroidToolChain::addToEnvironment(Environment &env) const
{ {
env.set(QLatin1String("ANDROID_NDK_HOST"), AndroidConfig config = AndroidConfigurations::currentConfig();
AndroidConfigurations::currentConfig().toolchainHost()); env.set(QLatin1String("ANDROID_NDK_HOST"), config.toolchainHostFromNdk(m_ndkLocation));
const Utils::FilePath javaHome = AndroidConfigurations::currentConfig().openJDKLocation(); const Utils::FilePath javaHome = config.openJDKLocation();
if (javaHome.exists()) { if (javaHome.exists()) {
env.set(QLatin1String("JAVA_HOME"), javaHome.toString()); env.set(QLatin1String("JAVA_HOME"), javaHome.toString());
const FilePath javaBin = javaHome.pathAppended("bin"); const FilePath javaBin = javaHome.pathAppended("bin");
@@ -101,10 +116,8 @@ void AndroidToolChain::addToEnvironment(Environment &env) const
if (!currentJavaFilePath.isChildOf(javaBin)) if (!currentJavaFilePath.isChildOf(javaBin))
env.prependOrSetPath(javaBin.toUserOutput()); env.prependOrSetPath(javaBin.toUserOutput());
} }
env.set(QLatin1String("ANDROID_HOME"), env.set(QLatin1String("ANDROID_HOME"), config.sdkLocation().toString());
AndroidConfigurations::currentConfig().sdkLocation().toString()); env.set(QLatin1String("ANDROID_SDK_ROOT"), config.sdkLocation().toString());
env.set(QLatin1String("ANDROID_SDK_ROOT"),
AndroidConfigurations::currentConfig().sdkLocation().toString());
} }
bool AndroidToolChain::fromMap(const QVariantMap &data) bool AndroidToolChain::fromMap(const QVariantMap &data)
@@ -122,7 +135,7 @@ QStringList AndroidToolChain::suggestedMkspecList() const
FilePath AndroidToolChain::makeCommand(const Environment &env) const FilePath AndroidToolChain::makeCommand(const Environment &env) const
{ {
Q_UNUSED(env) Q_UNUSED(env)
FilePath makePath = AndroidConfigurations::currentConfig().makePath(); FilePath makePath = AndroidConfigurations::currentConfig().makePathFromNdk(m_ndkLocation);
return makePath.exists() ? makePath : FilePath::fromString("make"); return makePath.exists() ? makePath : FilePath::fromString("make");
} }
@@ -160,17 +173,44 @@ static FilePath clangPlusPlusPath(const FilePath &clangPath)
QFileInfo(clangPath.toString()).baseName() + "++")); QFileInfo(clangPath.toString()).baseName() + "++"));
} }
static QList<QtSupport::BaseQtVersion *> androidQtVersionsWithUniqueNdk()
{
AndroidConfig config = AndroidConfigurations::currentConfig();
auto androidQtVersions = QtSupport::QtVersionManager::versions(
[](const QtSupport::BaseQtVersion *v) {
return v->targetDeviceTypes().contains(Android::Constants::ANDROID_DEVICE_TYPE);
});
auto shouldRemove = [config](const QtSupport::BaseQtVersion *first,
const QtSupport::BaseQtVersion *second) {
return config.ndkLocation(first) == config.ndkLocation(second);
};
QList<QtSupport::BaseQtVersion *>::iterator it = std::unique(androidQtVersions.begin(),
androidQtVersions.end(),
shouldRemove);
androidQtVersions.erase(it, androidQtVersions.end());
return androidQtVersions;
}
ToolChainList AndroidToolChainFactory::autodetectToolChainsForNdk(const ToolChainList &alreadyKnown) ToolChainList AndroidToolChainFactory::autodetectToolChainsForNdk(const ToolChainList &alreadyKnown)
{ {
QList<ToolChain *> result; QList<ToolChain *> result;
FilePath clangPath = AndroidConfigurations::currentConfig().clangPath(); const QList<QtSupport::BaseQtVersion *> androidQtVersions = androidQtVersionsWithUniqueNdk();
const AndroidConfig config = AndroidConfigurations::currentConfig();
for (const QtSupport::BaseQtVersion *qtVersion : androidQtVersions) {
FilePath clangPath = config.clangPath(qtVersion);
if (!clangPath.exists()) { if (!clangPath.exists()) {
qCDebug(androidTCLog) << "Clang toolchains detection fails. Can not find Clang"<< clangPath; qCDebug(androidTCLog) << "Clang toolchains detection fails. Can not find Clang"
<< clangPath;
return result; return result;
} }
qCDebug(androidTCLog) << "Detecting toolchains from Android NDK:" qCDebug(androidTCLog) << "Detecting toolchains from Android NDK:"
<< AndroidConfigurations::currentConfig().ndkLocation(); << config.ndkLocation(qtVersion);
for (const Core::Id &lang : LanguageIds) { for (const Core::Id &lang : LanguageIds) {
FilePath compilerCommand = clangPath; FilePath compilerCommand = clangPath;
@@ -178,8 +218,8 @@ ToolChainList AndroidToolChainFactory::autodetectToolChainsForNdk(const ToolChai
compilerCommand = clangPlusPlusPath(clangPath); compilerCommand = clangPlusPlusPath(clangPath);
if (!compilerCommand.exists()) { if (!compilerCommand.exists()) {
qCDebug(androidTCLog) << "Skipping Clang toolchain. Can not find compiler" qCDebug(androidTCLog)
<< compilerCommand; << "Skipping Clang toolchain. Can not find compiler" << compilerCommand;
continue; continue;
} }
@@ -192,16 +232,18 @@ ToolChainList AndroidToolChainFactory::autodetectToolChainsForNdk(const ToolChai
qCDebug(androidTCLog) << "Tool chain already known" << abi.toString() << lang; qCDebug(androidTCLog) << "Tool chain already known" << abi.toString() << lang;
} else { } else {
qCDebug(androidTCLog) << "New Clang toolchain found" << abi.toString() << lang; qCDebug(androidTCLog) << "New Clang toolchain found" << abi.toString() << lang;
auto atc = new AndroidToolChain; auto atc = new AndroidToolChain();
atc->setNdkLocation(config.ndkLocation(qtVersion));
atc->setOriginalTargetTriple(target); atc->setOriginalTargetTriple(target);
atc->setLanguage(lang); atc->setLanguage(lang);
atc->setTargetAbi(ClangTargets[target]); atc->setTargetAbi(ClangTargets[target]);
atc->setPlatformCodeGenFlags({"-target", target}); atc->setPlatformCodeGenFlags({"-target", target});
atc->setPlatformLinkerFlags({"-target", target}); atc->setPlatformLinkerFlags({"-target", target});
atc->setDetection(ToolChain::AutoDetection); atc->setDetection(ToolChain::AutoDetection);
atc->setDisplayName(QString("Android Clang (%1, %2)") atc->setDisplayName(QString("Android Clang (%1, %2, NDK %3)")
.arg(ToolChainManager::displayNameOfLanguageId(lang), .arg(ToolChainManager::displayNameOfLanguageId(lang),
AndroidConfig::displayName(abi))); AndroidConfig::displayName(abi),
config.ndkVersion(qtVersion).toString()));
atc->resetToolChain(compilerCommand); atc->resetToolChain(compilerCommand);
tc = atc; tc = atc;
} }
@@ -209,6 +251,7 @@ ToolChainList AndroidToolChainFactory::autodetectToolChainsForNdk(const ToolChai
++targetItr; ++targetItr;
} }
} }
}
return result; return result;
} }

View File

@@ -25,6 +25,8 @@
#pragma once #pragma once
#include <qtsupport/baseqtversion.h>
#include <projectexplorer/gcctoolchain.h> #include <projectexplorer/gcctoolchain.h>
namespace Android { namespace Android {
@@ -44,6 +46,9 @@ public:
Utils::FilePath makeCommand(const Utils::Environment &environment) const override; Utils::FilePath makeCommand(const Utils::Environment &environment) const override;
bool fromMap(const QVariantMap &data) override; bool fromMap(const QVariantMap &data) override;
void setNdkLocation(const Utils::FilePath &ndkLocation);
Utils::FilePath ndkLocation() const;
protected: protected:
DetectedAbisResult detectSupportedAbis() const override; DetectedAbisResult detectSupportedAbis() const override;
@@ -51,6 +56,8 @@ private:
explicit AndroidToolChain(); explicit AndroidToolChain();
friend class AndroidToolChainFactory; friend class AndroidToolChainFactory;
Utils::FilePath m_ndkLocation;
}; };
class AndroidToolChainFactory : public ProjectExplorer::ToolChainFactory class AndroidToolChainFactory : public ProjectExplorer::ToolChainFactory

View File

@@ -49,28 +49,6 @@ namespace Uv {
const char kProjectSchema[] = "2.1"; const char kProjectSchema[] = "2.1";
// Helpers
QString toolsFilePath(const QString &uVisionFilePath)
{
const QFileInfo fi(uVisionFilePath);
QDir dir = fi.dir();
if (!dir.cdUp())
return {};
return dir.absoluteFilePath("tools.ini");
}
QString targetUVisionPath()
{
if (const Target *target = SessionManager::startupTarget()) {
if (const Kit *kit = target->kit()) {
const Runnable runnable = DebuggerKitAspect::runnable(kit);
return runnable.executable.toString();
}
}
return {};
}
static QString buildToolsetNumber(int number) static QString buildToolsetNumber(int number)
{ {
return QStringLiteral("0x%1").arg(QString::number(number, 16)); return QStringLiteral("0x%1").arg(QString::number(number, 16));

View File

@@ -39,11 +39,6 @@ class UvscServerProvider;
namespace Uv { namespace Uv {
// Helpers
QString toolsFilePath(const QString &uVisionFilePath);
QString targetUVisionPath();
// UvProject // UvProject
class Project final : public Gen::Xml::Project class Project final : public Gen::Xml::Project

View File

@@ -39,6 +39,7 @@
#include <projectexplorer/project.h> #include <projectexplorer/project.h>
#include <projectexplorer/runconfigurationaspects.h> #include <projectexplorer/runconfigurationaspects.h>
#include <utils/pathchooser.h>
#include <utils/qtcassert.h> #include <utils/qtcassert.h>
#include <QComboBox> #include <QComboBox>
@@ -57,6 +58,7 @@ namespace Internal {
using namespace Uv; using namespace Uv;
// Whole software package selection keys. // Whole software package selection keys.
constexpr char toolsIniKeyC[] = "BareMetal.UvscServerProvider.ToolsIni";
constexpr char deviceSelectionKeyC[] = "BareMetal.UvscServerProvider.DeviceSelection"; constexpr char deviceSelectionKeyC[] = "BareMetal.UvscServerProvider.DeviceSelection";
constexpr char driverSelectionKeyC[] = "BareMetal.UvscServerProvider.DriverSelection"; constexpr char driverSelectionKeyC[] = "BareMetal.UvscServerProvider.DriverSelection";
@@ -78,6 +80,16 @@ UvscServerProvider::UvscServerProvider(const UvscServerProvider &other)
setEngineType(UvscEngineType); setEngineType(UvscEngineType);
} }
void UvscServerProvider::setToolsIniFile(const Utils::FilePath &toolsIniFile)
{
m_toolsIniFile = toolsIniFile;
}
Utils::FilePath UvscServerProvider::toolsIniFile() const
{
return m_toolsIniFile;
}
void UvscServerProvider::setDeviceSelection(const DeviceSelection &deviceSelection) void UvscServerProvider::setDeviceSelection(const DeviceSelection &deviceSelection)
{ {
m_deviceSelection = deviceSelection; m_deviceSelection = deviceSelection;
@@ -123,7 +135,8 @@ bool UvscServerProvider::operator==(const IDebugServerProvider &other) const
if (!IDebugServerProvider::operator==(other)) if (!IDebugServerProvider::operator==(other))
return false; return false;
const auto p = static_cast<const UvscServerProvider *>(&other); const auto p = static_cast<const UvscServerProvider *>(&other);
return m_deviceSelection == p->m_deviceSelection return m_toolsIniFile == p->m_toolsIniFile
&& m_deviceSelection == p->m_deviceSelection
&& m_driverSelection == p->m_driverSelection && m_driverSelection == p->m_driverSelection
&& m_toolsetNumber == p->m_toolsetNumber; && m_toolsetNumber == p->m_toolsetNumber;
} }
@@ -147,6 +160,7 @@ FilePath UvscServerProvider::buildOptionsFilePath(DebuggerRunTool *runTool) cons
QVariantMap UvscServerProvider::toMap() const QVariantMap UvscServerProvider::toMap() const
{ {
QVariantMap data = IDebugServerProvider::toMap(); QVariantMap data = IDebugServerProvider::toMap();
data.insert(toolsIniKeyC, m_toolsIniFile.toVariant());
data.insert(deviceSelectionKeyC, m_deviceSelection.toMap()); data.insert(deviceSelectionKeyC, m_deviceSelection.toMap());
data.insert(driverSelectionKeyC, m_driverSelection.toMap()); data.insert(driverSelectionKeyC, m_driverSelection.toMap());
return data; return data;
@@ -217,6 +231,7 @@ bool UvscServerProvider::fromMap(const QVariantMap &data)
{ {
if (!IDebugServerProvider::fromMap(data)) if (!IDebugServerProvider::fromMap(data))
return false; return false;
m_toolsIniFile = FilePath::fromVariant(data.value(toolsIniKeyC));
m_deviceSelection.fromMap(data.value(deviceSelectionKeyC).toMap()); m_deviceSelection.fromMap(data.value(deviceSelectionKeyC).toMap());
m_driverSelection.fromMap(data.value(driverSelectionKeyC).toMap()); m_driverSelection.fromMap(data.value(driverSelectionKeyC).toMap());
return true; return true;
@@ -257,6 +272,11 @@ UvscServerProviderConfigWidget::UvscServerProviderConfigWidget(UvscServerProvide
{ {
m_hostWidget = new HostWidget; m_hostWidget = new HostWidget;
m_mainLayout->addRow(tr("Host:"), m_hostWidget); m_mainLayout->addRow(tr("Host:"), m_hostWidget);
m_toolsIniChooser = new PathChooser;
m_toolsIniChooser->setExpectedKind(PathChooser::File);
m_toolsIniChooser->setPromptDialogFilter("tools.ini");
m_toolsIniChooser->setPromptDialogTitle(tr("Choose a Keil toolset configuration file"));
m_mainLayout->addRow(tr("Tools file path:"), m_toolsIniChooser);
m_deviceSelector = new DeviceSelector; m_deviceSelector = new DeviceSelector;
m_mainLayout->addRow(tr("Target device:"), m_deviceSelector); m_mainLayout->addRow(tr("Target device:"), m_deviceSelector);
m_driverSelector = new DriverSelector(provider->supportedDrivers()); m_driverSelector = new DriverSelector(provider->supportedDrivers());
@@ -266,15 +286,27 @@ UvscServerProviderConfigWidget::UvscServerProviderConfigWidget(UvscServerProvide
connect(m_hostWidget, &HostWidget::dataChanged, connect(m_hostWidget, &HostWidget::dataChanged,
this, &UvscServerProviderConfigWidget::dirty); this, &UvscServerProviderConfigWidget::dirty);
connect(m_toolsIniChooser, &PathChooser::pathChanged,
this, &UvscServerProviderConfigWidget::dirty);
connect(m_deviceSelector, &DeviceSelector::selectionChanged, connect(m_deviceSelector, &DeviceSelector::selectionChanged,
this, &UvscServerProviderConfigWidget::dirty); this, &UvscServerProviderConfigWidget::dirty);
connect(m_driverSelector, &DriverSelector::selectionChanged, connect(m_driverSelector, &DriverSelector::selectionChanged,
this, &UvscServerProviderConfigWidget::dirty); this, &UvscServerProviderConfigWidget::dirty);
auto updateSelectors = [this]() {
const FilePath toolsIniFile = m_toolsIniChooser->fileName();
m_deviceSelector->setToolsIniFile(toolsIniFile);
m_driverSelector->setToolsIniFile(toolsIniFile);
};
connect(m_toolsIniChooser, &PathChooser::pathChanged, updateSelectors);
updateSelectors();
} }
void UvscServerProviderConfigWidget::apply() void UvscServerProviderConfigWidget::apply()
{ {
const auto p = static_cast<UvscServerProvider *>(m_provider); const auto p = static_cast<UvscServerProvider *>(m_provider);
p->setToolsIniFile(toolsIniFile());
p->setDeviceSelection(deviceSelection()); p->setDeviceSelection(deviceSelection());
p->setDriverSelection(driverSelection()); p->setDriverSelection(driverSelection());
IDebugServerProviderConfigWidget::apply(); IDebugServerProviderConfigWidget::apply();
@@ -286,6 +318,16 @@ void UvscServerProviderConfigWidget::discard()
IDebugServerProviderConfigWidget::discard(); IDebugServerProviderConfigWidget::discard();
} }
void UvscServerProviderConfigWidget::setToolsIniFile(const Utils::FilePath &toolsIniFile)
{
m_toolsIniChooser->setFileName(toolsIniFile);
}
Utils::FilePath UvscServerProviderConfigWidget::toolsIniFile() const
{
return m_toolsIniChooser->fileName();
}
void UvscServerProviderConfigWidget::setDeviceSelection(const DeviceSelection &deviceSelection) void UvscServerProviderConfigWidget::setDeviceSelection(const DeviceSelection &deviceSelection)
{ {
m_deviceSelector->setSelection(deviceSelection); m_deviceSelector->setSelection(deviceSelection);
@@ -310,6 +352,7 @@ void UvscServerProviderConfigWidget::setFromProvider()
{ {
const auto p = static_cast<UvscServerProvider *>(m_provider); const auto p = static_cast<UvscServerProvider *>(m_provider);
m_hostWidget->setChannel(p->channel()); m_hostWidget->setChannel(p->channel());
m_toolsIniChooser->setFileName(p->toolsIniFile());
m_deviceSelector->setSelection(p->deviceSelection()); m_deviceSelector->setSelection(p->deviceSelection());
m_driverSelector->setSelection(p->driverSelection()); m_driverSelector->setSelection(p->driverSelection());
} }

View File

@@ -32,6 +32,8 @@
#include <projectexplorer/runcontrol.h> // for RunWorker #include <projectexplorer/runcontrol.h> // for RunWorker
namespace Utils { class PathChooser; }
namespace BareMetal { namespace BareMetal {
namespace Internal { namespace Internal {
@@ -54,6 +56,9 @@ public:
ArmAdsToolsetNumber = 4 // ARM-ADS toolset ArmAdsToolsetNumber = 4 // ARM-ADS toolset
}; };
void setToolsIniFile(const Utils::FilePath &toolsIniFile);
Utils::FilePath toolsIniFile() const;
void setDeviceSelection(const Uv::DeviceSelection &deviceSelection); void setDeviceSelection(const Uv::DeviceSelection &deviceSelection);
Uv::DeviceSelection deviceSelection() const; Uv::DeviceSelection deviceSelection() const;
@@ -91,6 +96,7 @@ protected:
virtual Utils::FilePath optionsFilePath(Debugger::DebuggerRunTool *runTool, virtual Utils::FilePath optionsFilePath(Debugger::DebuggerRunTool *runTool,
QString &errorMessage) const = 0; QString &errorMessage) const = 0;
Utils::FilePath m_toolsIniFile;
Uv::DeviceSelection m_deviceSelection; Uv::DeviceSelection m_deviceSelection;
Uv::DriverSelection m_driverSelection; Uv::DriverSelection m_driverSelection;
@@ -113,6 +119,8 @@ public:
void discard() override; void discard() override;
protected: protected:
void setToolsIniFile(const Utils::FilePath &toolsIniFile);
Utils::FilePath toolsIniFile() const;
void setDeviceSelection(const Uv::DeviceSelection &deviceSelection); void setDeviceSelection(const Uv::DeviceSelection &deviceSelection);
Uv::DeviceSelection deviceSelection() const; Uv::DeviceSelection deviceSelection() const;
void setDriverSelection(const Uv::DriverSelection &driverSelection); void setDriverSelection(const Uv::DriverSelection &driverSelection);
@@ -121,6 +129,7 @@ protected:
void setFromProvider(); void setFromProvider();
HostWidget *m_hostWidget = nullptr; HostWidget *m_hostWidget = nullptr;
Utils::PathChooser *m_toolsIniChooser = nullptr;
Uv::DeviceSelector *m_deviceSelector = nullptr; Uv::DeviceSelector *m_deviceSelector = nullptr;
Uv::DriverSelector *m_driverSelector = nullptr; Uv::DriverSelector *m_driverSelector = nullptr;
}; };

View File

@@ -23,7 +23,6 @@
** **
****************************************************************************/ ****************************************************************************/
#include "uvproject.h" // for toolsFilePath()
#include "uvtargetdevicemodel.h" #include "uvtargetdevicemodel.h"
#include <QDirIterator> #include <QDirIterator>
@@ -37,9 +36,9 @@ namespace BareMetal {
namespace Internal { namespace Internal {
namespace Uv { namespace Uv {
static QString extractPacksPath(const QString &uVisionFilePath) static QString extractPacksPath(const FilePath &toolsIniFile)
{ {
QFile f(toolsFilePath(uVisionFilePath)); QFile f(toolsIniFile.toString());
if (!f.open(QIODevice::ReadOnly)) if (!f.open(QIODevice::ReadOnly))
return {}; return {};
QTextStream in(&f); QTextStream in(&f);
@@ -258,15 +257,15 @@ DeviceSelectionModel::DeviceSelectionModel(QObject *parent)
setHeader({tr("Name"), tr("Version"), tr("Vendor")}); setHeader({tr("Name"), tr("Version"), tr("Vendor")});
} }
void DeviceSelectionModel::fillAllPacks(const QString &uVisionFilePath) void DeviceSelectionModel::fillAllPacks(const FilePath &toolsIniFile)
{ {
if (m_uVisionFilePath == uVisionFilePath) if (m_toolsIniFile == toolsIniFile)
return; return;
clear(); clear();
m_uVisionFilePath = uVisionFilePath; m_toolsIniFile = toolsIniFile;
const QString packsPath = extractPacksPath(m_uVisionFilePath); const QString packsPath = extractPacksPath(m_toolsIniFile);
if (packsPath.isEmpty()) if (packsPath.isEmpty())
return; return;

View File

@@ -28,6 +28,7 @@
#include "uvtargetdeviceselection.h" #include "uvtargetdeviceselection.h"
#include <utils/basetreeview.h> #include <utils/basetreeview.h>
#include <utils/fileutils.h>
#include <utils/treemodel.h> #include <utils/treemodel.h>
QT_BEGIN_NAMESPACE QT_BEGIN_NAMESPACE
@@ -47,7 +48,7 @@ class DeviceSelectionModel final : public Utils::TreeModel<DeviceSelectionItem>
public: public:
explicit DeviceSelectionModel(QObject *parent = nullptr); explicit DeviceSelectionModel(QObject *parent = nullptr);
void fillAllPacks(const QString &uVisionFilePath); void fillAllPacks(const Utils::FilePath &toolsIniFile);
private: private:
void parsePackage(const QString &packageFile); void parsePackage(const QString &packageFile);
@@ -59,7 +60,7 @@ private:
DeviceSelection::Cpu &cpu, DeviceSelection::Memories &memories); DeviceSelection::Cpu &cpu, DeviceSelection::Memories &memories);
void parseDeviceVariant(QXmlStreamReader &in, DeviceSelectionItem *parent); void parseDeviceVariant(QXmlStreamReader &in, DeviceSelectionItem *parent);
QString m_uVisionFilePath; Utils::FilePath m_toolsIniFile;
}; };
// DeviceSelectionView // DeviceSelectionView

View File

@@ -124,28 +124,30 @@ DeviceSelector::DeviceSelector(QWidget *parent)
setWidget(detailsPanel); setWidget(detailsPanel);
connect(toolPanel, &DeviceSelectorToolPanel::clicked, this, [this]() { connect(toolPanel, &DeviceSelectorToolPanel::clicked, this, [this]() {
const QString uVisionPath = targetUVisionPath(); DeviceSelectionDialog dialog(m_toolsIniFile, this);
if (uVisionPath.isEmpty()) {
QMessageBox::warning(this,
tr("uVision path not found"),
tr("Please open a configured project before\n"
"the target device selection."),
QMessageBox::Ok);
} else {
DeviceSelectionDialog dialog(uVisionPath, this);
const int result = dialog.exec(); const int result = dialog.exec();
if (result != QDialog::Accepted) if (result != QDialog::Accepted)
return; return;
DeviceSelection selection; DeviceSelection selection;
selection = dialog.selection(); selection = dialog.selection();
setSelection(selection); setSelection(selection);
}
}); });
connect(detailsPanel, &DeviceSelectorDetailsPanel::selectionChanged, connect(detailsPanel, &DeviceSelectorDetailsPanel::selectionChanged,
this, &DeviceSelector::selectionChanged); this, &DeviceSelector::selectionChanged);
} }
void DeviceSelector::setToolsIniFile(const Utils::FilePath &toolsIniFile)
{
m_toolsIniFile = toolsIniFile;
setEnabled(m_toolsIniFile.exists());
}
Utils::FilePath DeviceSelector::toolsIniFile() const
{
return m_toolsIniFile;
}
void DeviceSelector::setSelection(const DeviceSelection &selection) void DeviceSelector::setSelection(const DeviceSelection &selection)
{ {
m_selection = selection; m_selection = selection;
@@ -167,7 +169,7 @@ DeviceSelection DeviceSelector::selection() const
// DeviceSelectionDialog // DeviceSelectionDialog
DeviceSelectionDialog::DeviceSelectionDialog(const QString &uVisionPath, QWidget *parent) DeviceSelectionDialog::DeviceSelectionDialog(const Utils::FilePath &toolsIniFile, QWidget *parent)
: QDialog(parent), m_model(new DeviceSelectionModel(this)), m_view(new DeviceSelectionView(this)) : QDialog(parent), m_model(new DeviceSelectionModel(this)), m_view(new DeviceSelectionView(this))
{ {
setWindowTitle(tr("Available target devices")); setWindowTitle(tr("Available target devices"));
@@ -187,7 +189,7 @@ DeviceSelectionDialog::DeviceSelectionDialog(const QString &uVisionPath, QWidget
m_selection = selection; m_selection = selection;
}); });
m_model->fillAllPacks(uVisionPath); m_model->fillAllPacks(toolsIniFile);
m_view->setModel(m_model); m_view->setModel(m_model);
} }

View File

@@ -29,6 +29,7 @@
#include <utils/detailsbutton.h> #include <utils/detailsbutton.h>
#include <utils/detailswidget.h> #include <utils/detailswidget.h>
#include <utils/fileutils.h>
#include <QDialog> #include <QDialog>
@@ -55,6 +56,9 @@ class DeviceSelector final : public Utils::DetailsWidget
public: public:
explicit DeviceSelector(QWidget *parent = nullptr); explicit DeviceSelector(QWidget *parent = nullptr);
void setToolsIniFile(const Utils::FilePath &toolsIniFile);
Utils::FilePath toolsIniFile() const;
void setSelection(const DeviceSelection &selection); void setSelection(const DeviceSelection &selection);
DeviceSelection selection() const; DeviceSelection selection() const;
@@ -62,6 +66,7 @@ signals:
void selectionChanged(); void selectionChanged();
private: private:
Utils::FilePath m_toolsIniFile;
DeviceSelection m_selection; DeviceSelection m_selection;
}; };
@@ -111,7 +116,7 @@ class DeviceSelectionDialog final : public QDialog
Q_OBJECT Q_OBJECT
public: public:
explicit DeviceSelectionDialog(const QString &uVisionPath, QWidget *parent = nullptr); explicit DeviceSelectionDialog(const Utils::FilePath &toolsIniFile, QWidget *parent = nullptr);
DeviceSelection selection() const; DeviceSelection selection() const;
private: private:

View File

@@ -23,7 +23,6 @@
** **
****************************************************************************/ ****************************************************************************/
#include "uvproject.h" // for toolsFilePath()
#include "uvtargetdrivermodel.h" #include "uvtargetdrivermodel.h"
#include <QFile> #include <QFile>
@@ -132,12 +131,12 @@ DriverSelectionModel::DriverSelectionModel(QObject *parent)
setHeader({tr("Path")}); setHeader({tr("Path")});
} }
void DriverSelectionModel::fillDrivers(const QString &uVisionFilePath, void DriverSelectionModel::fillDrivers(const FilePath &toolsIniFile,
const QStringList &supportedDrivers) const QStringList &supportedDrivers)
{ {
clear(); clear();
QFile f(toolsFilePath(uVisionFilePath)); QFile f(toolsIniFile.toString());
if (!f.open(QIODevice::ReadOnly)) if (!f.open(QIODevice::ReadOnly))
return; return;

View File

@@ -28,6 +28,7 @@
#include "uvtargetdriverselection.h" #include "uvtargetdriverselection.h"
#include <utils/basetreeview.h> #include <utils/basetreeview.h>
#include <utils/fileutils.h>
#include <utils/treemodel.h> #include <utils/treemodel.h>
namespace BareMetal { namespace BareMetal {
@@ -43,7 +44,7 @@ class DriverSelectionModel final : public Utils::TreeModel<DriverSelectionItem>
public: public:
explicit DriverSelectionModel(QObject *parent = nullptr); explicit DriverSelectionModel(QObject *parent = nullptr);
void fillDrivers(const QString &uVisionFilePath, const QStringList &supportedDrivers); void fillDrivers(const Utils::FilePath &toolsIniFile, const QStringList &supportedDrivers);
}; };
// DriverSelectionView // DriverSelectionView

View File

@@ -105,28 +105,30 @@ DriverSelector::DriverSelector(const QStringList &supportedDrivers, QWidget *par
setWidget(detailsPanel); setWidget(detailsPanel);
connect(toolPanel, &DriverSelectorToolPanel::clicked, this, [=]() { connect(toolPanel, &DriverSelectorToolPanel::clicked, this, [=]() {
const QString uVisionPath = targetUVisionPath(); DriverSelectionDialog dialog(m_toolsIniFile, supportedDrivers, this);
if (uVisionPath.isEmpty()) {
QMessageBox::warning(this,
tr("uVision path not found"),
tr("Please open a configured project before\n"
"the target driver selection."),
QMessageBox::Ok);
} else {
DriverSelectionDialog dialog(uVisionPath, supportedDrivers, this);
const int result = dialog.exec(); const int result = dialog.exec();
if (result != QDialog::Accepted) if (result != QDialog::Accepted)
return; return;
DriverSelection selection; DriverSelection selection;
selection = dialog.selection(); selection = dialog.selection();
setSelection(selection); setSelection(selection);
}
}); });
connect(detailsPanel, &DriverSelectorDetailsPanel::selectionChanged, connect(detailsPanel, &DriverSelectorDetailsPanel::selectionChanged,
this, &DriverSelector::selectionChanged); this, &DriverSelector::selectionChanged);
} }
void DriverSelector::setToolsIniFile(const Utils::FilePath &toolsIniFile)
{
m_toolsIniFile = toolsIniFile;
setEnabled(m_toolsIniFile.exists());
}
Utils::FilePath DriverSelector::toolsIniFile() const
{
return m_toolsIniFile;
}
void DriverSelector::setSelection(const DriverSelection &selection) void DriverSelector::setSelection(const DriverSelection &selection)
{ {
m_selection = selection; m_selection = selection;
@@ -148,7 +150,7 @@ DriverSelection DriverSelector::selection() const
// DriverSelectionDialog // DriverSelectionDialog
DriverSelectionDialog::DriverSelectionDialog(const QString &uVisionPath, DriverSelectionDialog::DriverSelectionDialog(const Utils::FilePath &toolsIniFile,
const QStringList &supportedDrivers, const QStringList &supportedDrivers,
QWidget *parent) QWidget *parent)
: QDialog(parent), m_model(new DriverSelectionModel(this)), : QDialog(parent), m_model(new DriverSelectionModel(this)),
@@ -171,7 +173,7 @@ DriverSelectionDialog::DriverSelectionDialog(const QString &uVisionPath,
m_selection = selection; m_selection = selection;
}); });
m_model->fillDrivers(uVisionPath, supportedDrivers); m_model->fillDrivers(toolsIniFile, supportedDrivers);
m_view->setModel(m_model); m_view->setModel(m_model);
} }

View File

@@ -29,6 +29,7 @@
#include <utils/detailsbutton.h> #include <utils/detailsbutton.h>
#include <utils/detailswidget.h> #include <utils/detailswidget.h>
#include <utils/fileutils.h>
#include <QDialog> #include <QDialog>
@@ -52,6 +53,10 @@ class DriverSelector final : public Utils::DetailsWidget
public: public:
explicit DriverSelector(const QStringList &supportedDrivers, QWidget *parent = nullptr); explicit DriverSelector(const QStringList &supportedDrivers, QWidget *parent = nullptr);
void setToolsIniFile(const Utils::FilePath &toolsIniFile);
Utils::FilePath toolsIniFile() const;
void setSelection(const DriverSelection &selection); void setSelection(const DriverSelection &selection);
DriverSelection selection() const; DriverSelection selection() const;
@@ -59,6 +64,7 @@ signals:
void selectionChanged(); void selectionChanged();
private: private:
Utils::FilePath m_toolsIniFile;
DriverSelection m_selection; DriverSelection m_selection;
}; };
@@ -105,7 +111,7 @@ class DriverSelectionDialog final : public QDialog
Q_OBJECT Q_OBJECT
public: public:
explicit DriverSelectionDialog(const QString &uVisionPath, explicit DriverSelectionDialog(const Utils::FilePath &toolsIniFile,
const QStringList &supportedDrivers, const QStringList &supportedDrivers,
QWidget *parent = nullptr); QWidget *parent = nullptr);
DriverSelection selection() const; DriverSelection selection() const;

View File

@@ -392,8 +392,10 @@ void Client::deactivateDocument(TextEditor::TextDocument *document)
hideDiagnostics(document); hideDiagnostics(document);
resetAssistProviders(document); resetAssistProviders(document);
document->setFormatter(nullptr); document->setFormatter(nullptr);
if (m_serverCapabilities.semanticHighlighting().has_value()) {
if (TextEditor::SyntaxHighlighter *highlighter = document->syntaxHighlighter()) if (TextEditor::SyntaxHighlighter *highlighter = document->syntaxHighlighter())
highlighter->clearAllExtraFormats(); highlighter->clearAllExtraFormats();
}
for (Core::IEditor *editor : Core::DocumentModel::editorsForDocument(document)) { for (Core::IEditor *editor : Core::DocumentModel::editorsForDocument(document)) {
if (auto textEditor = qobject_cast<TextEditor::BaseTextEditor *>(editor)) if (auto textEditor = qobject_cast<TextEditor::BaseTextEditor *>(editor))
textEditor->editorWidget()->removeHoverHandler(&m_hoverHandler); textEditor->editorWidget()->removeHoverHandler(&m_hoverHandler);

View File

@@ -151,11 +151,13 @@ void applyHighlight(TextEditor::TextDocument *doc,
} }
} }
if (capabilities.semanticHighlighting().has_value()) {
TextEditor::SemanticHighlighter::setExtraAdditionalFormats( TextEditor::SemanticHighlighter::setExtraAdditionalFormats(
doc->syntaxHighlighter(), doc->syntaxHighlighter(),
results, results,
scopesToFormatHash(highlightScopes(capabilities), doc->fontSettings())); scopesToFormatHash(highlightScopes(capabilities), doc->fontSettings()));
} }
}
} // namespace SemanticHighligtingSupport } // namespace SemanticHighligtingSupport
} // namespace LanguageClient } // namespace LanguageClient

View File

@@ -561,8 +561,10 @@ RunConfiguration *RunConfigurationFactory::restore(Target *parent, const QVarian
const Core::Id id = idFromMap(map); const Core::Id id = idFromMap(map);
if (id.name().startsWith(factory->m_runConfigBaseId.name())) { if (id.name().startsWith(factory->m_runConfigBaseId.name())) {
RunConfiguration *rc = factory->create(parent); RunConfiguration *rc = factory->create(parent);
if (rc->fromMap(map)) if (rc->fromMap(map)) {
rc->update();
return rc; return rc;
}
delete rc; delete rc;
return nullptr; return nullptr;
} }

View File

@@ -386,6 +386,7 @@ extend_qtc_plugin(QmlDesigner
include/abstractproperty.h include/abstractproperty.h
include/abstractview.h include/abstractview.h
include/anchorline.h include/anchorline.h
include/annotation.h
include/basetexteditmodifier.h include/basetexteditmodifier.h
include/bindingproperty.h include/bindingproperty.h
include/bytearraymodifier.h include/bytearraymodifier.h
@@ -475,6 +476,7 @@ extend_qtc_plugin(QmlDesigner
model/abstractproperty.cpp model/abstractproperty.cpp
model/abstractview.cpp model/abstractview.cpp
model/anchorline.cpp model/anchorline.cpp
model/annotation.cpp
model/basetexteditmodifier.cpp model/basetexteditmodifier.cpp
model/bindingproperty.cpp model/bindingproperty.cpp
model/componenttextmodifier.cpp model/componenttextmodifier.cpp
@@ -541,8 +543,7 @@ extend_qtc_plugin(QmlDesigner
extend_qtc_plugin(QmlDesigner extend_qtc_plugin(QmlDesigner
SOURCES_PREFIX components/annotationeditor SOURCES_PREFIX components/annotationeditor
SOURCES annotation.cpp annotation.h SOURCES annotationcommenttab.cpp annotationcommenttab.h annotationcommenttab.ui
annotationcommenttab.cpp annotationcommenttab.h annotationcommenttab.ui
annotationeditordialog.cpp annotationeditordialog.h annotationeditordialog.ui annotationeditordialog.cpp annotationeditordialog.h annotationeditordialog.ui
annotationeditor.cpp annotationeditor.h annotationeditor.cpp annotationeditor.h
annotationtool.cpp annotationtool.h annotationtool.cpp annotationtool.h

View File

@@ -1,10 +1,8 @@
HEADERS += $$PWD/annotation.h
HEADERS += $$PWD/annotationtool.h HEADERS += $$PWD/annotationtool.h
HEADERS += $$PWD/annotationcommenttab.h HEADERS += $$PWD/annotationcommenttab.h
HEADERS += $$PWD/annotationeditordialog.h HEADERS += $$PWD/annotationeditordialog.h
HEADERS += $$PWD/annotationeditor.h HEADERS += $$PWD/annotationeditor.h
SOURCES += $$PWD/annotation.cpp
SOURCES += $$PWD/annotationtool.cpp SOURCES += $$PWD/annotationtool.cpp
SOURCES += $$PWD/annotationcommenttab.cpp SOURCES += $$PWD/annotationcommenttab.cpp
SOURCES += $$PWD/annotationeditordialog.cpp SOURCES += $$PWD/annotationeditordialog.cpp

View File

@@ -30,14 +30,13 @@
#include "ui_annotationcommenttab.h" #include "ui_annotationcommenttab.h"
#include <timelineicons.h> //replace timeline icons with our own?
#include <QObject> #include <QObject>
#include <QToolBar> #include <QToolBar>
#include <QAction> #include <QAction>
#include <QMessageBox> #include <QMessageBox>
#include "timelineicons.h" //replace timeline icons with our own?
namespace QmlDesigner { namespace QmlDesigner {
AnnotationEditorDialog::AnnotationEditorDialog(QWidget *parent, const QString &targetId, const QString &customId, const Annotation &annotation) AnnotationEditorDialog::AnnotationEditorDialog(QWidget *parent, const QString &targetId, const QString &customId, const Annotation &annotation)

View File

@@ -35,7 +35,6 @@
#include <coreplugin/icore.h> #include <coreplugin/icore.h>
#include <utils/theme/theme.h> #include <utils/theme/theme.h>
#include <utils/stylehelper.h> #include <utils/stylehelper.h>
#include <annotationeditor/annotation.h>
#include <annotationeditor/annotationeditordialog.h> #include <annotationeditor/annotationeditordialog.h>
#include <formeditorscene.h> #include <formeditorscene.h>

View File

@@ -25,17 +25,13 @@
#pragma once #pragma once
#include <annotationeditor/annotation.h> #include <annotation.h>
#include <modelnode.h>
#include <QGraphicsItem> #include <QGraphicsItem>
#include <QGraphicsObject> #include <QGraphicsObject>
#include <QIcon> #include <QIcon>
#include <QObject> #include <QObject>
#include <modelnode.h>
QT_BEGIN_NAMESPACE
QT_END_NAMESPACE
namespace QmlDesigner { namespace QmlDesigner {

View File

@@ -25,8 +25,8 @@
#include "selectionindicator.h" #include "selectionindicator.h"
#include "annotation.h"
#include <designeractionmanager.h> #include <designeractionmanager.h>
#include "annotationeditor/annotation.h"
#include <formeditorannotationicon.h> #include <formeditorannotationicon.h>
#include <QPen> #include <QPen>

View File

@@ -82,7 +82,8 @@ SOURCES += $$PWD/model/abstractview.cpp \
$$PWD/model/anchorline.cpp \ $$PWD/model/anchorline.cpp \
$$PWD/instances/puppetdialog.cpp \ $$PWD/instances/puppetdialog.cpp \
$$PWD/model/qmltimeline.cpp \ $$PWD/model/qmltimeline.cpp \
$$PWD/model/qmltimelinekeyframegroup.cpp $$PWD/model/qmltimelinekeyframegroup.cpp \
$$PWD/model/annotation.cpp
HEADERS += $$PWD/include/qmldesignercorelib_global.h \ HEADERS += $$PWD/include/qmldesignercorelib_global.h \
$$PWD/include/abstractview.h \ $$PWD/include/abstractview.h \
@@ -158,7 +159,8 @@ HEADERS += $$PWD/include/qmldesignercorelib_global.h \
$$PWD/include/anchorline.h \ $$PWD/include/anchorline.h \
$$PWD/instances/puppetdialog.h \ $$PWD/instances/puppetdialog.h \
$$PWD/include/qmltimeline.h \ $$PWD/include/qmltimeline.h \
$$PWD/include/qmltimelinekeyframegroup.h $$PWD/include/qmltimelinekeyframegroup.h \
$$PWD/include/annotation.h
FORMS += \ FORMS += \
$$PWD/instances/puppetdialog.ui $$PWD/instances/puppetdialog.ui

View File

@@ -41,7 +41,7 @@
#include "nodelistproperty.h" #include "nodelistproperty.h"
#include "nodeproperty.h" #include "nodeproperty.h"
#include <rewriterview.h> #include <rewriterview.h>
#include "annotationeditor/annotation.h" #include "annotation.h"
#include <utils/algorithm.h> #include <utils/algorithm.h>

View File

@@ -55,7 +55,8 @@ Project {
"components/navigator", "components/navigator",
"components/pluginmanager", "components/pluginmanager",
"components/stateseditor", "components/stateseditor",
"components/texteditor" "components/texteditor",
"components/timelineeditor",
]) ])
Properties { Properties {
@@ -245,6 +246,7 @@ Project {
"include/abstractproperty.h", "include/abstractproperty.h",
"include/abstractview.h", "include/abstractview.h",
"include/anchorline.h", "include/anchorline.h",
"include/annotation.h",
"include/basetexteditmodifier.h", "include/basetexteditmodifier.h",
"include/bindingproperty.h", "include/bindingproperty.h",
"include/componenttextmodifier.h", "include/componenttextmodifier.h",
@@ -321,6 +323,7 @@ Project {
"model/abstractproperty.cpp", "model/abstractproperty.cpp",
"model/abstractview.cpp", "model/abstractview.cpp",
"model/anchorline.cpp", "model/anchorline.cpp",
"model/annotation.cpp",
"model/basetexteditmodifier.cpp", "model/basetexteditmodifier.cpp",
"model/bindingproperty.cpp", "model/bindingproperty.cpp",
"model/componenttextmodifier.cpp", "model/componenttextmodifier.cpp",
@@ -638,8 +641,6 @@ Project {
name: "extension" name: "extension"
prefix: "components/" prefix: "components/"
files: [ files: [
"annotationeditor/annotation.cpp",
"annotationeditor/annotation.h",
"annotationeditor/annotationcommenttab.cpp", "annotationeditor/annotationcommenttab.cpp",
"annotationeditor/annotationcommenttab.h", "annotationeditor/annotationcommenttab.h",
"annotationeditor/annotationcommenttab.ui", "annotationeditor/annotationcommenttab.ui",
@@ -647,7 +648,7 @@ Project {
"annotationeditor/annotationeditor.h", "annotationeditor/annotationeditor.h",
"annotationeditor/annotationeditordialog.cpp", "annotationeditor/annotationeditordialog.cpp",
"annotationeditor/annotationeditordialog.h", "annotationeditor/annotationeditordialog.h",
"annotationeditor/annotationeditordialog.ui "annotationeditor/annotationeditordialog.ui",
"annotationeditor/annotationtool.cpp", "annotationeditor/annotationtool.cpp",
"annotationeditor/annotationtool.h", "annotationeditor/annotationtool.h",
"bindingeditor/bindingeditor.cpp", "bindingeditor/bindingeditor.cpp",

View File

@@ -292,8 +292,6 @@ bool FunctionHintProposalWidget::eventFilter(QObject *obj, QEvent *e)
if (d->m_model && d->m_model->size() > 1) if (d->m_model && d->m_model->size() > 1)
return false; return false;
} }
if (QTC_GUARD(d->m_assistant))
d->m_assistant->notifyChange();
} }
break; break;
case QEvent::WindowDeactivate: case QEvent::WindowDeactivate:

View File

@@ -665,8 +665,6 @@ bool GenericProposalWidget::eventFilter(QObject *o, QEvent *e)
} }
QApplication::sendEvent(const_cast<QWidget *>(d->m_underlyingWidget), e); QApplication::sendEvent(const_cast<QWidget *>(d->m_underlyingWidget), e);
if (isVisible())
d->m_assistant->notifyChange();
return true; return true;
} }

View File

@@ -741,7 +741,6 @@ public:
QTimer m_highlightBlocksTimer; QTimer m_highlightBlocksTimer;
CodeAssistant m_codeAssistant; CodeAssistant m_codeAssistant;
bool m_assistRelevantContentAdded = false;
QList<BaseHoverHandler *> m_hoverHandlers; // Not owned QList<BaseHoverHandler *> m_hoverHandlers; // Not owned
HoverHandlerRunner m_hoverHandlerRunner; HoverHandlerRunner m_hoverHandlerRunner;
@@ -1502,8 +1501,8 @@ void TextEditorWidgetPrivate::editorContentsChange(int position, int charsRemove
snippetCheckCursor(cursor); snippetCheckCursor(cursor);
} }
if (charsAdded != 0 && q->document()->characterAt(position + charsAdded - 1).isPrint()) if ((charsAdded != 0 && q->document()->characterAt(position + charsAdded - 1).isPrint()) || charsRemoved != 0)
m_assistRelevantContentAdded = true; m_codeAssistant.notifyChange();
int newBlockCount = doc->blockCount(); int newBlockCount = doc->blockCount();
if (!q->hasFocus() && newBlockCount != m_blockCount) { if (!q->hasFocus() && newBlockCount != m_blockCount) {

View File

@@ -31,40 +31,33 @@
namespace VcsBase { namespace VcsBase {
VcsOutputFormatter::VcsOutputFormatter() : VcsOutputFormatter::VcsOutputFormatter() :
m_urlRegexp("https?://\\S*"), m_regexp(
m_referenceRegexp("(v[0-9]+\\.[0-9]+\\.[0-9]+[\\-A-Za-z0-9]*)" // v0.1.2-beta3 "(https?://\\S*)" // https://codereview.org/c/1234
"|(v[0-9]+\\.[0-9]+\\.[0-9]+[\\-A-Za-z0-9]*)" // v0.1.2-beta3
"|([0-9a-f]{6,}(?:\\.\\.[0-9a-f]{6,})?)") // 789acf or 123abc..456cde "|([0-9a-f]{6,}(?:\\.\\.[0-9a-f]{6,})?)") // 789acf or 123abc..456cde
{ {
} }
void VcsOutputFormatter::appendMessage(const QString &text, Utils::OutputFormat format) void VcsOutputFormatter::appendMessage(const QString &text, Utils::OutputFormat format)
{ {
const QRegularExpressionMatch urlMatch = m_urlRegexp.match(text); QRegularExpressionMatchIterator it = m_regexp.globalMatch(text);
const QRegularExpressionMatch referenceMatch = m_referenceRegexp.match(text); int begin = 0;
while (it.hasNext()) {
auto append = [this](const QRegularExpressionMatch &match, const QRegularExpressionMatch match = it.next();
QString text, Utils::OutputFormat format) {
const QTextCharFormat normalFormat = charFormat(format); const QTextCharFormat normalFormat = charFormat(format);
OutputFormatter::appendMessage(text.left(match.capturedStart()), format); OutputFormatter::appendMessage(text.mid(begin, match.capturedStart() - begin), format);
QTextCursor tc = plainTextEdit()->textCursor(); QTextCursor tc = plainTextEdit()->textCursor();
QStringView url = match.capturedView(); QStringView url = match.capturedView();
int end = match.capturedEnd(); begin = match.capturedEnd();
while (url.rbegin()->isPunct()) { while (url.rbegin()->isPunct()) {
url.chop(1); url.chop(1);
--end; --begin;
} }
tc.movePosition(QTextCursor::End, QTextCursor::MoveAnchor); tc.movePosition(QTextCursor::End);
tc.insertText(url.toString(), linkFormat(normalFormat, url.toString())); tc.insertText(url.toString(), linkFormat(normalFormat, url.toString()));
tc.movePosition(QTextCursor::End, QTextCursor::MoveAnchor); tc.movePosition(QTextCursor::End);
OutputFormatter::appendMessage(text.mid(end), format); }
}; OutputFormatter::appendMessage(text.mid(begin), format);
if (urlMatch.hasMatch())
append(urlMatch, text, format);
else if (referenceMatch.hasMatch())
append(referenceMatch, text, format);
else
OutputFormatter::appendMessage(text, format);
} }
void VcsOutputFormatter::handleLink(const QString &href) void VcsOutputFormatter::handleLink(const QString &href)

View File

@@ -42,8 +42,7 @@ signals:
void referenceClicked(const QString &reference); void referenceClicked(const QString &reference);
private: private:
const QRegularExpression m_urlRegexp; const QRegularExpression m_regexp;
const QRegularExpression m_referenceRegexp;
}; };
} }

View File

@@ -210,7 +210,7 @@
:qdesigner_internal::WidgetBoxCategoryListView {container=':Widget Box_qdesigner_internal::WidgetBoxTreeWidget' occurrence='3' type='qdesigner_internal::WidgetBoxCategoryListView' unnamed='1' visible='1'} :qdesigner_internal::WidgetBoxCategoryListView {container=':Widget Box_qdesigner_internal::WidgetBoxTreeWidget' occurrence='3' type='qdesigner_internal::WidgetBoxCategoryListView' unnamed='1' visible='1'}
:qmakeCallEdit {container=':Qt Creator.scrollArea_QScrollArea' text?='<b>qmake:</b> qmake*' type='QLabel' unnamed='1' visible='1'} :qmakeCallEdit {container=':Qt Creator.scrollArea_QScrollArea' text?='<b>qmake:</b> qmake*' type='QLabel' unnamed='1' visible='1'}
:qt_tabwidget_stackedwidget.Core__Internal__GeneralSettings_QWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' name='Core__Internal__GeneralSettings' type='QWidget' visible='1'} :qt_tabwidget_stackedwidget.Core__Internal__GeneralSettings_QWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' name='Core__Internal__GeneralSettings' type='QWidget' visible='1'}
:qt_tabwidget_stackedwidget.QtSupport__Internal__QtVersionManager_QtSupport::Internal::QtOptionsPageWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' name='QtSupport__Internal__QtVersionManager' type='QtSupport::Internal::QtOptionsPageWidget' visible='1'} :qt_tabwidget_stackedwidget.QtSupport__Internal__QtVersionManager_QtSupport::Internal::QtOptionsPageWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' type='QScrollArea' unnamed='1' visible='1'}
:qt_tabwidget_stackedwidget_QScrollArea {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' type='QScrollArea' unnamed='1' visible='1'} :qt_tabwidget_stackedwidget_QScrollArea {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' type='QScrollArea' unnamed='1' visible='1'}
:qt_tabwidget_stackedwidget_QWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' type='QWidget' unnamed='1' visible='1'} :qt_tabwidget_stackedwidget_QWidget {container=':Options.qt_tabwidget_stackedwidget_QStackedWidget' type='QWidget' unnamed='1' visible='1'}
:qtdirList_QTreeView {container=':qt_tabwidget_stackedwidget_QScrollArea' name='qtdirList' type='QTreeView' visible='1'} :qtdirList_QTreeView {container=':qt_tabwidget_stackedwidget_QScrollArea' name='qtdirList' type='QTreeView' visible='1'}

View File

@@ -419,7 +419,7 @@ def __chooseTargets__(targets, availableTargets=None, additionalFunc=None):
if additionalFunc: if additionalFunc:
detailsWidget = waitForObject("{type='Utils::DetailsWidget' unnamed='1' " detailsWidget = waitForObject("{type='Utils::DetailsWidget' unnamed='1' "
"window=':Qt Creator_Core::Internal::MainWindow' " "window=':Qt Creator_Core::Internal::MainWindow' "
"toolTip?='<html><body><h3>%s</h3>*' visible='1'}" "summaryText='%s' visible='1'}"
% Targets.getStringForTarget(current)) % Targets.getStringForTarget(current))
detailsButton = getChildByClass(detailsWidget, "Utils::DetailsButton") detailsButton = getChildByClass(detailsWidget, "Utils::DetailsButton")
clickButton(detailsButton) clickButton(detailsButton)

View File

@@ -147,9 +147,9 @@ def invokeContextMenuOnProject(projectName, menuItem):
return projItem return projItem
def addAndActivateKit(kit): def addAndActivateKit(kit):
clickToActivate = "<h3>Click to activate:</h3>"
bAndRIndex = getQModelIndexStr("text='Build & Run'", ":Projects.ProjectNavigationTreeView") bAndRIndex = getQModelIndexStr("text='Build & Run'", ":Projects.ProjectNavigationTreeView")
kitString = Targets.getStringForTarget(kit) kitString = Targets.getStringForTarget(kit)
clickToActivate = "<html><body><h3>%s</h3><p><h3>Click to activate</h3>" % kitString
switchViewTo(ViewConstants.PROJECTS) switchViewTo(ViewConstants.PROJECTS)
try: try:
waitForObject(":Projects.ProjectNavigationTreeView") waitForObject(":Projects.ProjectNavigationTreeView")