diff --git a/src/plugins/android/androiddeploystep.cpp b/src/plugins/android/androiddeploystep.cpp index 9f9fc4d2cea0ceae2124755906b51ac8775cf1d2..0eba7056726feb76d3fb55b6faf0ba2fa67ecd6a 100644 --- a/src/plugins/android/androiddeploystep.cpp +++ b/src/plugins/android/androiddeploystep.cpp @@ -208,6 +208,11 @@ void AndroidDeployStep::setDeployQASIPackagePath(const QString &package) void AndroidDeployStep::setUseLocalQtLibs(bool useLocal) { m_useLocalQtLibs = useLocal; + + // ### Passes -1 for API level, which means it won't work with setups that require + // library selection based on API level. Use the old approach (command line argument) + // in these cases. + AndroidManager::setUseLocalLibs(target(), useLocal, -1); } bool AndroidDeployStep::runCommand(QProcess *buildProc, diff --git a/src/plugins/android/androidmanager.cpp b/src/plugins/android/androidmanager.cpp index 449a80575c502654fcf0da430d841c46eed0dfb4..edb77dcd91feef176b073b4382a43b9d85617442 100644 --- a/src/plugins/android/androidmanager.cpp +++ b/src/plugins/android/androidmanager.cpp @@ -348,6 +348,62 @@ QString AndroidManager::targetApplication(ProjectExplorer::Target *target) return QString(); } +bool AndroidManager::setUseLocalLibs(ProjectExplorer::Target *target, bool useLocalLibs, int deviceAPILevel) +{ + // For Qt 4, the "use local libs" options is handled by passing command line arguments to the + // app, so no need to alter the AndroidManifest.xml + QtSupport::BaseQtVersion *baseQtVersion = QtSupport::QtKitInformation::qtVersion(target->kit()); + if (baseQtVersion == 0 || baseQtVersion->qtVersion() < QtSupport::QtVersionNumber(5,0,0)) + return true; + + QDomDocument doc; + if (!openManifest(target, doc)) + return false; + + QDomElement metadataElem = doc.documentElement().firstChildElement(QLatin1String("application")).firstChildElement(QLatin1String("activity")).firstChildElement(QLatin1String("meta-data")); + + QString localLibs; + QString localJars; + QString staticInitClasses; + if (useLocalLibs) { + localLibs = loadLocalLibs(target, deviceAPILevel); + localJars = loadLocalJars(target, deviceAPILevel); + staticInitClasses = loadLocalJarsInitClasses(target, deviceAPILevel); + } + + bool changedManifest = false; + while (!metadataElem.isNull()) { + if (metadataElem.attribute(QLatin1String("android:name")) == QLatin1String("android.app.use_local_qt_libs")) { + if (metadataElem.attribute(QLatin1String("android:value")).toInt() != useLocalLibs) { + metadataElem.setAttribute(QLatin1String("android:value"), int(useLocalLibs)); + changedManifest = true; + } + } else if (metadataElem.attribute(QLatin1String("android:name")) == QLatin1String("android.app.load_local_libs")) { + if (metadataElem.attribute(QLatin1String("android:value")) != localLibs) { + metadataElem.setAttribute(QLatin1String("android:value"), localLibs); + changedManifest = true; + } + } else if (metadataElem.attribute(QLatin1String("android:name")) == QLatin1String("android.app.load_local_jars")) { + if (metadataElem.attribute(QLatin1String("android:value")) != localJars) { + metadataElem.setAttribute(QLatin1String("android:value"), localJars); + changedManifest = true; + } + } else if (metadataElem.attribute(QLatin1String("android:name")) == QLatin1String("android.app.static_init_classes")) { + if (metadataElem.attribute(QLatin1String("android:value")) != staticInitClasses) { + metadataElem.setAttribute(QLatin1String("android:value"), staticInitClasses); + changedManifest = true; + } + } + + metadataElem = metadataElem.nextSiblingElement(QLatin1String("meta-data")); + } + + if (changedManifest) + return saveManifest(target, doc); + else + return true; +} + bool AndroidManager::setTargetApplication(ProjectExplorer::Target *target, const QString &name) { QDomDocument doc; diff --git a/src/plugins/android/androidmanager.h b/src/plugins/android/androidmanager.h index a03e0980174476f7e49e9679463579a796de02cb..6316dfdafc9ae84211e08bdb596c37d0cbc8d4e3 100644 --- a/src/plugins/android/androidmanager.h +++ b/src/plugins/android/androidmanager.h @@ -84,6 +84,8 @@ public: static bool setTargetApplication(ProjectExplorer::Target *target, const QString &name); static QString targetApplicationPath(ProjectExplorer::Target *target); + static bool setUseLocalLibs(ProjectExplorer::Target *target, bool useLocalLibs, int deviceAPILevel); + static QString targetSDK(ProjectExplorer::Target *target); static bool setTargetSDK(ProjectExplorer::Target *target, const QString &sdk); diff --git a/src/plugins/android/androidpackagecreationwidget.cpp b/src/plugins/android/androidpackagecreationwidget.cpp index a22172b57c5d6666b4aee505ff03b90ad44829f2..21701e79db5efcbc271bc36291f21e013fcc5c40 100644 --- a/src/plugins/android/androidpackagecreationwidget.cpp +++ b/src/plugins/android/androidpackagecreationwidget.cpp @@ -32,6 +32,8 @@ #include "androidconfigurations.h" #include "androidcreatekeystorecertificate.h" #include "androidmanager.h" +#include "androiddeploystep.h" +#include "androidglobal.h" #include "ui_androidpackagecreationwidget.h" #include <projectexplorer/project.h> @@ -376,11 +378,25 @@ void AndroidPackageCreationWidget::setTarget(const QString &target) void AndroidPackageCreationWidget::setQtLibs(QModelIndex, QModelIndex) { AndroidManager::setQtLibs(m_step->target(), m_qtLibsModel->checkedItems()); + AndroidDeployStep * const deployStep = AndroidGlobal::buildStep<AndroidDeployStep>(m_step->target()->activeDeployConfiguration()); + if (deployStep->useLocalQtLibs()) { + // ### Passes -1 for API level, which means it won't work with setups that require + // library selection based on API level. Use the old approach (command line argument) + // in these cases. + AndroidManager::setUseLocalLibs(m_step->target(), true, -1); + } } void AndroidPackageCreationWidget::setPrebundledLibs(QModelIndex, QModelIndex) { AndroidManager::setPrebundledLibs(m_step->target(), m_prebundledLibs->checkedItems()); + AndroidDeployStep * const deployStep = AndroidGlobal::buildStep<AndroidDeployStep>(m_step->target()->activeDeployConfiguration()); + if (deployStep->useLocalQtLibs()) { + // ### Passes -1 for API level, which means it won't work with setups that require + // library selection based on API level. Use the old approach (command line argument) + // in these cases. + AndroidManager::setUseLocalLibs(m_step->target(), true, -1); + } } void AndroidPackageCreationWidget::prebundledLibSelected(const QModelIndex &index)