forked from qt-creator/qt-creator
Merge remote-tracking branch 'origin/7.0'
Conflicts: src/plugins/mcusupport/mcupackage.cpp src/plugins/mcusupport/mcusupportoptions.cpp src/plugins/mcusupport/mcusupportoptions.h src/plugins/mcusupport/mcusupportoptionspage.cpp src/plugins/mcusupport/mcusupportplugin.cpp src/plugins/mcusupport/mcusupportsdk.cpp Change-Id: Ib423e9f23877176f01b188104b0a179ed32c4770
This commit is contained in:
4
.github/workflows/build_cmake.yml
vendored
4
.github/workflows/build_cmake.yml
vendored
@@ -25,8 +25,8 @@ jobs:
|
||||
matrix:
|
||||
config:
|
||||
- {
|
||||
name: "Windows Latest MSVC", artifact: "Windows-MSVC",
|
||||
os: windows-latest,
|
||||
name: "Windows MSVC 2019", artifact: "Windows-MSVC",
|
||||
os: windows-2019,
|
||||
cc: "cl", cxx: "cl",
|
||||
environment_script: "C:/Program Files (x86)/Microsoft Visual Studio/2019/Enterprise/VC/Auxiliary/Build/vcvars64.bat",
|
||||
is_msvc: true
|
||||
|
@@ -66,6 +66,9 @@ if (Qt5_VERSION VERSION_LESS 6.0.0)
|
||||
if (MSVC AND MSVC_VERSION GREATER_EQUAL 1910)
|
||||
add_compile_options(/permissive- /Zc:__cplusplus)
|
||||
endif()
|
||||
if (CMAKE_CXX_COMPILER_ID STREQUAL GNU)
|
||||
add_compile_options(-Wno-missing-field-initializers)
|
||||
endif()
|
||||
else()
|
||||
# Common intermediate directory for QML modules which are defined via qt_add_qml_module()
|
||||
set(QT_QML_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/qml_modules")
|
||||
|
@@ -39,6 +39,17 @@
|
||||
|
||||
\image qtcreator-cmake-build-settings-initial.png "CMake build settings"
|
||||
|
||||
\uicontrol {Initial Configuration} lists the variables that are used to
|
||||
configure the CMake project for the first time. The default values that
|
||||
are inherited from the kit's CMake configuration are displayed in italic.
|
||||
The initial configuration list of variables is saved in the project's source
|
||||
directory as the \e CMakeLists.txt.user file.
|
||||
|
||||
\uicontrol {Current Configuration} lists the CMake variables in the
|
||||
\c cmake-file-api JSON export in the \c {.cmake/api/v1/reply} directory.
|
||||
The variables that are inherited from the initial configuration are
|
||||
displayed in italic. Mismatched values are displayed in red.
|
||||
|
||||
You can view and edit the actual values of the variables that are passed
|
||||
to CMake. Variable names are listed in the \uicontrol Key column and their
|
||||
current values in the \uicontrol Value column. For more information about
|
||||
|
@@ -1,6 +1,6 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2019 The Qt Company Ltd.
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of the Qt Creator documentation.
|
||||
@@ -291,7 +291,7 @@
|
||||
\row
|
||||
\li M106
|
||||
\li Warning
|
||||
\li \c Name is already a var
|
||||
\li \c Name already is a var
|
||||
\li
|
||||
|
||||
\row
|
||||
@@ -416,6 +416,12 @@
|
||||
\li A state cannot have the specified child item
|
||||
\li
|
||||
|
||||
\row
|
||||
\li M129
|
||||
\li Error
|
||||
\li Type cannot be instantiated recursively
|
||||
\li
|
||||
|
||||
\row
|
||||
\li M201
|
||||
\li Hint
|
||||
@@ -430,6 +436,7 @@
|
||||
\li Use only one statement per line
|
||||
\li
|
||||
|
||||
\if defined(qtdesignstudio)
|
||||
\row
|
||||
\li M203
|
||||
\li Warning
|
||||
@@ -463,60 +470,70 @@
|
||||
\row
|
||||
\li M208
|
||||
\li Error
|
||||
\li This id might be ambiguous and is not supported in \QDS.
|
||||
\li This id might be ambiguous and is not supported in \QDS
|
||||
\li
|
||||
|
||||
\row
|
||||
\li M209
|
||||
\li Error
|
||||
\li This type (type name) is not supported as a root element in
|
||||
\QDS.
|
||||
\QDS
|
||||
\li
|
||||
\endif
|
||||
|
||||
\row
|
||||
\li M220
|
||||
\li Error
|
||||
\li This type (type name) is not supported as a root element of a
|
||||
UI file (.ui.qml).
|
||||
\li
|
||||
UI file (.ui.qml)
|
||||
\li For more information about supported QML types, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M221
|
||||
\li Error
|
||||
\li This type (type name) is not supported in a UI file (.ui.qml).
|
||||
\li
|
||||
\li This type (type name) is not supported in a UI file (.ui.qml)
|
||||
\li For more information about supported QML types, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M222
|
||||
\li Error
|
||||
\li Functions are not supported in a UI file (.ui.qml).
|
||||
\li Functions are not supported in a UI file (.ui.qml)
|
||||
\li For a list of supported JavaScript functions, see
|
||||
\l{Supported Methods}.
|
||||
|
||||
\row
|
||||
\li M223
|
||||
\li Error
|
||||
\li Java Script blocks are not supported in a UI file (.ui.qml).
|
||||
\li
|
||||
\li JavaScript blocks are not supported in a UI file (.ui.qml)
|
||||
\li For more information about supported features, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M224
|
||||
\li Error
|
||||
\li Behavior type is not supported in a UI file (.ui.qml).
|
||||
\li
|
||||
\li Behavior type is not supported in a UI file (.ui.qml)
|
||||
\li For more information about supported QML types, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M225
|
||||
\li Error
|
||||
\li States are only supported in the root item in a UI file (.ui.qml).
|
||||
\li
|
||||
\li States are only supported in the root item in a UI file (.ui.qml)
|
||||
\li For more information about supported features, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M226
|
||||
\li Error
|
||||
\li Referencing the parent of the root item is not supported in a
|
||||
UI file (.ui.qml).
|
||||
\li
|
||||
UI file (.ui.qml)
|
||||
\li For more information about supported features, see \l{UI Files}.
|
||||
|
||||
\row
|
||||
\li M227
|
||||
\li Error
|
||||
\li Do not mix translation functions in a UI file (.ui.qml)
|
||||
\li Even though several different translation functions, such as
|
||||
\c qsTr and \c qsTrId are supported, you should pick one and
|
||||
use it consistently within a UI file. For more information,
|
||||
see \l{Qt QML Methods}.
|
||||
|
||||
\row
|
||||
\li M300
|
||||
@@ -674,11 +691,30 @@
|
||||
and most likely invalid
|
||||
\li
|
||||
|
||||
\row
|
||||
\li M325
|
||||
\li Warning
|
||||
\li Logical value does not depend on actual values
|
||||
\li
|
||||
|
||||
\row
|
||||
\li M326
|
||||
\li Error
|
||||
\li Components are only allowed to have a single child element
|
||||
\li For more information, see \l [QML] {Component}.
|
||||
|
||||
\row
|
||||
\li M327
|
||||
\li Warning
|
||||
\li Components require a child element
|
||||
\li For more information, see \l [QML] {Component}.
|
||||
|
||||
\row
|
||||
\li M400
|
||||
\li Warning
|
||||
\li Duplicate import
|
||||
\li
|
||||
\li An import statement has been added twice. For more information,
|
||||
see \l{Import Statements}.
|
||||
|
||||
\endtable
|
||||
|
||||
|
@@ -83,7 +83,7 @@
|
||||
|
||||
By default, logging categories and messages coming directly from Qt are
|
||||
disabled. To display them, select \inlineimage icons/qtlogo-16.png
|
||||
(\uicontrol {Toggle logging of Qt internal loggings.})
|
||||
(\uicontrol {Toggle Qt Internal Logging}).
|
||||
|
||||
New messages automatically scroll the message display to the bottom.
|
||||
To stop automatic scrolling, toggle \inlineimage icons/arrowdown.png
|
||||
|
@@ -1,6 +1,6 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2021 The Qt Company Ltd.
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of the Qt Creator documentation.
|
||||
@@ -52,6 +52,7 @@
|
||||
be edited in \QDS only.
|
||||
\endif
|
||||
|
||||
|
||||
The following features are not supported in .ui.qml files:
|
||||
|
||||
\list
|
||||
@@ -61,6 +62,7 @@
|
||||
\li States in other components than the root component
|
||||
\li Root components that are not derived from \l QQuickItem or
|
||||
\l [QML]{Item}
|
||||
\li Referencing the parent of the root component
|
||||
\endlist
|
||||
|
||||
The following components are not supported:
|
||||
@@ -69,11 +71,9 @@
|
||||
\li Behavior
|
||||
\li Binding
|
||||
\li Canvas
|
||||
\li Component
|
||||
\li Shader Effect
|
||||
\li Timer
|
||||
\li Transform
|
||||
\li Transition
|
||||
\endlist
|
||||
|
||||
\section1 Supported Methods
|
||||
@@ -165,6 +165,8 @@
|
||||
\li \l{Qt::}{qsTrNoOp()}
|
||||
\endlist
|
||||
|
||||
\note Do not mix translation methods in a UI file.
|
||||
|
||||
For more information about using the methods, see
|
||||
\l{https://doc.qt.io/qt/qml-qtqml-qt.html}{Qt QML Methods}.
|
||||
|
||||
|
@@ -74,12 +74,8 @@
|
||||
In \uicontrol Navigator, select \e particleSystem and in
|
||||
\uicontrol Properties, set \uicontrol Translation > \uicontrol Y to 193.
|
||||
\li Set the \e rain-drop-white-square.png as texture for the particles.
|
||||
From \uicontrol Library > \uicontrol Components, drag a \uicontrol Texture
|
||||
to \e spriteParticle.
|
||||
\li In \uicontrol Navigator, select \uicontrol texture1 and in \uicontrol
|
||||
Properties, set \uicontrol Source to \e rain-drop-white-square.png.
|
||||
\li In \uicontrol Navigator, select \uicontrol spriteParticle and in the
|
||||
\uicontrol Properties, set \uicontrol Sprite to texture.
|
||||
From \uicontrol Library > \uicontrol Assets, drag
|
||||
\e {rain-drop-white-square.png} to \e spriteParticle.
|
||||
\li Adjust the apperance and behavior of the sprite further. In \uicontrol
|
||||
Properties, set:
|
||||
\list
|
||||
|
Binary file not shown.
Before Width: | Height: | Size: 8.5 KiB After Width: | Height: | Size: 6.9 KiB |
Binary file not shown.
After Width: | Height: | Size: 17 KiB |
@@ -38,7 +38,7 @@
|
||||
\QDS is available in binary packages for the following operating systems:
|
||||
|
||||
\list
|
||||
\li \macOS 10.15
|
||||
\li \macOS 11.0
|
||||
\li Linux:
|
||||
\list
|
||||
\li CentOS 8.1
|
||||
|
@@ -92,22 +92,9 @@
|
||||
\li Drag-and-drop an instance of the \uicontrol {Particle System}
|
||||
component from \uicontrol Library to a scene component instance
|
||||
in \l Navigator.
|
||||
\li Drag-and-drop an instance of the \uicontrol Texture component
|
||||
from \uicontrol Library > \uicontrol Components >
|
||||
\uicontrol {Qt Quick 3D} to the sprite particle instance
|
||||
in \uicontrol Navigator.
|
||||
\li Drag-and-drop the sprite image from \uicontrol Library >
|
||||
\uicontrol Assets to the texture instance in \uicontrol Navigator.
|
||||
\li Select the sprite particle instance in \uicontrol Navigator to
|
||||
display its properties in \l Properties.
|
||||
\li In \uicontrol Sprite, select the texture instance.
|
||||
\li Select the emitter instance in \uicontrol Navigator to
|
||||
display its properties in \uicontrol Properties.
|
||||
\li In \uicontrol Particle, select the particle instance to emit.
|
||||
\li Select the vector 3D instance in \uicontrol Navigator to
|
||||
display its properties in \uicontrol Properties.
|
||||
\li In \uicontrol Direction, set the emitted particle velocity
|
||||
towards the target vector.
|
||||
\uicontrol Assets to the sprite particle instance
|
||||
in \uicontrol Navigator.
|
||||
\endlist
|
||||
|
||||
Add instances of other components according to your use case. The following
|
||||
@@ -122,6 +109,9 @@
|
||||
their property values, such as particle source images and their color, life
|
||||
span, and fading effects, to simulate fire.
|
||||
|
||||
You can download the completed project from
|
||||
\l {https://git.qt.io/public-demos/qtdesign-studio/-/tree/master/tutorial%20projects/FireParticles}{here}.
|
||||
|
||||
We will need the following \l{Assets}{assets}:
|
||||
|
||||
\list
|
||||
@@ -199,12 +189,16 @@
|
||||
\uicontrol {Particle end scale} to \e 5.00 for the flame
|
||||
particles and to \e 6.00 for the smoke particles.
|
||||
|
||||
We can now modify the appearance of the particles by setting their color in
|
||||
We can now modify the appearance of the particles by selecting the
|
||||
\e spriteParticle in \uicontrol Navigator and then setting their color in
|
||||
\uicontrol Properties > \uicontrol Particle. We select transparent yellow,
|
||||
orange, and transparent gray in \uicontrol Color and set values for
|
||||
\uicontrol {Color variation} to use slightly different colors for the
|
||||
individual particles.
|
||||
|
||||
We can also try changing the \uicontrol{Blend Mode} for the particle to get
|
||||
a more realistic fire effect.
|
||||
|
||||
\image studio-3d-particles-fire-properties-particle.png "Particle properties"
|
||||
|
||||
We set \uicontrol {Fade in effect} and \uicontrol {Fade out effect} values
|
||||
@@ -220,6 +214,11 @@
|
||||
|
||||
\image studio-3d-particles-fire-properties-sprite-particle.png "Sprite Particle properties"
|
||||
|
||||
In \uicontrol{Particle Rotation}, we also need to set \uicontrol Rotation
|
||||
and \uicontrol{Velocity Variation} for all emitters to 0.
|
||||
|
||||
\image studio-3d-particles-fire-properties-rotation.png "Emitter rotation properties"
|
||||
|
||||
Finally, we will specify the direction in which the particles move by
|
||||
modifying the property values of the \uicontrol {Vector Direction} component
|
||||
instances in \uicontrol Properties > \uicontrol {Particle Vector Direction}.
|
||||
|
@@ -50,7 +50,7 @@ Product {
|
||||
flags.push("-Wno-deprecated-copy", "-Wno-constant-logical-operand");
|
||||
}
|
||||
if (!qbs.toolchain.contains("clang")) {
|
||||
flags.push("-Wno-noexcept-type");
|
||||
flags.push("-Wno-missing-field-initializers", "-Wno-noexcept-type");
|
||||
if (Utilities.versionCompare(cpp.compilerVersion, "9") >= 0)
|
||||
flags.push("-Wno-deprecated-copy", "-Wno-init-list-lifetime");
|
||||
}
|
||||
|
65
qbs/modules/qtc_gtest_gmock/qtc_gtest_gmock.qbs
Normal file
65
qbs/modules/qtc_gtest_gmock/qtc_gtest_gmock.qbs
Normal file
@@ -0,0 +1,65 @@
|
||||
import qbs
|
||||
import qbs.File
|
||||
import qbs.FileInfo
|
||||
|
||||
Module {
|
||||
property bool preferExternalLibs: true
|
||||
|
||||
Depends { name: "pkgconfig"; condition: preferExternalLibs; required: false }
|
||||
Depends { name: "gtest"; condition: preferExternalLibs; required: false }
|
||||
Depends { name: "gmock"; condition: preferExternalLibs; required: false }
|
||||
Depends { name: "cpp" }
|
||||
|
||||
Probe {
|
||||
id: gtestProbe
|
||||
|
||||
property string repoDir
|
||||
property string gtestDir
|
||||
property string gmockDir
|
||||
property bool hasRepo
|
||||
|
||||
configure: {
|
||||
repoDir = FileInfo.cleanPath(path + "/../../../tests/unit/unittest/3rdparty/googletest");
|
||||
gtestDir = FileInfo.joinPaths(repoDir, "googletest");
|
||||
gmockDir = FileInfo.joinPaths(repoDir, "googlemock");
|
||||
hasRepo = File.exists(gtestDir);
|
||||
found = hasRepo;
|
||||
}
|
||||
}
|
||||
|
||||
property bool hasRepo: gtestProbe.hasRepo
|
||||
property bool externalLibsPresent: preferExternalLibs && gtest.present && gmock.present
|
||||
property bool useRepo: !externalLibsPresent && hasRepo
|
||||
property string gtestDir: gtestProbe.gtestDir
|
||||
property string gmockDir: gtestProbe.gmockDir
|
||||
|
||||
Group {
|
||||
name: "Files from repository"
|
||||
condition: qtc_gtest_gmock.useRepo
|
||||
cpp.includePaths: [
|
||||
qtc_gtest_gmock.gtestDir,
|
||||
qtc_gtest_gmock.gmockDir,
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gtestDir, "include"),
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gmockDir, "include"),
|
||||
]
|
||||
files: [
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gtestDir, "src", "gtest-all.cc"),
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gmockDir, "src", "gmock-all.cc"),
|
||||
]
|
||||
}
|
||||
|
||||
Properties {
|
||||
condition: qtc_gtest_gmock.useRepo
|
||||
cpp.includePaths: [
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gtestDir, "include"),
|
||||
FileInfo.joinPaths(qtc_gtest_gmock.gmockDir, "include"),
|
||||
]
|
||||
}
|
||||
|
||||
validate: {
|
||||
if (!qtc_gtest_gmock.externalLibsPresent && !gtestProbe.found) {
|
||||
console.warn("No GTest found.");
|
||||
throw new Error();
|
||||
}
|
||||
}
|
||||
}
|
@@ -19,6 +19,7 @@
|
||||
"qbs.FileInfo",
|
||||
"qbs.ModUtils",
|
||||
"qbs.PathTools",
|
||||
"qbs.PkgConfig",
|
||||
"qbs.Probes",
|
||||
"qbs.Process",
|
||||
"qbs.PropertyList",
|
||||
|
@@ -133,6 +133,7 @@ Module {
|
||||
Property { name: "multiplexedType"; type: "string"; isList: true }
|
||||
Property { name: "name"; type: "string" }
|
||||
Property { name: "profiles"; type: "string"; isList: true }
|
||||
Property { name: "qbsModuleProviders"; type: "string"; isList: true }
|
||||
Property { name: "qbsSearchPaths"; type: "string"; isList: true }
|
||||
Property { name: "targetName"; type: "string" }
|
||||
Property { name: "type"; type: "string"; isList: true }
|
||||
@@ -155,6 +156,7 @@ Module {
|
||||
Property { name: "minimumQbsVersion"; type: "string" }
|
||||
Property { name: "name"; type: "string" }
|
||||
Property { name: "profile"; type: "string" }
|
||||
Property { name: "qbsModuleProviders"; type: "string"; isList: true }
|
||||
Property { name: "qbsSearchPaths"; type: "string"; isList: true }
|
||||
Property { name: "references"; type: "string"; isList: true }
|
||||
Property { name: "sourceDirectory"; type: "string" }
|
||||
|
@@ -398,6 +398,8 @@ QImage Qt5NodeInstanceServer::grabItem(QQuickItem *item)
|
||||
|
||||
QQuickItemPrivate *pItem = QQuickItemPrivate::get(item);
|
||||
|
||||
const bool rootIs3dNode = rootNodeInstance().isSubclassOf("QQuick3DNode");
|
||||
|
||||
const bool renderEffects = qEnvironmentVariableIsSet("QMLPUPPET_RENDER_EFFECTS");
|
||||
|
||||
if (renderEffects) {
|
||||
@@ -426,6 +428,9 @@ QImage Qt5NodeInstanceServer::grabItem(QQuickItem *item)
|
||||
QRectF renderBoundingRect;
|
||||
if (instance.isValid())
|
||||
renderBoundingRect = instance.boundingRect();
|
||||
|
||||
else if (rootIs3dNode)
|
||||
renderBoundingRect = item->boundingRect();
|
||||
else
|
||||
renderBoundingRect = ServerNodeInstance::effectAdjustedBoundingRect(item);
|
||||
|
||||
|
@@ -133,6 +133,14 @@ void Qt5RenderNodeInstanceServer::collectItemChangesAndSendChangeCommands()
|
||||
nodeInstanceClient()->synchronizeWithClientProcess();
|
||||
}
|
||||
|
||||
if (rootNodeInstance().isSubclassOf("QQuick3DNode") && rootNodeInstance().contentItem()
|
||||
&& DesignerSupport::isDirty(rootNodeInstance().contentItem(),
|
||||
DesignerSupport::ContentUpdateMask)
|
||||
&& nodeInstanceClient()->bytesToWrite() < 10000) {
|
||||
Internal::QuickItemNodeInstance::updateDirtyNode(rootNodeInstance().contentItem());
|
||||
nodeInstanceClient()->pixmapChanged(createPixmapChangedCommand({rootNodeInstance()}));
|
||||
}
|
||||
|
||||
inFunction = false;
|
||||
}
|
||||
}
|
||||
|
@@ -55,6 +55,8 @@
|
||||
namespace QmlDesigner {
|
||||
namespace Internal {
|
||||
|
||||
const QRectF preview3dBoundingRect(0, 0, 640, 480);
|
||||
|
||||
Quick3DNodeInstance::Quick3DNodeInstance(QObject *node)
|
||||
: ObjectNodeInstance(node)
|
||||
{
|
||||
@@ -97,7 +99,7 @@ void Quick3DNodeInstance::initialize(const ObjectNodeInstance::Pointer &objectNo
|
||||
#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0)
|
||||
// In case this is the scene root, we need to create a dummy View3D for the scene
|
||||
// in preview puppets
|
||||
if (instanceId() == 0 && nodeInstanceServer()->isPreviewServer()) {
|
||||
if (instanceId() == 0 && (!nodeInstanceServer()->isInformationServer())) {
|
||||
auto helper = new QmlDesigner::Internal::GeneralHelper();
|
||||
engine()->rootContext()->setContextProperty("_generalHelper", helper);
|
||||
|
||||
@@ -111,8 +113,8 @@ void Quick3DNodeInstance::initialize(const ObjectNodeInstance::Pointer &objectNo
|
||||
|
||||
nodeInstanceServer()->setRootItem(m_dummyRootView);
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
#endif // QT_VERSION
|
||||
#endif // QUICK3D_MODULE
|
||||
ObjectNodeInstance::initialize(objectNodeInstance, flags);
|
||||
}
|
||||
|
||||
@@ -122,7 +124,7 @@ QImage Quick3DNodeInstance::renderImage() const
|
||||
if (!isRootNodeInstance() || !m_dummyRootView)
|
||||
return {};
|
||||
|
||||
QSize size(640, 480);
|
||||
QSize size = preview3dBoundingRect.size().toSize();
|
||||
nodeInstanceServer()->quickWindow()->resize(size);
|
||||
m_dummyRootView->setSize(size);
|
||||
|
||||
@@ -190,13 +192,37 @@ bool Quick3DNodeInstance::isRenderable() const
|
||||
return m_dummyRootView;
|
||||
}
|
||||
|
||||
bool Quick3DNodeInstance::hasContent() const
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
QRectF Quick3DNodeInstance::boundingRect() const
|
||||
{
|
||||
//The information server has no m_dummyRootView therefore we use the hardcoded value
|
||||
if (nodeInstanceServer()->isInformationServer())
|
||||
return preview3dBoundingRect;
|
||||
|
||||
if (m_dummyRootView)
|
||||
return m_dummyRootView->boundingRect();
|
||||
return ObjectNodeInstance::boundingRect();
|
||||
}
|
||||
|
||||
QRectF Quick3DNodeInstance::contentItemBoundingBox() const
|
||||
{
|
||||
return boundingRect();
|
||||
}
|
||||
|
||||
QPointF Quick3DNodeInstance::position() const
|
||||
{
|
||||
return QPointF(0, 0);
|
||||
}
|
||||
|
||||
QSizeF Quick3DNodeInstance::size() const
|
||||
{
|
||||
return boundingRect().size();
|
||||
}
|
||||
|
||||
QList<ServerNodeInstance> Quick3DNodeInstance::stateInstances() const
|
||||
{
|
||||
QList<ServerNodeInstance> instanceList;
|
||||
@@ -212,6 +238,11 @@ QList<ServerNodeInstance> Quick3DNodeInstance::stateInstances() const
|
||||
return instanceList;
|
||||
}
|
||||
|
||||
QQuickItem *Quick3DNodeInstance::contentItem() const
|
||||
{
|
||||
return m_dummyRootView;
|
||||
}
|
||||
|
||||
Qt5NodeInstanceServer *Quick3DNodeInstance::qt5NodeInstanceServer() const
|
||||
{
|
||||
return qobject_cast<Qt5NodeInstanceServer *>(nodeInstanceServer());
|
||||
|
@@ -51,10 +51,16 @@ public:
|
||||
QImage renderPreviewImage(const QSize &previewImageSize) const override;
|
||||
|
||||
bool isRenderable() const override;
|
||||
bool hasContent() const override;
|
||||
QRectF boundingRect() const override;
|
||||
QRectF contentItemBoundingBox() const override;
|
||||
QPointF position() const override;
|
||||
QSizeF size() const override;
|
||||
|
||||
QList<ServerNodeInstance> stateInstances() const override;
|
||||
|
||||
QQuickItem *contentItem() const override;
|
||||
|
||||
protected:
|
||||
explicit Quick3DNodeInstance(QObject *node);
|
||||
|
||||
|
@@ -162,6 +162,11 @@ bool ServerNodeInstance::isComponentWrap() const
|
||||
return m_nodeInstance->isComponentWrap();
|
||||
}
|
||||
|
||||
QQuickItem *ServerNodeInstance::contentItem() const
|
||||
{
|
||||
return m_nodeInstance->contentItem();
|
||||
}
|
||||
|
||||
void ServerNodeInstance::updateDirtyNodeRecursive()
|
||||
{
|
||||
m_nodeInstance->updateAllDirtyNodesRecursive();
|
||||
|
@@ -188,6 +188,8 @@ public:
|
||||
|
||||
bool isComponentWrap() const;
|
||||
|
||||
QQuickItem *contentItem() const;
|
||||
|
||||
private: // functions
|
||||
ServerNodeInstance(const QSharedPointer<Internal::ObjectNodeInstance> &abstractInstance);
|
||||
|
||||
|
@@ -98,6 +98,8 @@ Item {
|
||||
StudioControls.Menu {
|
||||
id: contextMenu
|
||||
|
||||
closePolicy: Popup.CloseOnPressOutside | Popup.CloseOnEscape
|
||||
|
||||
StudioControls.MenuItem {
|
||||
text: qsTr("Expand All")
|
||||
enabled: allExpandedState !== 1
|
||||
@@ -167,7 +169,7 @@ Item {
|
||||
Dialog {
|
||||
id: renameFolderDialog
|
||||
|
||||
title: qsTr("Rename folder")
|
||||
title: qsTr("Rename Folder")
|
||||
anchors.centerIn: parent
|
||||
closePolicy: Popup.CloseOnEscape
|
||||
implicitWidth: 280
|
||||
@@ -192,15 +194,15 @@ Item {
|
||||
}
|
||||
|
||||
Text {
|
||||
text: qsTr("Folder Name cannot be empty.")
|
||||
text: qsTr("Folder name cannot be empty.")
|
||||
color: "#ff0000"
|
||||
visible: folderRename.text === "" && !renameFolderDialog.renameError
|
||||
}
|
||||
|
||||
Text {
|
||||
text: qsTr("Could not rename directory. Make sure no folder with the same name exists.")
|
||||
text: qsTr("Could not rename folder. Make sure no folder with the same name exists.")
|
||||
wrapMode: Text.WordWrap
|
||||
width: renameFolderDialog.width
|
||||
width: renameFolderDialog.width - 12
|
||||
color: "#ff0000"
|
||||
visible: renameFolderDialog.renameError
|
||||
}
|
||||
@@ -259,7 +261,7 @@ Item {
|
||||
Dialog {
|
||||
id: newFolderDialog
|
||||
|
||||
title: qsTr("Create new folder")
|
||||
title: qsTr("Create New Folder")
|
||||
anchors.centerIn: parent
|
||||
closePolicy: Popup.CloseOnEscape
|
||||
modal: true
|
||||
@@ -269,7 +271,7 @@ Item {
|
||||
|
||||
Row {
|
||||
Text {
|
||||
text: qsTr("Folder Name: ")
|
||||
text: qsTr("Folder name: ")
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
color: StudioTheme.Values.themeTextColor
|
||||
}
|
||||
@@ -287,7 +289,7 @@ Item {
|
||||
}
|
||||
|
||||
Text {
|
||||
text: qsTr("Folder Name cannot be empty.")
|
||||
text: qsTr("Folder name cannot be empty.")
|
||||
color: "#ff0000"
|
||||
anchors.right: parent.right
|
||||
visible: folderName.text === ""
|
||||
@@ -329,7 +331,7 @@ Item {
|
||||
Dialog {
|
||||
id: confirmDeleteFolderDialog
|
||||
|
||||
title: qsTr("Folder not empty")
|
||||
title: qsTr("Folder Not Empty")
|
||||
anchors.centerIn: parent
|
||||
closePolicy: Popup.CloseOnEscape
|
||||
implicitWidth: 300
|
||||
@@ -342,7 +344,7 @@ Item {
|
||||
Text {
|
||||
id: folderNotEmpty
|
||||
|
||||
text: qsTr("Folder '%1' is not empty. Are you sure you want to delete it?")
|
||||
text: qsTr("Folder \"%1\" is not empty. Delete it anyway?")
|
||||
.arg(contextDir ? contextDir.dirName : "")
|
||||
color: StudioTheme.Values.themeTextColor
|
||||
wrapMode: Text.WordWrap
|
||||
|
@@ -59,8 +59,8 @@ Section {
|
||||
|
||||
PropertyLabel {
|
||||
visible: root.showAudioOutput
|
||||
text: qsTr("Audio Output")
|
||||
tooltip: qsTr("Holds the target audio output.")
|
||||
text: qsTr("Audio output")
|
||||
tooltip: qsTr("Target audio output.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
@@ -80,8 +80,8 @@ Section {
|
||||
|
||||
PropertyLabel {
|
||||
visible: root.showVideoOutput
|
||||
text: qsTr("Video Output")
|
||||
tooltip: qsTr("Holds the target video output.")
|
||||
text: qsTr("Video output")
|
||||
tooltip: qsTr("Target video output.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
|
@@ -41,7 +41,7 @@ import QtQuickDesignerTheme 1.0
|
||||
import StudioTheme 1.0 as StudioTheme
|
||||
|
||||
Section {
|
||||
caption: qsTr("Button content")
|
||||
caption: qsTr("Button Content")
|
||||
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
@@ -49,7 +49,7 @@ Section {
|
||||
SectionLayout {
|
||||
PropertyLabel {
|
||||
text: qsTr("Text")
|
||||
tooltip: qsTr("The text displayed on the button.")
|
||||
tooltip: qsTr("Text displayed on the button.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
|
@@ -41,7 +41,7 @@ Column {
|
||||
SectionLayout {
|
||||
PropertyLabel {
|
||||
text: qsTr("Active")
|
||||
tooltip: qsTr("This property is true if the Loader is currently active.")
|
||||
tooltip: qsTr("Whether the loader is currently active.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
@@ -57,7 +57,7 @@ Column {
|
||||
|
||||
PropertyLabel {
|
||||
text: qsTr("Source")
|
||||
tooltip: qsTr("This property holds the URL of the QML component to instantiate.")
|
||||
tooltip: qsTr("URL of the component to instantiate.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
@@ -70,8 +70,8 @@ Column {
|
||||
}
|
||||
|
||||
PropertyLabel {
|
||||
text: qsTr("Source Component")
|
||||
tooltip: qsTr("This property holds the component to instantiate.")
|
||||
text: qsTr("Source component")
|
||||
tooltip: qsTr("Component to instantiate.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
@@ -88,7 +88,7 @@ Column {
|
||||
|
||||
PropertyLabel {
|
||||
text: qsTr("Asynchronous")
|
||||
tooltip: qsTr("This property holds whether the component will be instantiated asynchronously.")
|
||||
tooltip: qsTr("Whether the component will be instantiated asynchronously.")
|
||||
}
|
||||
|
||||
SecondColumnLayout {
|
||||
|
@@ -386,6 +386,7 @@ SecondColumnLayout {
|
||||
|
||||
property ListModel items: ListModel {}
|
||||
|
||||
enabled: isBaseState
|
||||
implicitWidth: StudioTheme.Values.colorEditorPopupCmoboBoxWidth
|
||||
width: implicitWidth
|
||||
actionIndicatorVisible: false
|
||||
@@ -442,6 +443,13 @@ SecondColumnLayout {
|
||||
}
|
||||
colorEditor.updateThumbnail()
|
||||
}
|
||||
|
||||
ToolTipArea {
|
||||
enabled: !isBaseState
|
||||
anchors.fill: parent
|
||||
tooltip: qsTr("Fill type can only be changed in base state.")
|
||||
z: 10
|
||||
}
|
||||
}
|
||||
|
||||
ExpandingSpacer {}
|
||||
|
@@ -218,7 +218,7 @@ Section {
|
||||
AbstractButton {
|
||||
id: editAnnotationButton
|
||||
buttonIcon: StudioTheme.Constants.edit
|
||||
tooltip: qsTr("Edit annotation")
|
||||
tooltip: qsTr("Edit Annotation")
|
||||
onClicked: annotationEditor.showWidget()
|
||||
onHoveredChanged: annotationEditor.checkAux()
|
||||
}
|
||||
@@ -226,7 +226,7 @@ Section {
|
||||
AbstractButton {
|
||||
id: removeAnnotationButton
|
||||
buttonIcon: StudioTheme.Constants.closeCross
|
||||
tooltip: qsTr("Remove annotation")
|
||||
tooltip: qsTr("Remove Annotation")
|
||||
onClicked: annotationEditor.removeFullAnnotation()
|
||||
onHoveredChanged: annotationEditor.checkAux()
|
||||
}
|
||||
|
@@ -35,13 +35,14 @@ import QtQuick.VirtualKeyboard %{QtQuickVersion}
|
||||
@endif
|
||||
|
||||
Window {
|
||||
width: Constants.width
|
||||
height: Constants.height
|
||||
width: mainScreen.width
|
||||
height: mainScreen.height
|
||||
|
||||
visible: true
|
||||
title: "%{ProjectName}"
|
||||
|
||||
%{UIClassName} {
|
||||
id: mainScreen
|
||||
}
|
||||
|
||||
@if %{UseVirtualKeyboard}
|
||||
|
@@ -62,6 +62,10 @@ Project {
|
||||
Environment {
|
||||
QT_QUICK_CONTROLS_CONF: "qtquickcontrols2.conf"
|
||||
QT_AUTO_SCREEN_SCALE_FACTOR: "1"
|
||||
@if %{IsQt6Project}
|
||||
@else
|
||||
QMLSCENE_CORE_PROFILE: "true" // Required for macOS, but can create issues on embedded Linux
|
||||
@endif
|
||||
@if %{UseVirtualKeyboard}
|
||||
QT_IM_MODULE: "qtvirtualkeyboard"
|
||||
QT_VIRTUALKEYBOARD_DESKTOP_DISABLE: 1
|
||||
|
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="OpenDocuments"><widget name="FileSystem" closed="true"/><widget name="OpenDocuments" closed="true"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>346 0 365</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="true"/></area><sizes>712 0</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="true"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="true"/></area><sizes>0 0</sizes></splitter><sizes>914 0</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="1" current=""><widget name="StatesEditor" closed="true"/></area><area tabs="1" current=""><widget name="TransitionEditor" closed="true"/></area><sizes>0 0</sizes></splitter><sizes>712 0</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="true"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="true"/></area><sizes>712 0 0</sizes></splitter><sizes>310 914 406</sizes></splitter><area tabs="2" current="Timelines"><widget name="Timelines" closed="false"/><widget name="CurveEditorId" closed="false"/></area><sizes>712 255</sizes></splitter></container></QtAdvancedDockingSystem>
|
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="FileSystem"><widget name="FileSystem" closed="true"/><widget name="OpenDocuments" closed="true"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>541 0 426</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="false"/></area><sizes>353 353</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="true"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="true"/></area><sizes>0 0</sizes></splitter><sizes>919 0</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="3" current="Timelines"><widget name="Timelines" closed="false"/><widget name="CurveEditorId" closed="false"/><widget name="StatesEditor" closed="true"/></area><area tabs="1" current=""><widget name="TransitionEditor" closed="true"/></area><sizes>919 0</sizes></splitter><sizes>707 260</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="true"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="true"/></area><sizes>968 0 0</sizes></splitter><sizes>312 919 408</sizes></splitter></container></QtAdvancedDockingSystem>
|
1
share/qtcreator/qmldesigner/workspacePresets/Basic.wrk
Normal file
1
share/qtcreator/qmldesigner/workspacePresets/Basic.wrk
Normal file
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="FileSystem"><widget name="FileSystem" closed="true"/><widget name="OpenDocuments" closed="true"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>481 0 486</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="true"/></area><sizes>968 0</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="true"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="true"/></area><sizes>968 0</sizes></splitter><sizes>919 0</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="2" current="Timelines"><widget name="StatesEditor" closed="true"/><widget name="Timelines" closed="true"/></area><area tabs="2" current="TransitionEditor"><widget name="CurveEditorId" closed="true"/><widget name="TransitionEditor" closed="true"/></area><sizes>0 919</sizes></splitter><sizes>968 0</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="true"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="true"/></area><sizes>968 0 0</sizes></splitter><sizes>312 919 408</sizes></splitter></container></QtAdvancedDockingSystem>
|
1
share/qtcreator/qmldesigner/workspacePresets/Code.wrk
Normal file
1
share/qtcreator/qmldesigner/workspacePresets/Code.wrk
Normal file
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="OpenDocuments"><widget name="FileSystem" closed="true"/><widget name="OpenDocuments" closed="true"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>541 0 426</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="true"/></area><sizes>707 0</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="false"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="false"/></area><sizes>488 218</sizes></splitter><sizes>601 448</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="2" current="StatesEditor"><widget name="StatesEditor" closed="false"/><widget name="Timelines" closed="true"/></area><area tabs="2" current="TransitionEditor"><widget name="CurveEditorId" closed="true"/><widget name="TransitionEditor" closed="true"/></area><sizes>1050 0</sizes></splitter><sizes>707 260</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="true"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="false"/></area><sizes>541 0 426</sizes></splitter><sizes>274 1050 315</sizes></splitter></container></QtAdvancedDockingSystem>
|
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="OpenDocuments"><widget name="FileSystem" closed="true"/><widget name="OpenDocuments" closed="true"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>487 0 480</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="true"/></area><sizes>707 0</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="true"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="true"/></area><sizes>707 0</sizes></splitter><sizes>914 0</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="2" current="StatesEditor"><widget name="StatesEditor" closed="false"/><widget name="Timelines" closed="true"/></area><area tabs="2" current="TransitionEditor"><widget name="CurveEditorId" closed="true"/><widget name="TransitionEditor" closed="true"/></area><sizes>914 0</sizes></splitter><sizes>707 260</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="true"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="false"/></area><sizes>707 0 260</sizes></splitter><sizes>310 914 406</sizes></splitter></container></QtAdvancedDockingSystem>
|
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><QtAdvancedDockingSystem version="1" userVersion="0" containers="1"><container floating="false"><splitter orientation="Horizontal" count="3"><splitter orientation="Vertical" count="3"><area tabs="2" current="Navigator"><widget name="Navigator" closed="false"/><widget name="Projects" closed="false"/></area><area tabs="2" current="FileSystem"><widget name="FileSystem" closed="false"/><widget name="OpenDocuments" closed="false"/></area><area tabs="2" current="Components"><widget name="Components" closed="false"/><widget name="Assets" closed="false"/></area><sizes>343 353 270</sizes></splitter><splitter orientation="Vertical" count="2"><splitter orientation="Horizontal" count="2"><splitter orientation="Vertical" count="2"><area tabs="1" current="FormEditor"><widget name="FormEditor" closed="false"/></area><area tabs="1" current="Editor3D"><widget name="Editor3D" closed="false"/></area><sizes>353 353</sizes></splitter><splitter orientation="Vertical" count="2"><area tabs="1" current="TextEditor"><widget name="TextEditor" closed="false"/></area><area tabs="1" current="OutputPane"><widget name="OutputPane" closed="false"/></area><sizes>353 353</sizes></splitter><sizes>448 465</sizes></splitter><splitter orientation="Horizontal" count="2"><area tabs="2" current="StatesEditor"><widget name="StatesEditor" closed="false"/><widget name="Timelines" closed="false"/></area><area tabs="2" current="CurveEditorId"><widget name="CurveEditorId" closed="false"/><widget name="TransitionEditor" closed="false"/></area><sizes>457 456</sizes></splitter><sizes>707 260</sizes></splitter><splitter orientation="Vertical" count="3"><area tabs="1" current="Properties"><widget name="Properties" closed="false"/></area><area tabs="1" current="TranslationsView"><widget name="TranslationsView" closed="false"/></area><area tabs="1" current="ConnectionView"><widget name="ConnectionView" closed="false"/></area><sizes>343 353 270</sizes></splitter><sizes>310 914 406</sizes></splitter></container></QtAdvancedDockingSystem>
|
@@ -1,4 +0,0 @@
|
||||
import QtQuick 2.4
|
||||
|
||||
%{FormClass} {
|
||||
}
|
@@ -1,6 +0,0 @@
|
||||
import QtQuick 2.4
|
||||
|
||||
Item {
|
||||
width: 400
|
||||
height: 400
|
||||
}
|
@@ -1,91 +0,0 @@
|
||||
{
|
||||
"version": 1,
|
||||
"supportedProjectTypes": [ ],
|
||||
"id": "R.QtQuickUi",
|
||||
"category": "R.Qt",
|
||||
"trDescription": "Creates a Qt Quick Designer UI form along with a matching QML file for implementation purposes. You can add the form and file to an existing Qt Quick Project.",
|
||||
"trDisplayName": "QtQuick UI File",
|
||||
"trDisplayCategory": "Qt",
|
||||
"iconText": "ui.qml",
|
||||
"featuresRequired": [ "QtSupport.Wizards.FeatureQtQuick.UiFiles" ],
|
||||
"enabled": "%{JS: value('Plugins').indexOf('QmlJSEditor') >= 0}",
|
||||
|
||||
"options" : [
|
||||
{ "key": "QmlFile", "value": "%{Class}.%{JS: Util.preferredSuffix('text/x-qml')}" },
|
||||
{ "key": "UiFile", "value": "%{FormClass}.%{JS: Util.preferredSuffix('application/x-qt.ui+qml')}" }
|
||||
],
|
||||
|
||||
"pages" :
|
||||
[
|
||||
{
|
||||
"trDisplayName": "Define Class",
|
||||
"trShortTitle": "Details",
|
||||
"typeId": "Fields",
|
||||
"data" :
|
||||
[
|
||||
{
|
||||
"name": "Class",
|
||||
"trDisplayName": "Component name:",
|
||||
"mandatory": true,
|
||||
"type": "LineEdit",
|
||||
"data": {
|
||||
"validator": "(?:[A-Z_][a-zA-Z_0-9]*|)",
|
||||
"fixup": "%{JS: '%{INPUT}'.charAt(0).toUpperCase() + '%{INPUT}'.slice(1) }"
|
||||
}
|
||||
},
|
||||
|
||||
{
|
||||
"name": "Sp1",
|
||||
"type": "Spacer",
|
||||
"data": { "factor": 2 }
|
||||
},
|
||||
{
|
||||
"name": "FormClass",
|
||||
"trDisplayName": "Component form name:",
|
||||
"mandatory": true,
|
||||
"type": "LineEdit",
|
||||
"data": {
|
||||
"validator": "(?:[A-Z_][a-zA-Z_0-9]*|)",
|
||||
"fixup": "%{JS: '%{INPUT}'.charAt(0).toUpperCase() + '%{INPUT}'.slice(1) }",
|
||||
"trText": "%{Class}Form"
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "TargetPath",
|
||||
"type": "PathChooser",
|
||||
"trDisplayName": "Path:",
|
||||
"mandatory": true,
|
||||
"data":
|
||||
{
|
||||
"kind": "directory",
|
||||
"basePath": "%{InitialPath}",
|
||||
"path": "%{InitialPath}"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"trDisplayName": "Project Management",
|
||||
"trShortTitle": "Summary",
|
||||
"typeId": "Summary"
|
||||
}
|
||||
],
|
||||
"generators" :
|
||||
[
|
||||
{
|
||||
"typeId": "File",
|
||||
"data": [
|
||||
{
|
||||
"source": "file.qml.tpl",
|
||||
"target": "%{TargetPath}/%{QmlFile}",
|
||||
"openInEditor": true
|
||||
},
|
||||
{
|
||||
"source": "fileForm.ui.qml.tpl",
|
||||
"target": "%{TargetPath}/%{UiFile}",
|
||||
"openInEditor": true
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
@@ -1758,12 +1758,12 @@ Cancelling pending operations...
|
||||
<context>
|
||||
<name>Android::Internal::AndroidServiceWidget::AndroidServiceModel</name>
|
||||
<message>
|
||||
<source>The name of the class implementing the service</source>
|
||||
<translation>Имя класса, реализующего сервис</translation>
|
||||
<source>The name of the class implementing the service.</source>
|
||||
<translation>Имя класса, реализующего сервис.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Checked if the service is run in an external process</source>
|
||||
<translation>Отмечено, если сервис работает во внешнем процессе</translation>
|
||||
<source>Checked if the service is run in an external process.</source>
|
||||
<translation>Отмечено, если сервис работает во внешнем процессе.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The name of the external process.
|
||||
@@ -1772,52 +1772,52 @@ Prefix with : if the process is private, use a lowercase name if the process is
|
||||
Если имя начинается с двоеточия, то процесс приватный, если написано в нижнем регистре, то процесс глобальный.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Checked if the service is in a separate dynamic library</source>
|
||||
<translation>Отмечено, если сервис в отдельной динамической библиотеке</translation>
|
||||
<source>Checked if the service is in a separate dynamic library.</source>
|
||||
<translation>Отмечено, если сервис в отдельной динамической библиотеке.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The name of the separate dynamic library</source>
|
||||
<translation>Имя отдельной динамической библиотеки</translation>
|
||||
<source>The name of the separate dynamic library.</source>
|
||||
<translation>Имя отдельной динамической библиотеки.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The arguments for telling the app to run the service instead of the main activity</source>
|
||||
<translation>Параметры запуска сервиса вместо основной функциональности приложения</translation>
|
||||
<source>The arguments for telling the app to run the service instead of the main activity.</source>
|
||||
<translation>Параметры запуска сервиса вместо основной функциональности приложения.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Service class name</source>
|
||||
<translation>Имя класса сервиса</translation>
|
||||
<source>Service class name.</source>
|
||||
<translation>Имя класса сервиса.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Run in external process</source>
|
||||
<translation>Работа во внешнем процессе</translation>
|
||||
<source>Run in external process.</source>
|
||||
<translation>Работа во внешнем процессе.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Process name</source>
|
||||
<translation>Имя процесса</translation>
|
||||
<source>Process name.</source>
|
||||
<translation>Имя процесса.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Run in external library</source>
|
||||
<translation>Работа во внешней библиотеке</translation>
|
||||
<source>Run in external library.</source>
|
||||
<translation>Работа во внешней библиотеке.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Library name</source>
|
||||
<translation>Имя библиотеки</translation>
|
||||
<source>Library name.</source>
|
||||
<translation>Имя библиотеки.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Service arguments</source>
|
||||
<translation>Параметры сервиса</translation>
|
||||
<source>Service arguments.</source>
|
||||
<translation>Параметры сервиса.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The class name must be set</source>
|
||||
<translation>Должно быть задано имя класса</translation>
|
||||
<source>The class name must be set.</source>
|
||||
<translation>Должно быть задано имя класса.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The process name must be set for a service run in an external process</source>
|
||||
<translation>Имя процесса должно быть задано для сервиса, работающего во внешнем процессе</translation>
|
||||
<source>The process name must be set for a service run in an external process.</source>
|
||||
<translation>Имя процесса должно быть задано для сервиса, работающего во внешнем процессе.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The library name must be set for a service run in an external library</source>
|
||||
<translation>Имя библиотеки должно быть задано для сервиса, работающего во внешней библиотеке</translation>
|
||||
<source>The library name must be set for a service run in an external library.</source>
|
||||
<translation>Имя библиотеки должно быть задано для сервиса, работающего во внешней библиотеке.</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>The service arguments must be set for a service not run in an external library</source>
|
||||
|
@@ -26,6 +26,7 @@ add_qtc_executable(qtcreator
|
||||
|
||||
extend_qtc_executable(qtcreator
|
||||
CONDITION APPLE
|
||||
DEPENDS ${FWFoundation}
|
||||
SOURCES
|
||||
main_mac.mm
|
||||
)
|
||||
|
@@ -43,6 +43,8 @@ QtcProduct {
|
||||
project.sharedSourcesDir + "/qtlockedfile",
|
||||
]
|
||||
|
||||
cpp.frameworks: base.concat(qbs.targetOS.contains("macos") ? ["Foundation"] : [])
|
||||
|
||||
Depends { name: "app_version_header" }
|
||||
Depends { name: "Qt"; submodules: ["widgets", "network"] }
|
||||
Depends { name: "Utils" }
|
||||
@@ -97,4 +99,12 @@ QtcProduct {
|
||||
"../shared/qtlockedfile/qtlockedfile_win.cpp"
|
||||
]
|
||||
}
|
||||
|
||||
Group {
|
||||
name: "main_macos"
|
||||
condition: qbs.targetOS.contains("macos")
|
||||
files: [
|
||||
"main_mac.mm"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
@@ -60,7 +60,7 @@ QT_END_NAMESPACE
|
||||
namespace ADS {
|
||||
|
||||
namespace Constants {
|
||||
const char DEFAULT_WORKSPACE[] = "Essentials"; // This needs to align with a name of the shipped presets
|
||||
const char DEFAULT_WORKSPACE[] = "Basic"; // This needs to align with a name of the shipped presets
|
||||
const char STARTUP_WORKSPACE_SETTINGS_KEY[] = "QML/Designer/StartupWorkspace";
|
||||
const char AUTO_RESTORE_WORKSPACE_SETTINGS_KEY[] = "QML/Designer/AutoRestoreLastWorkspace";
|
||||
} // namespace Constants
|
||||
|
@@ -60,7 +60,7 @@ struct ConvertArgValueToString {
|
||||
|
||||
std::string Arg::value() const
|
||||
{
|
||||
return std::visit(ConvertArgValueToString(), m_value);
|
||||
return Utils::visit(ConvertArgValueToString(), m_value);
|
||||
}
|
||||
|
||||
|
||||
|
@@ -33,9 +33,9 @@
|
||||
# define NANOTRACESHARED_EXPORT Q_DECL_IMPORT
|
||||
#endif
|
||||
|
||||
#include <utils/variant.h> // revert when macos minimum target is >= 10.14
|
||||
|
||||
#include <string>
|
||||
#include <variant>
|
||||
#include <vector>
|
||||
|
||||
|
||||
@@ -80,7 +80,7 @@ using TimePoint = std::chrono::time_point< Clock >;
|
||||
class NANOTRACESHARED_EXPORT Arg
|
||||
{
|
||||
public:
|
||||
using SupportedType = std::variant<int, int64_t, double, std::string>;
|
||||
using SupportedType = Utils::variant<int, int64_t, double, std::string>;
|
||||
|
||||
Arg(const std::string &name, const SupportedType &val);
|
||||
std::string name() const;
|
||||
|
Submodule src/libs/qlitehtml updated: 1d73f76fac...62a1650652
@@ -185,7 +185,7 @@ ObjectValue *Bind::bindObject(UiQualifiedId *qualifiedTypeNameId, UiObjectInitia
|
||||
|
||||
void Bind::throwRecursionDepthError()
|
||||
{
|
||||
_diagnosticMessages->append(DiagnosticMessage(Severity::Error, SourceLocation(), tr("Hit maximal recursion depth in AST visit")));
|
||||
_diagnosticMessages->append(DiagnosticMessage(Severity::Error, SourceLocation(), tr("Hit maximal recursion depth in AST visit.")));
|
||||
}
|
||||
|
||||
void Bind::accept(Node *node)
|
||||
|
@@ -71,7 +71,7 @@ static inline QString msgInvalidConstructor(const char *what)
|
||||
StaticAnalysisMessages::StaticAnalysisMessages()
|
||||
{
|
||||
// When changing a message or severity, update the documentation, currently
|
||||
// in creator-editors.qdoc, accordingly.
|
||||
// in creator-code-syntax.qdoc, accordingly.
|
||||
newMsg(ErrInvalidEnumValue, Error,
|
||||
tr("Invalid value for enum."));
|
||||
newMsg(ErrEnumValueMustBeStringOrNumber, Error,
|
||||
@@ -211,36 +211,36 @@ StaticAnalysisMessages::StaticAnalysisMessages()
|
||||
newMsg(ErrInvalidArrayValueLength, Error,
|
||||
tr("%1 elements expected in array value."), 1);
|
||||
newMsg(WarnImperativeCodeNotEditableInVisualDesigner, Warning,
|
||||
tr("Imperative code is not supported in the Qt Quick Designer."));
|
||||
tr("Imperative code is not supported in Qt Design Studio."));
|
||||
newMsg(WarnUnsupportedTypeInVisualDesigner, Warning,
|
||||
tr("This type (%1) is not supported in the Qt Quick Designer."), 1);
|
||||
tr("This type (%1) is not supported in Qt Design Studio."), 1);
|
||||
newMsg(WarnReferenceToParentItemNotSupportedByVisualDesigner, Warning,
|
||||
tr("Reference to parent item cannot be resolved correctly by the Qt Quick Designer."));
|
||||
tr("Reference to parent item cannot be resolved correctly by Qt Design Studio."));
|
||||
newMsg(WarnUndefinedValueForVisualDesigner, Warning,
|
||||
tr("This visual property binding cannot be evaluated in the local context "
|
||||
"and might not show up in Qt Quick Designer as expected."));
|
||||
"and might not show up in Qt Design Studio as expected."));
|
||||
newMsg(WarnStatesOnlyInRootItemForVisualDesigner, Warning,
|
||||
tr("Qt Quick Designer only supports states in the root item."));
|
||||
tr("Qt Design Studio only supports states in the root item."));
|
||||
newMsg(ErrInvalidIdeInVisualDesigner, Error,
|
||||
tr("This id might be ambiguous and is not supported in the Qt Quick Designer."));
|
||||
tr("This id might be ambiguous and is not supported in Qt Design Studio."));
|
||||
newMsg(ErrUnsupportedRootTypeInVisualDesigner, Error,
|
||||
tr("This type (%1) is not supported as a root element by Qt Quick Designer."), 1);
|
||||
tr("This type (%1) is not supported as a root element by Qt Design Studio."), 1);
|
||||
newMsg(ErrUnsupportedRootTypeInQmlUi, Error,
|
||||
tr("This type (%1) is not supported as a root element of a Qt Quick UI form."), 1);
|
||||
tr("This type (%1) is not supported as a root element of a UI file (.ui.qml)."), 1);
|
||||
newMsg(ErrUnsupportedTypeInQmlUi, Error,
|
||||
tr("This type (%1) is not supported in a Qt Quick UI form."), 1);
|
||||
tr("This type (%1) is not supported in a UI file (.ui.qml)."), 1);
|
||||
newMsg(ErrFunctionsNotSupportedInQmlUi, Error,
|
||||
tr("Functions are not supported in a Qt Quick UI form."));
|
||||
tr("Functions are not supported in a UI file (.ui.qml)."));
|
||||
newMsg(ErrBlocksNotSupportedInQmlUi, Error,
|
||||
tr("JavaScript blocks are not supported in a Qt Quick UI form."));
|
||||
tr("JavaScript blocks are not supported in a UI file (.ui.qml)."));
|
||||
newMsg(ErrBehavioursNotSupportedInQmlUi, Error,
|
||||
tr("Behavior type is not supported in a Qt Quick UI form."));
|
||||
tr("Behavior type is not supported in a UI file (.ui.qml)."));
|
||||
newMsg(ErrStatesOnlyInRootItemInQmlUi, Error,
|
||||
tr("States are only supported in the root item in a Qt Quick UI form."));
|
||||
tr("States are only supported in the root item in a UI file (.ui.qml)."));
|
||||
newMsg(ErrReferenceToParentItemNotSupportedInQmlUi, Error,
|
||||
tr("Referencing the parent of the root item is not supported in a Qt Quick UI form."));
|
||||
tr("Referencing the parent of the root item is not supported in a UI file (.ui.qml)."));
|
||||
newMsg(ErrDoNotMixTranslationFunctionsInQmlUi, Error,
|
||||
tr("Do not mix translation functions in a Qt Quick UI form."));
|
||||
tr("Do not mix translation functions in a UI file (.ui.qml)."));
|
||||
newMsg(StateCannotHaveChildItem, Error,
|
||||
tr("A State cannot have a child item (%1)."), 1);
|
||||
newMsg(WarnDuplicateImport, Warning,
|
||||
@@ -250,7 +250,7 @@ StaticAnalysisMessages::StaticAnalysisMessages()
|
||||
newMsg(ErrTypeIsInstantiatedRecursively, Error,
|
||||
tr("Type cannot be instantiated recursively (%1)."), 1);
|
||||
newMsg(WarnLogicalValueDoesNotDependOnValues, Warning,
|
||||
tr("Logical value does not depend on actual values"));
|
||||
tr("Logical value does not depend on actual values."));
|
||||
newMsg(ErrToManyComponentChildren, Error,
|
||||
tr("Components are only allowed to have a single child element."));
|
||||
newMsg(WarnComponentRequiresChildren, Warning,
|
||||
|
@@ -34,6 +34,7 @@ add_qtc_library(Utils
|
||||
differ.cpp differ.h
|
||||
displayname.cpp displayname.h
|
||||
dropsupport.cpp dropsupport.h
|
||||
dynamiclicensecheck.h
|
||||
elfreader.cpp elfreader.h
|
||||
elidinglabel.cpp elidinglabel.h
|
||||
environment.cpp environment.h
|
||||
|
68
src/libs/utils/dynamiclicensecheck.h
Normal file
68
src/libs/utils/dynamiclicensecheck.h
Normal file
@@ -0,0 +1,68 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
**
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <extensionsystem/pluginmanager.h>
|
||||
#include <extensionsystem/pluginspec.h>
|
||||
#include <extensionsystem/iplugin.h>
|
||||
|
||||
#include <utils/predicates.h>
|
||||
#include <utils/algorithm.h>
|
||||
|
||||
#include <QMetaObject>
|
||||
|
||||
namespace Utils {
|
||||
|
||||
enum FoundLicense {
|
||||
community,
|
||||
professional,
|
||||
enterprise
|
||||
};
|
||||
|
||||
FoundLicense checkLicense() {
|
||||
const ExtensionSystem::PluginSpec *pluginSpec = Utils::findOrDefault(
|
||||
ExtensionSystem::PluginManager::plugins(),
|
||||
Utils::equal(&ExtensionSystem::PluginSpec::name, QString("LicenseChecker")));
|
||||
|
||||
if (!pluginSpec)
|
||||
return community;
|
||||
|
||||
ExtensionSystem::IPlugin *plugin = pluginSpec->plugin();
|
||||
|
||||
if (!plugin)
|
||||
return community;
|
||||
|
||||
bool retVal = false;
|
||||
bool success = QMetaObject::invokeMethod(plugin,
|
||||
"qdsEnterpriseLicense",
|
||||
Qt::DirectConnection,
|
||||
Q_RETURN_ARG(bool, retVal));
|
||||
if (success && retVal)
|
||||
return enterprise;
|
||||
|
||||
return professional;
|
||||
}
|
||||
} // namespace Utils
|
@@ -889,7 +889,7 @@ void LauncherSocket::handleSocketDisconnected()
|
||||
{
|
||||
QTC_ASSERT(isCalledFromLaunchersThread(), return);
|
||||
handleError(QCoreApplication::translate("Utils::LauncherSocket",
|
||||
"Launcher socket closed unexpectedly"));
|
||||
"Launcher socket closed unexpectedly."));
|
||||
}
|
||||
|
||||
void LauncherSocket::handleError(const QString &error)
|
||||
|
@@ -106,29 +106,36 @@ LayoutBuilder::LayoutItem::LayoutItem(const QString &text)
|
||||
: text(text)
|
||||
{}
|
||||
|
||||
static QLayout *createLayoutFromType(LayoutBuilder::LayoutType layoutType)
|
||||
QLayout *LayoutBuilder::createLayout() const
|
||||
{
|
||||
switch (layoutType) {
|
||||
QLayout *layout = nullptr;
|
||||
switch (m_layoutType) {
|
||||
case LayoutBuilder::FormLayout: {
|
||||
auto formLayout = new QFormLayout;
|
||||
formLayout->setFieldGrowthPolicy(QFormLayout::AllNonFixedFieldsGrow);
|
||||
return formLayout;
|
||||
layout = formLayout;
|
||||
break;
|
||||
}
|
||||
case LayoutBuilder::GridLayout: {
|
||||
auto gridLayout = new QGridLayout;
|
||||
return gridLayout;
|
||||
layout = gridLayout;
|
||||
break;
|
||||
}
|
||||
case LayoutBuilder::HBoxLayout: {
|
||||
auto hboxLayout = new QHBoxLayout;
|
||||
return hboxLayout;
|
||||
layout = hboxLayout;
|
||||
break;
|
||||
}
|
||||
case LayoutBuilder::VBoxLayout: {
|
||||
auto vboxLayout = new QVBoxLayout;
|
||||
return vboxLayout;
|
||||
layout = vboxLayout;
|
||||
break;
|
||||
}
|
||||
}
|
||||
QTC_CHECK(false);
|
||||
return nullptr;
|
||||
QTC_ASSERT(layout, return nullptr);
|
||||
if (m_spacing)
|
||||
layout->setSpacing(*m_spacing);
|
||||
return layout;
|
||||
}
|
||||
|
||||
static void setMargins(bool on, QLayout *layout)
|
||||
@@ -246,7 +253,7 @@ static void doLayoutHelper(QLayout *layout,
|
||||
*/
|
||||
LayoutBuilder::LayoutItem::LayoutItem(const LayoutBuilder &builder)
|
||||
{
|
||||
layout = createLayoutFromType(builder.m_layoutType);
|
||||
layout = builder.createLayout();
|
||||
doLayoutHelper(layout, builder.m_items);
|
||||
setMargins(builder.m_withMargins, layout);
|
||||
}
|
||||
@@ -287,6 +294,12 @@ LayoutBuilder::LayoutBuilder(LayoutType layoutType, const LayoutItems &items)
|
||||
addItem(item);
|
||||
}
|
||||
|
||||
LayoutBuilder &LayoutBuilder::setSpacing(int spacing)
|
||||
{
|
||||
m_spacing = spacing;
|
||||
return *this;
|
||||
}
|
||||
|
||||
LayoutBuilder::LayoutBuilder() = default;
|
||||
|
||||
/*!
|
||||
@@ -343,7 +356,7 @@ LayoutBuilder &LayoutBuilder::addItem(const LayoutItem &item)
|
||||
|
||||
void LayoutBuilder::doLayout(QWidget *parent)
|
||||
{
|
||||
QLayout *layout = createLayoutFromType(m_layoutType);
|
||||
QLayout *layout = createLayout();
|
||||
parent->setLayout(layout);
|
||||
|
||||
doLayoutHelper(layout, m_items);
|
||||
|
@@ -27,6 +27,8 @@
|
||||
|
||||
#include "utils_global.h"
|
||||
|
||||
#include "optional.h"
|
||||
|
||||
#include <QList>
|
||||
#include <QString>
|
||||
#include <QVariant>
|
||||
@@ -97,6 +99,8 @@ public:
|
||||
|
||||
~LayoutBuilder();
|
||||
|
||||
LayoutBuilder &setSpacing(int spacing);
|
||||
|
||||
LayoutBuilder &addItem(const LayoutItem &item);
|
||||
LayoutBuilder &addItems(const LayoutItems &items);
|
||||
|
||||
@@ -148,10 +152,12 @@ public:
|
||||
protected:
|
||||
explicit LayoutBuilder(); // Adds to existing layout.
|
||||
|
||||
QLayout *createLayout() const;
|
||||
void doLayout(QWidget *parent);
|
||||
|
||||
LayoutItems m_items;
|
||||
LayoutType m_layoutType;
|
||||
Utils::optional<int> m_spacing;
|
||||
bool m_withMargins = false;
|
||||
};
|
||||
|
||||
|
@@ -980,12 +980,12 @@ static bool askToKill(const QString &command)
|
||||
#ifdef QT_GUI_LIB
|
||||
if (QThread::currentThread() != QCoreApplication::instance()->thread())
|
||||
return true;
|
||||
const QString title = QtcProcess::tr("Process not Responding");
|
||||
const QString title = QtcProcess::tr("Process Not Responding");
|
||||
QString msg = command.isEmpty() ?
|
||||
QtcProcess::tr("The process is not responding.") :
|
||||
QtcProcess::tr("The process \"%1\" is not responding.").arg(command);
|
||||
msg += ' ';
|
||||
msg += QtcProcess::tr("Would you like to terminate it?");
|
||||
msg += QtcProcess::tr("Terminate the process?");
|
||||
// Restore the cursor that is set to wait while running.
|
||||
const bool hasOverrideCursor = QApplication::overrideCursor() != nullptr;
|
||||
if (hasOverrideCursor)
|
||||
|
@@ -13,6 +13,8 @@ Project {
|
||||
var libs = [];
|
||||
if (qbs.targetOS.contains("windows")) {
|
||||
libs.push("user32", "iphlpapi", "ws2_32", "shell32", "ole32");
|
||||
if (qbs.toolchainType === "mingw")
|
||||
libs.push("uuid");
|
||||
} else if (qbs.targetOS.contains("unix")) {
|
||||
if (!qbs.targetOS.contains("macos"))
|
||||
libs.push("X11");
|
||||
|
@@ -164,14 +164,15 @@ bool AndroidDeployQtStep::init()
|
||||
if (selectedAbis.isEmpty())
|
||||
selectedAbis.append(bs->extraData(buildKey, Constants::AndroidAbi).toString());
|
||||
|
||||
// TODO: use AndroidDevice directly instead of AndroidDeviceInfo.
|
||||
if (!info.isValid()) {
|
||||
const IDevice *dev = DeviceKitAspect::device(kit()).data();
|
||||
const auto dev =
|
||||
static_cast<const AndroidDevice *>(DeviceKitAspect::device(kit()).data());
|
||||
if (!dev) {
|
||||
reportWarningOrError(tr("No valid deployment device is set."), Task::Error);
|
||||
return false;
|
||||
}
|
||||
|
||||
// TODO: use AndroidDevice directly instead of AndroidDeviceInfo.
|
||||
info = AndroidDevice::androidDeviceInfoFromIDevice(dev);
|
||||
m_deviceInfo = info; // Keep around for later steps
|
||||
|
||||
@@ -181,18 +182,17 @@ bool AndroidDeployQtStep::init()
|
||||
return false;
|
||||
}
|
||||
|
||||
const AndroidDevice *androidDev = static_cast<const AndroidDevice *>(dev);
|
||||
if (androidDev && !androidDev->canSupportAbis(selectedAbis)) {
|
||||
if (!dev->canSupportAbis(selectedAbis)) {
|
||||
const QString error = tr("The deployment device \"%1\" does not support the "
|
||||
"architectures used by the kit.\n"
|
||||
"The kit supports \"%2\", but the device uses \"%3\".")
|
||||
.arg(dev->displayName()).arg(selectedAbis.join(", "))
|
||||
.arg(androidDev->supportedAbis().join(", "));
|
||||
.arg(dev->supportedAbis().join(", "));
|
||||
reportWarningOrError(error, Task::Error);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (androidDev && !androidDev->canHandleDeployments()) {
|
||||
if (!dev->canHandleDeployments()) {
|
||||
reportWarningOrError(tr("The deployment device \"%1\" is disconnected.")
|
||||
.arg(dev->displayName()), Task::Error);
|
||||
return false;
|
||||
|
@@ -204,31 +204,31 @@ QVariant AndroidServiceWidget::AndroidServiceModel::headerData(int section, Qt::
|
||||
{
|
||||
if (role == Qt::ToolTipRole && orientation == Qt::Horizontal) {
|
||||
if (section == 0)
|
||||
return tr("The name of the class implementing the service");
|
||||
return tr("The name of the class implementing the service.");
|
||||
else if (section == 1)
|
||||
return tr("Checked if the service is run in an external process");
|
||||
return tr("Checked if the service is run in an external process.");
|
||||
else if (section == 2)
|
||||
return tr("The name of the external process.\n"
|
||||
"Prefix with : if the process is private, use a lowercase name if the process is global.");
|
||||
else if (section == 3)
|
||||
return tr("Checked if the service is in a separate dynamic library");
|
||||
return tr("Checked if the service is in a separate dynamic library.");
|
||||
else if (section == 4)
|
||||
return tr("The name of the separate dynamic library");
|
||||
return tr("The name of the separate dynamic library.");
|
||||
else if (section == 5)
|
||||
return tr("The arguments for telling the app to run the service instead of the main activity");
|
||||
return tr("The arguments for telling the app to run the service instead of the main activity.");
|
||||
} else if (role == Qt::DisplayRole && orientation == Qt::Horizontal) {
|
||||
if (section == 0)
|
||||
return tr("Service class name");
|
||||
return tr("Service class name.");
|
||||
else if (section == 1)
|
||||
return tr("Run in external process");
|
||||
return tr("Run in external process.");
|
||||
else if (section == 2)
|
||||
return tr("Process name");
|
||||
return tr("Process name.");
|
||||
else if (section == 3)
|
||||
return tr("Run in external library");
|
||||
return tr("Run in external library.");
|
||||
else if (section == 4)
|
||||
return tr("Library name");
|
||||
return tr("Library name.");
|
||||
else if (section == 5)
|
||||
return tr("Service arguments");
|
||||
return tr("Service arguments.");
|
||||
}
|
||||
return {};
|
||||
}
|
||||
@@ -247,22 +247,22 @@ QVariant AndroidServiceWidget::AndroidServiceModel::data(const QModelIndex &inde
|
||||
if (index.column() == 0)
|
||||
return m_services[index.row()].className();
|
||||
else if (index.column() == 1)
|
||||
return tr("Run in external process");
|
||||
return tr("Run in external process.");
|
||||
else if (index.column() == 2)
|
||||
return m_services[index.row()].externalProcessName();
|
||||
else if (index.column() == 3)
|
||||
return tr("Run in external library");
|
||||
return tr("Run in external library.");
|
||||
else if (index.column() == 4)
|
||||
return m_services[index.row()].externalLibraryName();
|
||||
else if (index.column() == 5)
|
||||
return m_services[index.row()].serviceArguments();
|
||||
} else if (role == Qt::ToolTipRole) {
|
||||
if (index.column() == 0 && m_services[index.row()].className().isEmpty())
|
||||
return tr("The class name must be set");
|
||||
return tr("The class name must be set.");
|
||||
else if (index.column() == 2 && m_services[index.row()].isRunInExternalProcess())
|
||||
return tr("The process name must be set for a service run in an external process");
|
||||
return tr("The process name must be set for a service run in an external process.");
|
||||
else if (index.column() == 4 && m_services[index.row()].isRunInExternalLibrary())
|
||||
return tr("The library name must be set for a service run in an external library");
|
||||
return tr("The library name must be set for a service run in an external library.");
|
||||
} else if (role == Qt::EditRole) {
|
||||
if (index.column() == 0)
|
||||
return m_services[index.row()].className();
|
||||
|
@@ -65,7 +65,7 @@
|
||||
<item>
|
||||
<widget class="QPushButton" name="makeDefaultNdkButton">
|
||||
<property name="toolTip">
|
||||
<string>Force a specific NDK installation to be used by all Android kits.<br/>Note that the forced NDK might not be compatible with all Qt registered versions.</string>
|
||||
<string>Force a specific NDK installation to be used by all Android kits.<br/>Note that the forced NDK might not be compatible with all registered Qt versions.</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
|
@@ -1402,7 +1402,10 @@ ClangdClient::ClangdClient(Project *project, const Utils::FilePath &jsonDbDir)
|
||||
setClientCapabilities(caps);
|
||||
setLocatorsEnabled(false);
|
||||
setAutoRequestCodeActions(false); // clangd sends code actions inside diagnostics
|
||||
setProgressTitleForToken(indexingToken(), tr("Parsing C/C++ Files (clangd)"));
|
||||
if (project) {
|
||||
setProgressTitleForToken(indexingToken(),
|
||||
tr("Indexing %1 with clangd").arg(project->displayName()));
|
||||
}
|
||||
setCurrentProject(project);
|
||||
setDocumentChangeUpdateThreshold(d->settings.documentUpdateThreshold);
|
||||
|
||||
@@ -2958,9 +2961,10 @@ void ClangdClient::Private::handleSemanticTokens(TextDocument *doc,
|
||||
int version, bool force)
|
||||
{
|
||||
SubtaskTimer t(highlightingTimer);
|
||||
qCDebug(clangdLog) << "handling LSP tokens" << doc->filePath() << tokens.size();
|
||||
qCInfo(clangdLogHighlight) << "handling LSP tokens" << doc->filePath()
|
||||
<< version << tokens.size();
|
||||
if (version != q->documentVersion(doc->filePath())) {
|
||||
qCDebug(clangdLogHighlight) << "LSP tokens outdated; aborting highlighting procedure"
|
||||
qCInfo(clangdLogHighlight) << "LSP tokens outdated; aborting highlighting procedure"
|
||||
<< version << q->documentVersion(doc->filePath());
|
||||
return;
|
||||
}
|
||||
@@ -2968,7 +2972,7 @@ void ClangdClient::Private::handleSemanticTokens(TextDocument *doc,
|
||||
const auto previous = previousTokens.find(doc);
|
||||
if (previous != previousTokens.end()) {
|
||||
if (!force && previous->first == tokens && previous->second == version) {
|
||||
qCDebug(clangdLogHighlight) << "tokens and version same as last time; nothing to do";
|
||||
qCInfo(clangdLogHighlight) << "tokens and version same as last time; nothing to do";
|
||||
return;
|
||||
}
|
||||
previous->first = tokens;
|
||||
@@ -2985,7 +2989,7 @@ void ClangdClient::Private::handleSemanticTokens(TextDocument *doc,
|
||||
if (!q->documentOpen(doc))
|
||||
return;
|
||||
if (version != q->documentVersion(doc->filePath())) {
|
||||
qCDebug(clangdLogHighlight) << "AST not up to date; aborting highlighting procedure"
|
||||
qCInfo(clangdLogHighlight) << "AST not up to date; aborting highlighting procedure"
|
||||
<< version << q->documentVersion(doc->filePath());
|
||||
return;
|
||||
}
|
||||
|
@@ -44,6 +44,7 @@
|
||||
#include <coreplugin/messagemanager.h>
|
||||
|
||||
#include <cppeditor/cppcodemodelsettings.h>
|
||||
#include <cppeditor/cppeditorconstants.h>
|
||||
#include <cppeditor/cppfollowsymbolundercursor.h>
|
||||
#include <cppeditor/cppmodelmanager.h>
|
||||
#include <cppeditor/cppprojectfile.h>
|
||||
@@ -58,6 +59,7 @@
|
||||
#include <projectexplorer/buildsystem.h>
|
||||
#include <projectexplorer/project.h>
|
||||
#include <projectexplorer/projectnodes.h>
|
||||
#include <projectexplorer/projecttree.h>
|
||||
#include <projectexplorer/session.h>
|
||||
#include <projectexplorer/target.h>
|
||||
|
||||
@@ -85,21 +87,20 @@ static CppEditor::CppModelManager *cppModelManager()
|
||||
return CppEditor::CppModelManager::instance();
|
||||
}
|
||||
|
||||
static const QList<TextEditor::BaseTextEditor *> allCppEditors()
|
||||
static ProjectExplorer::Project *fallbackProject()
|
||||
{
|
||||
QList<TextEditor::BaseTextEditor *> cppEditors;
|
||||
for (const Core::DocumentModel::Entry * const entry : Core::DocumentModel::entries()) {
|
||||
const auto textDocument = qobject_cast<TextEditor::TextDocument *>(entry->document);
|
||||
if (!textDocument)
|
||||
continue;
|
||||
if (const auto cppEditor = qobject_cast<TextEditor::BaseTextEditor *>(Utils::findOrDefault(
|
||||
Core::DocumentModel::editorsForDocument(textDocument), [](Core::IEditor *editor) {
|
||||
return CppEditor::CppModelManager::isCppEditor(editor);
|
||||
}))) {
|
||||
cppEditors << cppEditor;
|
||||
}
|
||||
}
|
||||
return cppEditors;
|
||||
if (ProjectExplorer::Project * const p = ProjectExplorer::ProjectTree::currentProject())
|
||||
return p;
|
||||
return ProjectExplorer::SessionManager::startupProject();
|
||||
}
|
||||
|
||||
static const QList<TextEditor::TextDocument *> allCppDocuments()
|
||||
{
|
||||
const auto isCppDocument = Utils::equal(&Core::IDocument::id,
|
||||
Utils::Id(CppEditor::Constants::CPPEDITOR_ID));
|
||||
const QList<Core::IDocument *> documents
|
||||
= Utils::filtered(Core::DocumentModel::openedDocuments(), isCppDocument);
|
||||
return Utils::qobject_container_cast<TextEditor::TextDocument *>(documents);
|
||||
}
|
||||
|
||||
ClangModelManagerSupport::ClangModelManagerSupport()
|
||||
@@ -149,10 +150,7 @@ ClangModelManagerSupport::ClangModelManagerSupport()
|
||||
connect(sessionManager, &ProjectExplorer::SessionManager::aboutToRemoveProject,
|
||||
this, &ClangModelManagerSupport::onAboutToRemoveProject);
|
||||
connect(sessionManager, &ProjectExplorer::SessionManager::projectRemoved,
|
||||
this, [this] {
|
||||
if (ClangdClient * const fallbackClient = clientForProject(nullptr))
|
||||
claimNonProjectSources(fallbackClient);
|
||||
});
|
||||
this, [this] { claimNonProjectSources(clientForProject(fallbackProject())); });
|
||||
|
||||
CppEditor::ClangdSettings::setDefaultClangdPath(Core::ICore::clangdExecutable(CLANG_BINDIR));
|
||||
connect(&CppEditor::ClangdSettings::instance(), &CppEditor::ClangdSettings::changed,
|
||||
@@ -369,14 +367,16 @@ void ClangModelManagerSupport::updateLanguageClient(
|
||||
|
||||
// Acquaint the client with all open C++ documents for this project.
|
||||
bool hasDocuments = false;
|
||||
for (TextEditor::BaseTextEditor * const editor : allCppEditors()) {
|
||||
const Utils::FilePath filePath = editor->textDocument()->filePath();
|
||||
if (!project->isKnownFile(filePath))
|
||||
continue;
|
||||
LanguageClientManager::openDocumentWithClient(editor->textDocument(), client);
|
||||
ClangEditorDocumentProcessor::clearTextMarks(filePath);
|
||||
for (TextEditor::TextDocument * const doc : allCppDocuments()) {
|
||||
const Client * const currentClient = LanguageClientManager::clientForDocument(doc);
|
||||
if (!currentClient || !currentClient->project()
|
||||
|| currentClient->state() != Client::Initialized
|
||||
|| project->isKnownFile(doc->filePath())) {
|
||||
LanguageClientManager::openDocumentWithClient(doc, client);
|
||||
ClangEditorDocumentProcessor::clearTextMarks(doc->filePath());
|
||||
hasDocuments = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (client->state() == Client::Initialized)
|
||||
updateParserConfig();
|
||||
@@ -444,7 +444,7 @@ ClangdClient *ClangModelManagerSupport::clientForProject(
|
||||
|
||||
ClangdClient *ClangModelManagerSupport::clientForFile(const Utils::FilePath &file) const
|
||||
{
|
||||
return clientForProject(ProjectExplorer::SessionManager::projectForFile(file));
|
||||
return qobject_cast<ClangdClient *>(LanguageClientManager::clientForFilePath(file));
|
||||
}
|
||||
|
||||
ClangdClient *ClangModelManagerSupport::createClient(ProjectExplorer::Project *project,
|
||||
@@ -455,15 +455,18 @@ ClangdClient *ClangModelManagerSupport::createClient(ProjectExplorer::Project *p
|
||||
return client;
|
||||
}
|
||||
|
||||
void ClangModelManagerSupport::claimNonProjectSources(ClangdClient *fallbackClient)
|
||||
void ClangModelManagerSupport::claimNonProjectSources(ClangdClient *client)
|
||||
{
|
||||
for (TextEditor::BaseTextEditor * const editor : allCppEditors()) {
|
||||
if (ProjectExplorer::SessionManager::projectForFile(editor->textDocument()->filePath()))
|
||||
if (!client)
|
||||
return;
|
||||
for (TextEditor::TextDocument * const doc : allCppDocuments()) {
|
||||
if (Client * const currentClient = LanguageClientManager::clientForDocument(doc);
|
||||
currentClient && currentClient->state() == Client::Initialized
|
||||
&& (currentClient == client || currentClient->project())) {
|
||||
continue;
|
||||
if (!fallbackClient->documentOpen(editor->textDocument())) {
|
||||
ClangEditorDocumentProcessor::clearTextMarks(editor->textDocument()->filePath());
|
||||
fallbackClient->openDocument(editor->textDocument());
|
||||
}
|
||||
ClangEditorDocumentProcessor::clearTextMarks(doc->filePath());
|
||||
client->openDocument(doc);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -563,8 +566,10 @@ void ClangModelManagerSupport::onEditorOpened(Core::IEditor *editor)
|
||||
|
||||
// TODO: Ensure that not fully loaded documents are updated?
|
||||
|
||||
ProjectExplorer::Project * const project
|
||||
ProjectExplorer::Project * project
|
||||
= ProjectExplorer::SessionManager::projectForFile(document->filePath());
|
||||
if (!project)
|
||||
project = fallbackProject();
|
||||
if (ClangdClient * const client = clientForProject(project))
|
||||
LanguageClientManager::openDocumentWithClient(textDocument, client);
|
||||
}
|
||||
|
@@ -134,7 +134,7 @@ private:
|
||||
void updateLanguageClient(ProjectExplorer::Project *project,
|
||||
const CppEditor::ProjectInfo::ConstPtr &projectInfo);
|
||||
ClangdClient *createClient(ProjectExplorer::Project *project, const Utils::FilePath &jsonDbDir);
|
||||
void claimNonProjectSources(ClangdClient *fallbackClient);
|
||||
void claimNonProjectSources(ClangdClient *client);
|
||||
void watchForExternalChanges();
|
||||
void watchForInternalChanges();
|
||||
|
||||
|
@@ -35,10 +35,12 @@
|
||||
#include <coreplugin/editormanager/editormanager.h>
|
||||
#include <coreplugin/editormanager/ieditor.h>
|
||||
#include <coreplugin/icore.h>
|
||||
#include <cppeditor/cppcodemodelsettings.h>
|
||||
#include <cppeditor/cpptoolsreuse.h>
|
||||
#include <cppeditor/cpptoolstestcase.h>
|
||||
#include <cppeditor/modelmanagertesthelper.h>
|
||||
#include <cppeditor/projectinfo.h>
|
||||
#include <languageclient/languageclientmanager.h>
|
||||
#include <texteditor/codeassist/assistproposalitem.h>
|
||||
#include <texteditor/codeassist/genericproposalmodel.h>
|
||||
#include <texteditor/textdocument.h>
|
||||
@@ -514,6 +516,13 @@ namespace ClangCodeModel {
|
||||
namespace Internal {
|
||||
namespace Tests {
|
||||
|
||||
void ClangCodeCompletionTest::initTestCase()
|
||||
{
|
||||
CppEditor::ClangdSettings::setUseClangd(false);
|
||||
for (LanguageClient::Client * const c : LanguageClient::LanguageClientManager::clients())
|
||||
LanguageClient::LanguageClientManager::shutdownClient(c);
|
||||
}
|
||||
|
||||
void ClangCodeCompletionTest::testCompleteDoxygenKeywords()
|
||||
{
|
||||
ProjectLessCompletionTest t("doxygenKeywordsCompletion.cpp");
|
||||
|
@@ -38,6 +38,8 @@ class ClangCodeCompletionTest : public QObject
|
||||
Q_OBJECT
|
||||
|
||||
private slots:
|
||||
void initTestCase();
|
||||
|
||||
void testCompleteDoxygenKeywords();
|
||||
void testCompletePreprocessorKeywords();
|
||||
void testCompleteIncludeDirective();
|
||||
|
@@ -2036,7 +2036,7 @@ void ClangdTestExternalChanges::test()
|
||||
QVERIFY(waitForSignalOrTimeout(ClangModelManagerSupport::instance(),
|
||||
&ClangModelManagerSupport::createdClient, timeOutInMs()));
|
||||
ClangdClient * const newClient = ClangModelManagerSupport::instance()
|
||||
->clientForFile(filePath("main.cpp"));
|
||||
->clientForProject(project());
|
||||
QVERIFY(newClient);
|
||||
QVERIFY(newClient != oldClient);
|
||||
newClient->enableTesting();
|
||||
|
@@ -303,7 +303,7 @@ CMakeBuildSettingsWidget::CMakeBuildSettingsWidget(CMakeBuildConfiguration *bc)
|
||||
m_resetButton->setEnabled(false);
|
||||
|
||||
m_batchEditButton = new QPushButton(tr("Batch Edit..."));
|
||||
m_batchEditButton->setToolTip(tr("Set or reset multiple values in the CMake Configuration."));
|
||||
m_batchEditButton->setToolTip(tr("Set or reset multiple values in the CMake configuration."));
|
||||
|
||||
m_showAdvancedCheckBox = new QCheckBox(tr("Advanced"));
|
||||
|
||||
@@ -339,8 +339,9 @@ CMakeBuildSettingsWidget::CMakeBuildSettingsWidget(CMakeBuildConfiguration *bc)
|
||||
qmlDebugAspect
|
||||
},
|
||||
m_warningMessageLabel,
|
||||
Space(10),
|
||||
Row{m_kitConfiguration, m_configurationStates},
|
||||
m_kitConfiguration,
|
||||
Column {
|
||||
m_configurationStates,
|
||||
Group {
|
||||
cmakeConfiguration,
|
||||
Row {
|
||||
@@ -349,6 +350,7 @@ CMakeBuildSettingsWidget::CMakeBuildSettingsWidget(CMakeBuildConfiguration *bc)
|
||||
},
|
||||
m_reconfigureButton,
|
||||
}
|
||||
}.setSpacing(0)
|
||||
}.attachTo(details, false);
|
||||
|
||||
updateAdvancedCheckBox();
|
||||
|
@@ -326,7 +326,7 @@ QSet<Id> CMakeKitAspect::availableFeatures(const Kit *k) const
|
||||
|
||||
QString CMakeKitAspect::msgUnsupportedVersion(const QByteArray &versionString)
|
||||
{
|
||||
return tr("CMake version %1 is unsupported. Please update to "
|
||||
return tr("CMake version %1 is unsupported. Update to "
|
||||
"version 3.14 (with file-api) or later.")
|
||||
.arg(QString::fromUtf8(versionString));
|
||||
}
|
||||
|
@@ -283,7 +283,7 @@ QObject *CorePlugin::remoteCommand(const QStringList & /* options */,
|
||||
});
|
||||
return nullptr;
|
||||
}
|
||||
const FilePaths filePaths = Utils::transform(args, FilePath::fromString);
|
||||
const FilePaths filePaths = Utils::transform(args, FilePath::fromUserInput);
|
||||
IDocument *res = MainWindow::openFiles(
|
||||
filePaths,
|
||||
ICore::OpenFilesFlags(ICore::SwitchMode | ICore::CanContainLineAndColumnNumbers | ICore::SwitchSplitIfAlreadyVisible),
|
||||
|
@@ -83,13 +83,16 @@ protected:
|
||||
void setSettings(Utils::AspectContainer *settings);
|
||||
void setLayouter(const std::function<void(QWidget *w)> &layouter);
|
||||
|
||||
// Used in FontSettingsPage. FIXME?
|
||||
QPointer<QWidget> m_widget; // Used in conjunction with m_widgetCreator
|
||||
|
||||
private:
|
||||
Utils::Id m_id;
|
||||
Utils::Id m_category;
|
||||
QString m_displayName;
|
||||
QString m_displayCategory;
|
||||
Utils::Icon m_categoryIcon;
|
||||
WidgetCreator m_widgetCreator;
|
||||
QPointer<QWidget> m_widget; // Used in conjunction with m_widgetCreator
|
||||
|
||||
mutable bool m_keywordsInitialized = false;
|
||||
mutable QStringList m_keywords;
|
||||
|
@@ -199,6 +199,7 @@ public:
|
||||
IDocument *m_blockedIDocument = nullptr;
|
||||
|
||||
QAction *m_saveAllAction;
|
||||
QString fileDialogFilterOverride;
|
||||
};
|
||||
|
||||
static DocumentManager *m_instance;
|
||||
@@ -770,6 +771,16 @@ bool DocumentManager::saveDocument(IDocument *document,
|
||||
return ret;
|
||||
}
|
||||
|
||||
QString DocumentManager::fileDialogFilter(QString *selectedFilter)
|
||||
{
|
||||
if (!d->fileDialogFilterOverride.isEmpty()) {
|
||||
if (selectedFilter)
|
||||
*selectedFilter = d->fileDialogFilterOverride.split(";;").first();
|
||||
return d->fileDialogFilterOverride;
|
||||
}
|
||||
return allDocumentFactoryFiltersString(selectedFilter);
|
||||
}
|
||||
|
||||
QString DocumentManager::allDocumentFactoryFiltersString(QString *allFilesFilter = nullptr)
|
||||
{
|
||||
QSet<QString> uniqueFilters;
|
||||
@@ -1531,6 +1542,11 @@ void DocumentManager::notifyFilesChangedInternally(const FilePaths &filePaths)
|
||||
emit m_instance->filesChangedInternally(filePaths);
|
||||
}
|
||||
|
||||
void DocumentManager::setFileDialogFilter(const QString &filter)
|
||||
{
|
||||
d->fileDialogFilterOverride = filter;
|
||||
}
|
||||
|
||||
void DocumentManager::registerSaveAllAction()
|
||||
{
|
||||
d->registerSaveAllAction();
|
||||
|
@@ -142,6 +142,10 @@ public:
|
||||
lead to any editors to reload or any other editor manager actions. */
|
||||
static void notifyFilesChangedInternally(const Utils::FilePaths &filePaths);
|
||||
|
||||
static void setFileDialogFilter(const QString &filter);
|
||||
|
||||
static QString fileDialogFilter(QString *selectedFilter = nullptr);
|
||||
|
||||
signals:
|
||||
/* Used to notify e.g. the code model to update the given files. Does *not*
|
||||
lead to any editors to reload or any other editor manager actions. */
|
||||
|
@@ -3231,7 +3231,7 @@ void EditorManager::addCloseEditorListener(const std::function<bool (IEditor *)>
|
||||
FilePaths EditorManager::getOpenFilePaths()
|
||||
{
|
||||
QString selectedFilter;
|
||||
const QString &fileFilters = DocumentManager::allDocumentFactoryFiltersString(&selectedFilter);
|
||||
const QString &fileFilters = DocumentManager::fileDialogFilter(&selectedFilter);
|
||||
return DocumentManager::getOpenFileNames(fileFilters, {}, &selectedFilter);
|
||||
}
|
||||
|
||||
|
@@ -425,7 +425,7 @@ LoggingViewManagerWidget::LoggingViewManagerWidget(QWidget *parent)
|
||||
buttonsLayout->addWidget(stop);
|
||||
auto qtInternal = new QToolButton;
|
||||
qtInternal->setIcon(Core::Icons::QTLOGO.icon());
|
||||
qtInternal->setToolTip(tr("Toggle logging of Qt internal loggings"));
|
||||
qtInternal->setToolTip(tr("Toggle Qt Internal Logging"));
|
||||
qtInternal->setCheckable(true);
|
||||
qtInternal->setChecked(false);
|
||||
buttonsLayout->addWidget(qtInternal);
|
||||
@@ -616,7 +616,7 @@ void LoggingViewManagerWidget::saveLoggingsToFile() const
|
||||
if (enabled)
|
||||
m_manager->setEnabled(false);
|
||||
const Utils::FilePath fp = Utils::FileUtils::getSaveFilePath(ICore::dialogParent(),
|
||||
tr("Save logs as"));
|
||||
tr("Save Logs As"));
|
||||
if (fp.isEmpty())
|
||||
return;
|
||||
const bool useTS = m_timestamps->isChecked();
|
||||
@@ -628,7 +628,7 @@ void LoggingViewManagerWidget::saveLoggingsToFile() const
|
||||
if (res == -1) {
|
||||
QMessageBox::critical(
|
||||
ICore::dialogParent(), tr("Error"),
|
||||
tr("Failed to write logs to '%1'.").arg(fp.toUserOutput()));
|
||||
tr("Failed to write logs to \"%1\".").arg(fp.toUserOutput()));
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -636,14 +636,14 @@ void LoggingViewManagerWidget::saveLoggingsToFile() const
|
||||
} else {
|
||||
QMessageBox::critical(
|
||||
ICore::dialogParent(), tr("Error"),
|
||||
tr("Failed to open file '%1' for writing logs.").arg(fp.toUserOutput()));
|
||||
tr("Failed to open file \"%1\" for writing logs.").arg(fp.toUserOutput()));
|
||||
}
|
||||
}
|
||||
|
||||
void LoggingViewManagerWidget::saveEnabledCategoryPreset() const
|
||||
{
|
||||
Utils::FilePath fp = Utils::FileUtils::getSaveFilePath(ICore::dialogParent(),
|
||||
tr("Save enabled categories as"));
|
||||
tr("Save Enabled Categories As"));
|
||||
if (fp.isEmpty())
|
||||
return;
|
||||
const QList<LoggingCategoryItem> enabled = m_categoryModel->enabledCategories();
|
||||
@@ -663,13 +663,13 @@ void LoggingViewManagerWidget::saveEnabledCategoryPreset() const
|
||||
if (!fp.writeFileContents(doc.toJson(QJsonDocument::Compact)))
|
||||
QMessageBox::critical(
|
||||
ICore::dialogParent(), tr("Error"),
|
||||
tr("Failed to write preset file '%1'.").arg(fp.toUserOutput()));
|
||||
tr("Failed to write preset file \"%1\".").arg(fp.toUserOutput()));
|
||||
}
|
||||
|
||||
void LoggingViewManagerWidget::loadAndUpdateFromPreset()
|
||||
{
|
||||
Utils::FilePath fp = Utils::FileUtils::getOpenFilePath(ICore::dialogParent(),
|
||||
tr("Load enabled categories from"));
|
||||
tr("Load Enabled Categories From"));
|
||||
if (fp.isEmpty())
|
||||
return;
|
||||
// read file, update categories
|
||||
@@ -677,7 +677,7 @@ void LoggingViewManagerWidget::loadAndUpdateFromPreset()
|
||||
QJsonDocument doc = QJsonDocument::fromJson(fp.fileContents(), &error);
|
||||
if (error.error != QJsonParseError::NoError) {
|
||||
QMessageBox::critical(ICore::dialogParent(), tr("Error"),
|
||||
tr("Failed to read preset file '%1': %2").arg(fp.toUserOutput())
|
||||
tr("Failed to read preset file \"%1\": %2").arg(fp.toUserOutput())
|
||||
.arg(error.errorString()));
|
||||
return;
|
||||
}
|
||||
|
@@ -41,7 +41,7 @@ namespace CppEditor {
|
||||
|
||||
ClangDiagnosticConfigsSelectionWidget::ClangDiagnosticConfigsSelectionWidget(QWidget *parent)
|
||||
: QWidget(parent)
|
||||
, m_label(new QLabel(tr("Diagnostic Configuration:")))
|
||||
, m_label(new QLabel(tr("Diagnostic configuration:")))
|
||||
, m_button(new QPushButton)
|
||||
{
|
||||
auto *layout = new QHBoxLayout(this);
|
||||
|
@@ -177,6 +177,8 @@ QList<AccessRange> collectAccessRanges(const CPlusPlus::TranslationUnit *tu,
|
||||
|
||||
if (AccessDeclarationAST *xsDecl = decl->asAccessDeclaration()) {
|
||||
const unsigned token = xsDecl->access_specifier_token;
|
||||
if (tu->tokenAt(token).generated())
|
||||
continue;
|
||||
InsertionPointLocator::AccessSpec newXsSpec = initialXs;
|
||||
bool isSlot = xsDecl->slots_token && tu->tokenKind(xsDecl->slots_token) == T_Q_SLOTS;
|
||||
|
||||
|
@@ -120,7 +120,7 @@ DebuggerSettings::DebuggerSettings()
|
||||
|
||||
forceLoggingToConsole.setSettingsKey(debugModeGroup, "ForceLoggingToConsole");
|
||||
forceLoggingToConsole.setLabelText(tr("Force logging to console"));
|
||||
forceLoggingToConsole.setToolTip(tr("This sets QT_LOGGING_TO_CONSOLE=1 in the environment "
|
||||
forceLoggingToConsole.setToolTip(tr("Sets QT_LOGGING_TO_CONSOLE=1 in the environment "
|
||||
"of the debugged program, preventing storing debug output "
|
||||
"in system logs."));
|
||||
|
||||
@@ -165,7 +165,7 @@ DebuggerSettings::DebuggerSettings()
|
||||
CommonOptionsPage::msgSetBreakpointAtFunction(Constants::CRT_DEBUG_REPORT));
|
||||
cdbBreakOnCrtDbgReport.setToolTip(
|
||||
CommonOptionsPage::msgSetBreakpointAtFunctionToolTip(Constants::CRT_DEBUG_REPORT,
|
||||
tr("This is useful to catch runtime error messages for example caused by assert().")));
|
||||
tr("Catches runtime error messages caused by assert(), for example.")));
|
||||
|
||||
useCdbConsole.setSettingsKey(cdbSettingsGroup, "CDB_Console");
|
||||
useCdbConsole.setToolTip("<html><head/><body><p>" + tr(
|
||||
@@ -421,7 +421,7 @@ DebuggerSettings::DebuggerSettings()
|
||||
|
||||
useAnnotationsInMainEditor.setSettingsKey(debugModeGroup, "UseAnnotations");
|
||||
useAnnotationsInMainEditor.setLabelText(tr("Use annotations in main editor when debugging"));
|
||||
useAnnotationsInMainEditor.setToolTip(tr("<p>Checking this will show simple variable values "
|
||||
useAnnotationsInMainEditor.setToolTip(tr("<p>Shows simple variable values "
|
||||
"as annotations in the main editor during debugging."));
|
||||
useAnnotationsInMainEditor.setDefaultValue(true);
|
||||
|
||||
@@ -440,7 +440,7 @@ DebuggerSettings::DebuggerSettings()
|
||||
|
||||
useToolTipsInMainEditor.setSettingsKey(debugModeGroup, "UseToolTips");
|
||||
useToolTipsInMainEditor.setLabelText(tr("Use tooltips in main editor when debugging"));
|
||||
useToolTipsInMainEditor.setToolTip(tr("<p>Checking this will enable tooltips for variable "
|
||||
useToolTipsInMainEditor.setToolTip(tr("<p>Enables tooltips for variable "
|
||||
"values during debugging. Since this can slow down debugging and "
|
||||
"does not provide reliable information as it does not use scope "
|
||||
"information, it is switched off by default."));
|
||||
@@ -448,17 +448,17 @@ DebuggerSettings::DebuggerSettings()
|
||||
|
||||
useToolTipsInLocalsView.setSettingsKey(debugModeGroup, "UseToolTipsInLocalsView");
|
||||
useToolTipsInLocalsView.setLabelText(tr("Use Tooltips in Locals View when Debugging"));
|
||||
useToolTipsInLocalsView.setToolTip(tr("<p>Checking this will enable tooltips in the locals "
|
||||
useToolTipsInLocalsView.setToolTip(tr("<p>Enables tooltips in the locals "
|
||||
"view during debugging."));
|
||||
|
||||
useToolTipsInBreakpointsView.setSettingsKey(debugModeGroup, "UseToolTipsInBreakpointsView");
|
||||
useToolTipsInBreakpointsView.setLabelText(tr("Use Tooltips in Breakpoints View when Debugging"));
|
||||
useToolTipsInBreakpointsView.setToolTip(tr("<p>Checking this will enable tooltips in the breakpoints "
|
||||
useToolTipsInBreakpointsView.setToolTip(tr("<p>Enables tooltips in the breakpoints "
|
||||
"view during debugging."));
|
||||
|
||||
useToolTipsInStackView.setSettingsKey(debugModeGroup, "UseToolTipsInStackView");
|
||||
useToolTipsInStackView.setLabelText(tr("Use Tooltips in Stack View when Debugging"));
|
||||
useToolTipsInStackView.setToolTip(tr("<p>Checking this will enable tooltips in the stack "
|
||||
useToolTipsInStackView.setToolTip(tr("<p>Enables tooltips in the stack "
|
||||
"view during debugging."));
|
||||
useToolTipsInStackView.setDefaultValue(true);
|
||||
|
||||
|
@@ -333,7 +333,7 @@ public:
|
||||
|
||||
m_runAsOutsideUser = new QCheckBox(tr("Run as outside user"));
|
||||
m_runAsOutsideUser->setToolTip(tr("Uses user ID and group ID of the user running Qt Creator "
|
||||
"in the Docker container."));
|
||||
"in the docker container."));
|
||||
m_runAsOutsideUser->setChecked(data.useLocalUidGid);
|
||||
m_runAsOutsideUser->setEnabled(HostOsInfo::isLinuxHost());
|
||||
|
||||
@@ -361,7 +361,7 @@ public:
|
||||
|
||||
m_pathsListEdit = new PathListEditor;
|
||||
m_pathsListEdit->setToolTip(tr("Maps paths in this list one-to-one to the "
|
||||
"Docker container."));
|
||||
"docker container."));
|
||||
m_pathsListEdit->setPathList(data.mounts);
|
||||
|
||||
connect(m_pathsListEdit, &PathListEditor::changed, this, [dockerDevice, this]() {
|
||||
@@ -378,12 +378,12 @@ public:
|
||||
|
||||
auto searchDirsComboBox = new QComboBox;
|
||||
searchDirsComboBox->addItem(tr("Search in PATH"));
|
||||
searchDirsComboBox->addItem(tr("Search in selected directories"));
|
||||
searchDirsComboBox->addItem(tr("Search in Selected Directories"));
|
||||
|
||||
auto searchDirsLineEdit = new QLineEdit;
|
||||
searchDirsLineEdit->setText("/usr/bin;/opt");
|
||||
searchDirsLineEdit->setToolTip(
|
||||
tr("Select the paths in the Docker image that should be scanned for Kit entries"));
|
||||
tr("Select the paths in the docker image that should be scanned for kit entries."));
|
||||
|
||||
auto searchPaths = [this, searchDirsComboBox, searchDirsLineEdit, dockerDevice] {
|
||||
FilePaths paths;
|
||||
@@ -491,7 +491,7 @@ Tasks DockerDevice::validate() const
|
||||
Tasks result;
|
||||
if (d->m_data.mounts.isEmpty()) {
|
||||
result << Task(Task::Error,
|
||||
tr("The Docker device has not set up shared directories."
|
||||
tr("The docker device has not set up shared directories."
|
||||
"This will not work for building."),
|
||||
{}, -1, {});
|
||||
}
|
||||
@@ -529,7 +529,7 @@ DockerDevice::DockerDevice(const DockerDeviceData &data)
|
||||
Q_UNUSED(env); // TODO: That's the runnable's environment in general. Use it via -e below.
|
||||
updateContainerAccess();
|
||||
if (d->m_container.isEmpty()) {
|
||||
MessageManager::writeDisrupting(tr("Error starting remote shell. No container"));
|
||||
MessageManager::writeDisrupting(tr("Error starting remote shell. No container."));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -910,7 +910,7 @@ void DockerDevicePrivate::startContainer()
|
||||
if (exitCode > 120) {
|
||||
DockerPlugin::setGlobalDaemonState(false);
|
||||
LOG("DOCKER DAEMON NOT RUNNING?");
|
||||
MessageManager::writeFlashing(tr("Docker Daemon appears to be not running. "
|
||||
MessageManager::writeFlashing(tr("Docker daemon appears to be not running. "
|
||||
"Verify daemon is up and running and reset the "
|
||||
"docker daemon on the docker device settings page "
|
||||
"or restart Qt Creator."));
|
||||
@@ -974,7 +974,7 @@ void DockerDevicePrivate::updateFileSystemAccess()
|
||||
|
||||
if (!QFileInfo(m_mergedDir).isReadable()) {
|
||||
MessageManager::writeFlashing(
|
||||
tr("Local read access to Docker container %1 unavailable through directory \"%2\".")
|
||||
tr("Local read access to docker container %1 unavailable through directory \"%2\".")
|
||||
.arg(m_container, m_mergedDir)
|
||||
+ '\n' + tr("Output: \"%1\"").arg(out)
|
||||
+ '\n' + tr("Error: \"%1\"").arg(proc.stdErr()));
|
||||
|
@@ -112,6 +112,11 @@ Client::Client(BaseClientInterface *clientInterface)
|
||||
|
||||
m_tokenSupport.setTokenTypesMap(SemanticTokens::defaultTokenTypesMap());
|
||||
m_tokenSupport.setTokenModifiersMap(SemanticTokens::defaultTokenModifiersMap());
|
||||
|
||||
m_shutdownTimer.setInterval(20 /*seconds*/ * 1000);
|
||||
connect(&m_shutdownTimer, &QTimer::timeout, this, [this] {
|
||||
LanguageClientManager::deleteClient(this);
|
||||
});
|
||||
}
|
||||
|
||||
QString Client::name() const
|
||||
@@ -317,7 +322,6 @@ void Client::initialize()
|
||||
|
||||
// directly send message otherwise the state check of sendContent would fail
|
||||
sendMessage(initRequest.toBaseMessage());
|
||||
m_clientInterface->sendMessage(initRequest.toBaseMessage());
|
||||
m_state = InitializeRequested;
|
||||
}
|
||||
|
||||
@@ -331,6 +335,7 @@ void Client::shutdown()
|
||||
});
|
||||
sendContent(shutdown);
|
||||
m_state = ShutdownRequested;
|
||||
m_shutdownTimer.start();
|
||||
}
|
||||
|
||||
Client::State Client::state() const
|
||||
@@ -364,7 +369,7 @@ void Client::setClientCapabilities(const LanguageServerProtocol::ClientCapabilit
|
||||
void Client::openDocument(TextEditor::TextDocument *document)
|
||||
{
|
||||
using namespace TextEditor;
|
||||
if (!isSupportedDocument(document))
|
||||
if (m_openedDocument.contains(document) || !isSupportedDocument(document))
|
||||
return;
|
||||
|
||||
if (m_state != Initialized) {
|
||||
@@ -372,8 +377,6 @@ void Client::openDocument(TextEditor::TextDocument *document)
|
||||
return;
|
||||
}
|
||||
|
||||
QTC_ASSERT(!m_openedDocument.contains(document), return);
|
||||
|
||||
const FilePath &filePath = document->filePath();
|
||||
const QString method(DidOpenTextDocumentNotification::methodName);
|
||||
if (Utils::optional<bool> registered = m_dynamicCapabilities.isRegistered(method)) {
|
||||
@@ -1622,6 +1625,7 @@ void Client::initializeCallback(const InitializeRequest::Response &initResponse)
|
||||
|
||||
void Client::shutDownCallback(const ShutdownRequest::Response &shutdownResponse)
|
||||
{
|
||||
m_shutdownTimer.stop();
|
||||
QTC_ASSERT(m_state == ShutdownRequested, return);
|
||||
QTC_ASSERT(m_clientInterface, return);
|
||||
optional<ShutdownRequest::Response::Error> errorValue = shutdownResponse.error();
|
||||
@@ -1634,6 +1638,7 @@ void Client::shutDownCallback(const ShutdownRequest::Response &shutdownResponse)
|
||||
sendMessage(ExitNotification().toBaseMessage());
|
||||
qCDebug(LOGLSPCLIENT) << "language server " << m_displayName << " shutdown";
|
||||
m_state = Shutdown;
|
||||
m_shutdownTimer.start();
|
||||
}
|
||||
|
||||
bool Client::sendWorkspceFolderChanges() const
|
||||
|
@@ -316,6 +316,7 @@ private:
|
||||
LogTarget m_logTarget = LogTarget::Ui;
|
||||
bool m_locatorsEnabled = true;
|
||||
bool m_autoRequestCodeActions = true;
|
||||
QTimer m_shutdownTimer;
|
||||
};
|
||||
|
||||
} // namespace LanguageClient
|
||||
|
@@ -232,7 +232,7 @@ void LanguageClientManager::deleteClient(Client *client)
|
||||
QTC_ASSERT(managerInstance, return);
|
||||
QTC_ASSERT(client, return);
|
||||
qCDebug(Log) << "delete client: " << client->name() << client;
|
||||
client->disconnect();
|
||||
client->disconnect(managerInstance);
|
||||
managerInstance->m_clients.removeAll(client);
|
||||
for (QVector<Client *> &clients : managerInstance->m_clientsForSetting)
|
||||
clients.removeAll(client);
|
||||
|
@@ -8,8 +8,10 @@ add_qtc_plugin(McuSupport
|
||||
mcusupportconstants.h
|
||||
mcusupportdevice.cpp mcusupportdevice.h
|
||||
mcusupportoptions.cpp mcusupportoptions.h mcuabstractpackage.h
|
||||
mcukitmanager.cpp mcukitmanager.h
|
||||
mcusupportoptionspage.cpp mcusupportoptionspage.h
|
||||
mcupackage.cpp mcupackage.h
|
||||
mcutarget.cpp mcutarget.h
|
||||
mcusupportplugin.cpp mcusupportplugin.h
|
||||
mcusupportsdk.cpp mcusupportsdk.h
|
||||
mcusupportrunconfiguration.cpp mcusupportrunconfiguration.h
|
||||
|
@@ -58,14 +58,10 @@ public:
|
||||
virtual const QString &environmentVariableName() const = 0;
|
||||
virtual void setAddToPath(bool) = 0;
|
||||
virtual bool addToPath() const = 0;
|
||||
virtual void writeGeneralSettings() const = 0;
|
||||
virtual bool writeToSettings() const = 0;
|
||||
virtual void setRelativePathModifier(const QString &) = 0;
|
||||
virtual void setVersions(const QStringList &) = 0;
|
||||
|
||||
virtual bool automaticKitCreationEnabled() const = 0;
|
||||
virtual void setAutomaticKitCreationEnabled(const bool enabled) = 0;
|
||||
|
||||
virtual QWidget *widget() = 0;
|
||||
|
||||
signals:
|
||||
|
596
src/plugins/mcusupport/mcukitmanager.cpp
Normal file
596
src/plugins/mcusupport/mcukitmanager.cpp
Normal file
@@ -0,0 +1,596 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2020 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
**
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcukitmanager.h"
|
||||
#include "mcusupportoptions.h"
|
||||
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcukitinformation.h"
|
||||
#include "mcupackage.h"
|
||||
#include "mcutarget.h"
|
||||
#include "mcusupportplugin.h"
|
||||
#include "mcusupportsdk.h"
|
||||
|
||||
#include <cmakeprojectmanager/cmakekitinformation.h>
|
||||
#include <cmakeprojectmanager/cmaketoolmanager.h>
|
||||
#include <coreplugin/icore.h>
|
||||
#include <debugger/debuggeritem.h>
|
||||
#include <debugger/debuggeritemmanager.h>
|
||||
#include <debugger/debuggerkitinformation.h>
|
||||
#include <utils/algorithm.h>
|
||||
#include <qtsupport/qtkitinformation.h>
|
||||
#include <qtsupport/qtversionmanager.h>
|
||||
|
||||
#include <QMessageBox>
|
||||
#include <QPushButton>
|
||||
|
||||
using CMakeProjectManager::CMakeConfigItem;
|
||||
using CMakeProjectManager::CMakeConfigurationKitAspect;
|
||||
using namespace ProjectExplorer;
|
||||
using namespace Utils;
|
||||
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
namespace McuKitManager {
|
||||
|
||||
static const int KIT_VERSION = 9; // Bumps up whenever details in Kit creation change
|
||||
|
||||
static FilePath qulDocsDir()
|
||||
{
|
||||
const FilePath qulDir = McuSupportOptions::qulDirFromSettings();
|
||||
if (qulDir.isEmpty() || !qulDir.exists())
|
||||
return {};
|
||||
const FilePath docsDir = qulDir.pathAppended("docs");
|
||||
return docsDir.exists() ? docsDir : FilePath();
|
||||
}
|
||||
|
||||
static void setKitToolchains(Kit *k, const McuToolChainPackage *tcPackage)
|
||||
{
|
||||
switch (tcPackage->type()) {
|
||||
case McuToolChainPackage::Type::Unsupported:
|
||||
return;
|
||||
|
||||
case McuToolChainPackage::Type::GHS:
|
||||
case McuToolChainPackage::Type::GHSArm:
|
||||
return; // No Green Hills toolchain, because support for it is missing.
|
||||
|
||||
case McuToolChainPackage::Type::IAR:
|
||||
case McuToolChainPackage::Type::KEIL:
|
||||
case McuToolChainPackage::Type::MSVC:
|
||||
case McuToolChainPackage::Type::GCC:
|
||||
case McuToolChainPackage::Type::ArmGcc:
|
||||
ToolChainKitAspect::setToolChain(k,
|
||||
tcPackage->toolChain(
|
||||
ProjectExplorer::Constants::C_LANGUAGE_ID));
|
||||
ToolChainKitAspect::setToolChain(k,
|
||||
tcPackage->toolChain(
|
||||
ProjectExplorer::Constants::CXX_LANGUAGE_ID));
|
||||
return;
|
||||
|
||||
default:
|
||||
Q_UNREACHABLE();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void setKitProperties(const QString &kitName,
|
||||
Kit *k,
|
||||
const McuTarget *mcuTarget,
|
||||
const FilePath &sdkPath)
|
||||
{
|
||||
using namespace Constants;
|
||||
|
||||
k->setUnexpandedDisplayName(kitName);
|
||||
k->setValue(KIT_MCUTARGET_VENDOR_KEY, mcuTarget->platform().vendor);
|
||||
k->setValue(KIT_MCUTARGET_MODEL_KEY, mcuTarget->platform().name);
|
||||
k->setValue(KIT_MCUTARGET_COLORDEPTH_KEY, mcuTarget->colorDepth());
|
||||
k->setValue(KIT_MCUTARGET_SDKVERSION_KEY, mcuTarget->qulVersion().toString());
|
||||
k->setValue(KIT_MCUTARGET_KITVERSION_KEY, KIT_VERSION);
|
||||
k->setValue(KIT_MCUTARGET_OS_KEY, static_cast<int>(mcuTarget->os()));
|
||||
k->setValue(KIT_MCUTARGET_TOOCHAIN_KEY, mcuTarget->toolChainPackage()->toolChainName());
|
||||
k->setAutoDetected(false);
|
||||
k->makeSticky();
|
||||
if (mcuTarget->toolChainPackage()->isDesktopToolchain())
|
||||
k->setDeviceTypeForIcon(DEVICE_TYPE);
|
||||
k->setValue(QtSupport::SuppliesQtQuickImportPath::id(), true);
|
||||
k->setValue(QtSupport::KitQmlImportPath::id(), sdkPath.pathAppended("include/qul").toVariant());
|
||||
k->setValue(QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id(), true);
|
||||
QSet<Id> irrelevant = {
|
||||
SysRootKitAspect::id(),
|
||||
QtSupport::SuppliesQtQuickImportPath::id(),
|
||||
QtSupport::KitQmlImportPath::id(),
|
||||
QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id(),
|
||||
};
|
||||
if (!McuSupportOptions::kitsNeedQtVersion())
|
||||
irrelevant.insert(QtSupport::QtKitAspect::id());
|
||||
k->setIrrelevantAspects(irrelevant);
|
||||
}
|
||||
|
||||
|
||||
static void setKitDebugger(Kit *k, const McuToolChainPackage *tcPackage)
|
||||
{
|
||||
if (tcPackage->isDesktopToolchain()) {
|
||||
// Qt Creator seems to be smart enough to deduce the right Kit debugger from the ToolChain
|
||||
return;
|
||||
}
|
||||
|
||||
switch (tcPackage->type()) {
|
||||
case McuToolChainPackage::Type::Unsupported:
|
||||
case McuToolChainPackage::Type::GHS:
|
||||
case McuToolChainPackage::Type::GHSArm:
|
||||
case McuToolChainPackage::Type::IAR:
|
||||
return; // No Green Hills and IAR debugger, because support for it is missing.
|
||||
|
||||
case McuToolChainPackage::Type::KEIL:
|
||||
case McuToolChainPackage::Type::MSVC:
|
||||
case McuToolChainPackage::Type::GCC:
|
||||
case McuToolChainPackage::Type::ArmGcc: {
|
||||
const QVariant debuggerId = tcPackage->debuggerId();
|
||||
if (debuggerId.isValid()) {
|
||||
Debugger::DebuggerKitAspect::setDebugger(k, debuggerId);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
default:
|
||||
Q_UNREACHABLE();
|
||||
}
|
||||
}
|
||||
|
||||
static void setKitDevice(Kit *k, const McuTarget *mcuTarget)
|
||||
{
|
||||
// "Device Type" Desktop is the default. We use that for the Qt for MCUs Desktop Kit
|
||||
if (mcuTarget->toolChainPackage()->isDesktopToolchain())
|
||||
return;
|
||||
|
||||
DeviceTypeKitAspect::setDeviceTypeId(k, Constants::DEVICE_TYPE);
|
||||
}
|
||||
|
||||
static bool expectsCmakeVars(const McuTarget *mcuTarget)
|
||||
{
|
||||
return mcuTarget->qulVersion() >= QVersionNumber{2, 0};
|
||||
}
|
||||
|
||||
static void setKitDependencies(Kit *k,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
NameValueItems dependencies;
|
||||
|
||||
auto processPackage = [&dependencies](const McuAbstractPackage *package) {
|
||||
if (!package->environmentVariableName().isEmpty())
|
||||
dependencies.append({package->environmentVariableName(),
|
||||
QDir::toNativeSeparators(package->detectionPath())});
|
||||
};
|
||||
for (auto package : mcuTarget->packages())
|
||||
processPackage(package);
|
||||
processPackage(qtForMCUsSdkPackage);
|
||||
|
||||
McuDependenciesKitAspect::setDependencies(k, dependencies);
|
||||
|
||||
auto irrelevant = k->irrelevantAspects();
|
||||
irrelevant.insert(McuDependenciesKitAspect::id());
|
||||
k->setIrrelevantAspects(irrelevant);
|
||||
}
|
||||
|
||||
static void setKitCMakeOptions(Kit *k, const McuTarget *mcuTarget, const FilePath &qulDir)
|
||||
{
|
||||
using namespace CMakeProjectManager;
|
||||
|
||||
CMakeConfig config = CMakeConfigurationKitAspect::configuration(k);
|
||||
// CMake ToolChain file for ghs handles CMAKE_*_COMPILER autonomously
|
||||
if (mcuTarget->toolChainPackage()->type() != McuToolChainPackage::Type::GHS
|
||||
&& mcuTarget->toolChainPackage()->type() != McuToolChainPackage::Type::GHSArm) {
|
||||
config.append(CMakeConfigItem("CMAKE_CXX_COMPILER", "%{Compiler:Executable:Cxx}"));
|
||||
config.append(CMakeConfigItem("CMAKE_C_COMPILER", "%{Compiler:Executable:C}"));
|
||||
}
|
||||
|
||||
if (!mcuTarget->toolChainPackage()->isDesktopToolchain()) {
|
||||
const FilePath cMakeToolchainFile = qulDir.pathAppended(
|
||||
"lib/cmake/Qul/toolchain/" + mcuTarget->toolChainPackage()->cmakeToolChainFileName());
|
||||
|
||||
config.append(
|
||||
CMakeConfigItem("CMAKE_TOOLCHAIN_FILE", cMakeToolchainFile.toString().toUtf8()));
|
||||
if (!cMakeToolchainFile.exists()) {
|
||||
printMessage(McuTarget::tr(
|
||||
"Warning for target %1: missing CMake toolchain file expected at %2.")
|
||||
.arg(kitName(mcuTarget),
|
||||
cMakeToolchainFile.toUserOutput()),
|
||||
false);
|
||||
}
|
||||
}
|
||||
|
||||
const FilePath generatorsPath = qulDir.pathAppended("/lib/cmake/Qul/QulGenerators.cmake");
|
||||
config.append(CMakeConfigItem("QUL_GENERATORS", generatorsPath.toString().toUtf8()));
|
||||
if (!generatorsPath.exists()) {
|
||||
printMessage(McuTarget::tr("Warning for target %1: missing QulGenerators expected at %2.")
|
||||
.arg(kitName(mcuTarget), generatorsPath.toUserOutput()),
|
||||
false);
|
||||
}
|
||||
|
||||
config.append(CMakeConfigItem("QUL_PLATFORM", mcuTarget->platform().name.toUtf8()));
|
||||
|
||||
if (mcuTarget->colorDepth() != McuTarget::UnspecifiedColorDepth)
|
||||
config.append(CMakeConfigItem("QUL_COLOR_DEPTH",
|
||||
QString::number(mcuTarget->colorDepth()).toLatin1()));
|
||||
if (McuSupportOptions::kitsNeedQtVersion())
|
||||
config.append(CMakeConfigItem("CMAKE_PREFIX_PATH", "%{Qt:QT_INSTALL_PREFIX}"));
|
||||
CMakeConfigurationKitAspect::setConfiguration(k, config);
|
||||
|
||||
if (HostOsInfo::isWindowsHost()) {
|
||||
auto type = mcuTarget->toolChainPackage()->type();
|
||||
if (type == McuToolChainPackage::Type::GHS || type == McuToolChainPackage::Type::GHSArm) {
|
||||
// See https://bugreports.qt.io/browse/UL-4247?focusedCommentId=565802&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-565802
|
||||
// and https://bugreports.qt.io/browse/UL-4247?focusedCommentId=565803&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-565803
|
||||
CMakeGeneratorKitAspect::setGenerator(k, "NMake Makefiles JOM");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void setKitQtVersionOptions(Kit *k)
|
||||
{
|
||||
if (!McuSupportOptions::kitsNeedQtVersion())
|
||||
QtSupport::QtKitAspect::setQtVersion(k, nullptr);
|
||||
// else: auto-select a Qt version
|
||||
}
|
||||
|
||||
QString kitName(const McuTarget *mcuTarget)
|
||||
{
|
||||
const McuToolChainPackage *tcPkg = mcuTarget->toolChainPackage();
|
||||
const QString compilerName = tcPkg && !tcPkg->isDesktopToolchain()
|
||||
? QString::fromLatin1(" (%1)").arg(
|
||||
tcPkg->toolChainName().toUpper())
|
||||
: "";
|
||||
const QString colorDepth = mcuTarget->colorDepth() != McuTarget::UnspecifiedColorDepth
|
||||
? QString::fromLatin1(" %1bpp").arg(mcuTarget->colorDepth())
|
||||
: "";
|
||||
const QString targetName = mcuTarget->platform().displayName.isEmpty()
|
||||
? mcuTarget->platform().name
|
||||
: mcuTarget->platform().displayName;
|
||||
return QString::fromLatin1("Qt for MCUs %1.%2 - %3%4%5")
|
||||
.arg(QString::number(mcuTarget->qulVersion().majorVersion()),
|
||||
QString::number(mcuTarget->qulVersion().minorVersion()),
|
||||
targetName,
|
||||
colorDepth,
|
||||
compilerName);
|
||||
}
|
||||
|
||||
QList<Kit *> existingKits(const McuTarget *mcuTarget)
|
||||
{
|
||||
using namespace Constants;
|
||||
return Utils::filtered(KitManager::kits(), [mcuTarget](Kit *kit) {
|
||||
return kit->value(KIT_MCUTARGET_KITVERSION_KEY) == KIT_VERSION
|
||||
&& (!mcuTarget
|
||||
|| (kit->value(KIT_MCUTARGET_VENDOR_KEY) == mcuTarget->platform().vendor
|
||||
&& kit->value(KIT_MCUTARGET_MODEL_KEY) == mcuTarget->platform().name
|
||||
&& kit->value(KIT_MCUTARGET_COLORDEPTH_KEY) == mcuTarget->colorDepth()
|
||||
&& kit->value(KIT_MCUTARGET_OS_KEY).toInt()
|
||||
== static_cast<int>(mcuTarget->os())
|
||||
&& kit->value(KIT_MCUTARGET_TOOCHAIN_KEY)
|
||||
== mcuTarget->toolChainPackage()->toolChainName()));
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> matchingKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget, qtForMCUsSdkPackage](Kit *kit) {
|
||||
return kitIsUpToDate(kit, mcuTarget, qtForMCUsSdkPackage);
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> upgradeableKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget, qtForMCUsSdkPackage](Kit *kit) {
|
||||
return !kitIsUpToDate(kit, mcuTarget, qtForMCUsSdkPackage);
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> kitsWithMismatchedDependencies(const McuTarget *mcuTarget)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget](Kit *kit) {
|
||||
const auto environment = Utils::NameValueDictionary(
|
||||
Utils::NameValueItem::toStringList(EnvironmentKitAspect::environmentChanges(kit)));
|
||||
return Utils::anyOf(mcuTarget->packages(),
|
||||
[&environment](const McuAbstractPackage *package) {
|
||||
return !package->environmentVariableName().isEmpty()
|
||||
&& environment.value(package->environmentVariableName())
|
||||
!= package->path().toUserOutput();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> outdatedKits()
|
||||
{
|
||||
return Utils::filtered(KitManager::kits(), [](Kit *kit) {
|
||||
return !kit->value(Constants::KIT_MCUTARGET_VENDOR_KEY).isNull()
|
||||
&& kit->value(Constants::KIT_MCUTARGET_KITVERSION_KEY) != KIT_VERSION;
|
||||
});
|
||||
}
|
||||
|
||||
void removeOutdatedKits()
|
||||
{
|
||||
for (auto kit : outdatedKits())
|
||||
KitManager::deregisterKit(kit);
|
||||
}
|
||||
|
||||
Kit *newKit(const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdk)
|
||||
{
|
||||
const auto init = [mcuTarget, qtForMCUsSdk](Kit *k) {
|
||||
KitGuard kitGuard(k);
|
||||
|
||||
setKitProperties(kitName(mcuTarget), k, mcuTarget, qtForMCUsSdk->path());
|
||||
setKitDevice(k, mcuTarget);
|
||||
setKitToolchains(k, mcuTarget->toolChainPackage());
|
||||
setKitDebugger(k, mcuTarget->toolChainPackage());
|
||||
McuSupportOptions::setKitEnvironment(k, mcuTarget, qtForMCUsSdk);
|
||||
setKitDependencies(k, mcuTarget, qtForMCUsSdk);
|
||||
setKitCMakeOptions(k, mcuTarget, qtForMCUsSdk->path());
|
||||
setKitQtVersionOptions(k);
|
||||
|
||||
k->setup();
|
||||
k->fix();
|
||||
};
|
||||
|
||||
return KitManager::registerKit(init);
|
||||
}
|
||||
|
||||
QVersionNumber kitQulVersion(const Kit *kit)
|
||||
{
|
||||
return QVersionNumber::fromString(
|
||||
kit->value(McuSupport::Constants::KIT_MCUTARGET_SDKVERSION_KEY).toString());
|
||||
}
|
||||
|
||||
static FilePath kitDependencyPath(const Kit *kit, const QString &variableName)
|
||||
{
|
||||
for (const NameValueItem &nameValueItem : EnvironmentKitAspect::environmentChanges(kit)) {
|
||||
if (nameValueItem.name == variableName)
|
||||
return FilePath::fromUserInput(nameValueItem.value);
|
||||
}
|
||||
return FilePath();
|
||||
}
|
||||
|
||||
bool kitIsUpToDate(const Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return kitQulVersion(kit) == mcuTarget->qulVersion()
|
||||
&& kitDependencyPath(kit, qtForMCUsSdkPackage->environmentVariableName()).toUserOutput()
|
||||
== qtForMCUsSdkPackage->path().toUserOutput();
|
||||
}
|
||||
|
||||
void createAutomaticKits()
|
||||
{
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
const auto createKits = [qtForMCUsPackage]() {
|
||||
if (McuSupportOptions::automaticKitCreationFromSettings()) {
|
||||
qtForMCUsPackage->updateStatus();
|
||||
if (!qtForMCUsPackage->validStatus()) {
|
||||
switch (qtForMCUsPackage->status()) {
|
||||
case McuAbstractPackage::Status::ValidPathInvalidPackage: {
|
||||
const QString displayPath
|
||||
= FilePath::fromString(qtForMCUsPackage->detectionPath()).toUserOutput();
|
||||
printMessage(McuPackage::tr("Path %1 exists, but does not contain %2.")
|
||||
.arg(qtForMCUsPackage->path().toUserOutput(), displayPath),
|
||||
true);
|
||||
break;
|
||||
}
|
||||
case McuAbstractPackage::Status::InvalidPath: {
|
||||
printMessage(McuPackage::tr("Path %1 does not exist. Add the path in Tools > Options > "
|
||||
"Devices > MCU.")
|
||||
.arg(qtForMCUsPackage->path().toUserOutput()),
|
||||
true);
|
||||
break;
|
||||
}
|
||||
case McuAbstractPackage::Status::EmptyPath: {
|
||||
printMessage(McuPackage::tr("Missing %1. Add the path in Tools > Options > Devices > MCU.")
|
||||
.arg(qtForMCUsPackage->detectionPath()),
|
||||
true);
|
||||
return;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (CMakeProjectManager::CMakeToolManager::cmakeTools().isEmpty()) {
|
||||
printMessage(McuPackage::tr("No CMake tool was detected. Add a CMake tool in Tools > Options > "
|
||||
"Kits > CMake."),
|
||||
true);
|
||||
return;
|
||||
}
|
||||
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
|
||||
bool needsUpgrade = false;
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
// if kit already exists, skip
|
||||
if (!matchingKits(target, qtForMCUsPackage).empty())
|
||||
continue;
|
||||
if (!upgradeableKits(target, qtForMCUsPackage).empty()) {
|
||||
// if kit exists but wrong version/path
|
||||
needsUpgrade = true;
|
||||
} else {
|
||||
// if no kits for this target, create
|
||||
if (target->isValid())
|
||||
newKit(target, qtForMCUsPackage);
|
||||
target->printPackageProblems();
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
|
||||
if (needsUpgrade)
|
||||
McuSupportPlugin::askUserAboutMcuSupportKitsUpgrade();
|
||||
}
|
||||
};
|
||||
|
||||
createKits();
|
||||
delete qtForMCUsPackage;
|
||||
}
|
||||
|
||||
void upgradeKitsByCreatingNewPackage(UpgradeOption upgradeOption)
|
||||
{
|
||||
if (upgradeOption == UpgradeOption::Ignore)
|
||||
return;
|
||||
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
auto dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
if (!matchingKits(target, qtForMCUsPackage).empty())
|
||||
// already up-to-date
|
||||
continue;
|
||||
|
||||
const auto kits = upgradeableKits(target, qtForMCUsPackage);
|
||||
if (!kits.empty()) {
|
||||
if (upgradeOption == UpgradeOption::Replace) {
|
||||
for (auto existingKit : kits)
|
||||
KitManager::deregisterKit(existingKit);
|
||||
}
|
||||
|
||||
if (target->isValid())
|
||||
newKit(target, qtForMCUsPackage);
|
||||
target->printPackageProblems();
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
delete qtForMCUsPackage;
|
||||
}
|
||||
|
||||
void upgradeKitInPlace(ProjectExplorer::Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdk)
|
||||
{
|
||||
setKitProperties(kitName(mcuTarget), kit, mcuTarget, qtForMCUsSdk->path());
|
||||
McuSupportOptions::setKitEnvironment(kit, mcuTarget, qtForMCUsSdk);
|
||||
setKitDependencies(kit, mcuTarget, qtForMCUsSdk);
|
||||
}
|
||||
|
||||
void fixKitsDependencies()
|
||||
{
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
if (target->isValid()) {
|
||||
for (auto *kit : kitsWithMismatchedDependencies(target)) {
|
||||
McuSupportOptions::updateKitEnvironment(kit, target);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
delete qtForMCUsPackage;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fix/update existing kits if needed
|
||||
*/
|
||||
void fixExistingKits()
|
||||
{
|
||||
for (Kit *kit : KitManager::kits()) {
|
||||
if (!kit->hasValue(Constants::KIT_MCUTARGET_KITVERSION_KEY))
|
||||
continue;
|
||||
|
||||
if (kit->isAutoDetected()) {
|
||||
kit->setAutoDetected(false);
|
||||
}
|
||||
|
||||
// Check if the MCU kits are flagged as supplying a QtQuick import path, in order
|
||||
// to tell the QMLJS code-model that it won't need to add a fall-back import
|
||||
// path.
|
||||
const auto bringsQtQuickImportPath = QtSupport::SuppliesQtQuickImportPath::id();
|
||||
auto irrelevantAspects = kit->irrelevantAspects();
|
||||
if (!irrelevantAspects.contains(bringsQtQuickImportPath)) {
|
||||
irrelevantAspects.insert(bringsQtQuickImportPath);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->hasValue(bringsQtQuickImportPath)) {
|
||||
kit->setValue(bringsQtQuickImportPath, true);
|
||||
}
|
||||
|
||||
// Check if the MCU kit supplies its import path.
|
||||
const auto kitQmlImportPath = QtSupport::KitQmlImportPath::id();
|
||||
if (!irrelevantAspects.contains(kitQmlImportPath)) {
|
||||
irrelevantAspects.insert(kitQmlImportPath);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->hasValue(kitQmlImportPath)) {
|
||||
auto config = CMakeProjectManager::CMakeConfigurationKitAspect::configuration(kit);
|
||||
for (const auto &cfgItem : qAsConst(config)) {
|
||||
if (cfgItem.key == "QUL_GENERATORS") {
|
||||
auto idx = cfgItem.value.indexOf("/lib/cmake/Qul");
|
||||
auto qulDir = cfgItem.value.left(idx);
|
||||
kit->setValue(kitQmlImportPath, QVariant(qulDir + "/include/qul"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check if the MCU kit has the flag for merged header/qml-import paths set.
|
||||
const auto mergedPaths = QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id();
|
||||
if (!irrelevantAspects.contains(mergedPaths)) {
|
||||
irrelevantAspects.insert(mergedPaths);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->value(mergedPaths, false).toBool()) {
|
||||
kit->setValue(mergedPaths, true);
|
||||
}
|
||||
}
|
||||
|
||||
// Fix kit dependencies for known targets
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
qtForMCUsPackage->updateStatus();
|
||||
if (qtForMCUsPackage->validStatus()) {
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
for (const auto &target : qAsConst(repo.mcuTargets))
|
||||
for (auto kit : existingKits(target)) {
|
||||
if (McuDependenciesKitAspect::dependencies(kit).isEmpty()) {
|
||||
setKitDependencies(kit, target, qtForMCUsPackage);
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
}
|
||||
delete qtForMCUsPackage;
|
||||
}
|
||||
|
||||
} // namespace McuKitManager
|
||||
} // namespace Internal
|
||||
} // namespace McuSupport
|
86
src/plugins/mcusupport/mcukitmanager.h
Normal file
86
src/plugins/mcusupport/mcukitmanager.h
Normal file
@@ -0,0 +1,86 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
**
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <utils/environmentfwd.h>
|
||||
#include "mcusupport_global.h"
|
||||
|
||||
#include <QCoreApplication>
|
||||
#include <QObject>
|
||||
#include <QVector>
|
||||
#include <QVersionNumber>
|
||||
|
||||
namespace ProjectExplorer {
|
||||
class Kit;
|
||||
} // namespace ProjectExplorer
|
||||
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
class McuAbstractPackage;
|
||||
class McuToolChainPackage;
|
||||
class McuTarget;
|
||||
|
||||
namespace McuKitManager
|
||||
{
|
||||
enum class UpgradeOption {
|
||||
Ignore,
|
||||
Keep,
|
||||
Replace
|
||||
};
|
||||
|
||||
// Creating kits:
|
||||
ProjectExplorer::Kit *newKit(const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdk);
|
||||
void createAutomaticKits();
|
||||
|
||||
// Querying the kits:
|
||||
QList<ProjectExplorer::Kit *> existingKits(const McuTarget *mcuTarget);
|
||||
QList<ProjectExplorer::Kit *> matchingKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
QList<ProjectExplorer::Kit *> upgradeableKits(
|
||||
const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
QList<ProjectExplorer::Kit *> kitsWithMismatchedDependencies(const McuTarget *mcuTarget);
|
||||
|
||||
// Upgrading kits:
|
||||
void upgradeKitsByCreatingNewPackage(UpgradeOption upgradeOption);
|
||||
void upgradeKitInPlace(ProjectExplorer::Kit *kit, const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdk);
|
||||
|
||||
// Fixing kits:
|
||||
void fixKitsDependencies();
|
||||
void fixExistingKits();
|
||||
|
||||
// Outdated kits:
|
||||
QList<ProjectExplorer::Kit *> outdatedKits();
|
||||
void removeOutdatedKits();
|
||||
|
||||
// Querying kits:
|
||||
QString kitName(const McuTarget* mcuTarget);
|
||||
QVersionNumber kitQulVersion(const ProjectExplorer::Kit *kit);
|
||||
bool kitIsUpToDate(const ProjectExplorer::Kit *kit, const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
|
||||
} // namespace McuKitManager
|
||||
} // namespace Internal
|
||||
} // namespace McuSupport
|
@@ -1,6 +1,6 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2020 The Qt Company Ltd.
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
@@ -25,6 +25,7 @@
|
||||
|
||||
#include "mcupackage.h"
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcusupportversiondetection.h"
|
||||
#include "mcusupportsdk.h"
|
||||
|
||||
#include <coreplugin/icore.h>
|
||||
@@ -40,15 +41,6 @@ using namespace Utils;
|
||||
|
||||
namespace McuSupport::Internal {
|
||||
|
||||
static bool automaticKitCreationFromSettings(QSettings::Scope scope = QSettings::UserScope)
|
||||
{
|
||||
QSettings *settings = Core::ICore::settings(scope);
|
||||
const QString key = QLatin1String(Constants::SETTINGS_GROUP) + '/'
|
||||
+ QLatin1String(Constants::SETTINGS_KEY_AUTOMATIC_KIT_CREATION);
|
||||
bool automaticKitCreation = settings->value(key, true).toBool();
|
||||
return automaticKitCreation;
|
||||
}
|
||||
|
||||
McuPackage::McuPackage(const QString &label,
|
||||
const FilePath &defaultPath,
|
||||
const QString &detectionPath,
|
||||
@@ -65,7 +57,6 @@ McuPackage::McuPackage(const QString &label,
|
||||
, m_downloadUrl(downloadUrl)
|
||||
{
|
||||
m_path = Sdk::packagePathFromSettings(settingsKey, QSettings::UserScope, m_defaultPath);
|
||||
m_automaticKitCreation = automaticKitCreationFromSettings(QSettings::UserScope);
|
||||
}
|
||||
|
||||
FilePath McuPackage::basePath() const
|
||||
@@ -161,14 +152,6 @@ bool McuPackage::addToPath() const
|
||||
return m_addToPath;
|
||||
}
|
||||
|
||||
void McuPackage::writeGeneralSettings() const
|
||||
{
|
||||
const QString key = QLatin1String(Constants::SETTINGS_GROUP) + '/'
|
||||
+ QLatin1String(Constants::SETTINGS_KEY_AUTOMATIC_KIT_CREATION);
|
||||
QSettings *settings = Core::ICore::settings();
|
||||
settings->setValue(key, m_automaticKitCreation);
|
||||
}
|
||||
|
||||
bool McuPackage::writeToSettings() const
|
||||
{
|
||||
const FilePath savedPath = Sdk::packagePathFromSettings(m_settingsKey,
|
||||
@@ -191,16 +174,6 @@ void McuPackage::setVersions(const QStringList &versions)
|
||||
m_versions = versions;
|
||||
}
|
||||
|
||||
bool McuPackage::automaticKitCreationEnabled() const
|
||||
{
|
||||
return m_automaticKitCreation;
|
||||
}
|
||||
|
||||
void McuPackage::setAutomaticKitCreationEnabled(const bool enabled)
|
||||
{
|
||||
m_automaticKitCreation = enabled;
|
||||
}
|
||||
|
||||
void McuPackage::updatePath()
|
||||
{
|
||||
m_path = m_fileChooser->rawFilePath();
|
||||
@@ -269,9 +242,10 @@ QString McuPackage::statusText() const
|
||||
.arg(displayPackagePath, displayDetectedPath);
|
||||
break;
|
||||
case Status::ValidPackageMismatchedVersion: {
|
||||
const QString versionWarning = m_versions.size() == 1 ?
|
||||
tr("but only version %1 is supported").arg(m_versions.first()) :
|
||||
tr("but only versions %1 are supported").arg(displayVersions);
|
||||
const QString versionWarning
|
||||
= m_versions.size() == 1
|
||||
? tr("but only version %1 is supported").arg(m_versions.first())
|
||||
: tr("but only versions %1 are supported").arg(displayVersions);
|
||||
response = tr("Path %1 is valid, %2 was found, %3.")
|
||||
.arg(displayPackagePath, displayDetectedPath, versionWarning);
|
||||
break;
|
||||
@@ -313,4 +287,5 @@ bool McuToolChainPackage::isDesktopToolchain() const
|
||||
return m_type == Type::MSVC || m_type == Type::GCC;
|
||||
}
|
||||
|
||||
|
||||
} // namespace McuSupport::Internal
|
||||
|
@@ -1,6 +1,6 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2020 The Qt Company Ltd.
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
@@ -26,10 +26,8 @@
|
||||
#pragma once
|
||||
|
||||
#include "mcuabstractpackage.h"
|
||||
#include "mcusupportversiondetection.h"
|
||||
|
||||
#include <utils/filepath.h>
|
||||
#include <utils/id.h>
|
||||
|
||||
#include <QObject>
|
||||
|
||||
@@ -42,11 +40,14 @@ class ToolChain;
|
||||
namespace Utils {
|
||||
class PathChooser;
|
||||
class InfoLabel;
|
||||
class Id;
|
||||
} // namespace Utils
|
||||
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
class McuPackageVersionDetector;
|
||||
|
||||
class McuPackage : public McuAbstractPackage
|
||||
{
|
||||
Q_OBJECT
|
||||
@@ -73,23 +74,14 @@ public:
|
||||
bool validStatus() const override;
|
||||
void setAddToPath(bool addToPath) override;
|
||||
bool addToPath() const override;
|
||||
void writeGeneralSettings() const override;
|
||||
bool writeToSettings() const override;
|
||||
void setRelativePathModifier(const QString &path) override;
|
||||
void setVersions(const QStringList &versions) override;
|
||||
|
||||
//TODO(piotr.mucko): Why every package knows about automatic kit creation. This should be outside of this class.
|
||||
bool automaticKitCreationEnabled() const override;
|
||||
void setAutomaticKitCreationEnabled(const bool enabled) override;
|
||||
|
||||
QWidget *widget() override;
|
||||
|
||||
const QString &environmentVariableName() const override;
|
||||
|
||||
signals:
|
||||
void changed();
|
||||
void statusChanged();
|
||||
|
||||
private:
|
||||
void updatePath();
|
||||
void updateStatusUi();
|
||||
@@ -111,7 +103,6 @@ private:
|
||||
const QString m_environmentVariableName;
|
||||
const QString m_downloadUrl;
|
||||
bool m_addToPath = false;
|
||||
bool m_automaticKitCreation = true;
|
||||
|
||||
Status m_status = Status::InvalidPath;
|
||||
};
|
||||
|
@@ -18,6 +18,8 @@ QtcPlugin {
|
||||
"mcuabstractpackage.h",
|
||||
"mcupackage.cpp",
|
||||
"mcupackage.h",
|
||||
"mcutarget.cpp",
|
||||
"mcutarget.h",
|
||||
"mcusupport.qrc",
|
||||
"mcusupport_global.h",
|
||||
"mcusupportconstants.h",
|
||||
@@ -25,6 +27,8 @@ QtcPlugin {
|
||||
"mcusupportdevice.h",
|
||||
"mcusupportoptions.cpp",
|
||||
"mcusupportoptions.h",
|
||||
"mcukitmanager.cpp",
|
||||
"mcukitmanager.h",
|
||||
"mcusupportoptionspage.cpp",
|
||||
"mcusupportoptionspage.h",
|
||||
"mcusupportplugin.cpp",
|
||||
|
@@ -24,47 +24,27 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcusupportoptions.h"
|
||||
#include "mcukitinformation.h"
|
||||
|
||||
#include "mcupackage.h"
|
||||
#include "mcutarget.h"
|
||||
#include "mcukitmanager.h"
|
||||
#include "mcukitinformation.h"
|
||||
#include "mcusupportcmakemapper.h"
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcusupportplugin.h"
|
||||
#include "mcusupportsdk.h"
|
||||
#include "mcusupportplugin.h"
|
||||
|
||||
#include <baremetal/baremetalconstants.h>
|
||||
#include <cmakeprojectmanager/cmakekitinformation.h>
|
||||
#include <cmakeprojectmanager/cmaketoolmanager.h>
|
||||
#include <coreplugin/helpmanager.h>
|
||||
#include <coreplugin/icore.h>
|
||||
#include <coreplugin/messagemanager.h>
|
||||
#include <debugger/debuggeritem.h>
|
||||
#include <debugger/debuggeritemmanager.h>
|
||||
#include <debugger/debuggerkitinformation.h>
|
||||
#include <projectexplorer/abi.h>
|
||||
#include <projectexplorer/devicesupport/devicemanager.h>
|
||||
#include <projectexplorer/kitinformation.h>
|
||||
#include <projectexplorer/kitmanager.h>
|
||||
#include <projectexplorer/projectexplorerconstants.h>
|
||||
#include <projectexplorer/toolchain.h>
|
||||
#include <projectexplorer/toolchainmanager.h>
|
||||
#include <utils/algorithm.h>
|
||||
#include <utils/fileutils.h>
|
||||
#include <utils/infolabel.h>
|
||||
#include <utils/pathchooser.h>
|
||||
#include <utils/qtcassert.h>
|
||||
#include <utils/utilsicons.h>
|
||||
#include <qtsupport/qtkitinformation.h>
|
||||
#include <qtsupport/qtversionmanager.h>
|
||||
|
||||
#include <QDesktopServices>
|
||||
#include <QDir>
|
||||
#include <QFileInfo>
|
||||
#include <QLabel>
|
||||
#include <QMessageBox>
|
||||
#include <QPushButton>
|
||||
#include <QToolButton>
|
||||
#include <QVBoxLayout>
|
||||
#include <QVariant>
|
||||
|
||||
using CMakeProjectManager::CMakeConfigItem;
|
||||
using CMakeProjectManager::CMakeConfigurationKitAspect;
|
||||
@@ -74,263 +54,6 @@ using namespace Utils;
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
static const int KIT_VERSION = 9; // Bumps up whenever details in Kit creation change
|
||||
|
||||
static bool kitNeedsQtVersion()
|
||||
{
|
||||
// Only on Windows, Qt is linked into the distributed qul Desktop libs. Also, the host tools
|
||||
// are missing the Qt runtime libraries on non-Windows.
|
||||
return !HostOsInfo::isWindowsHost();
|
||||
}
|
||||
|
||||
static ToolChain *msvcToolChain(Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
const Abi abi = t->targetAbi();
|
||||
// TODO: Should Abi::WindowsMsvc2022Flavor be added too?
|
||||
return (abi.osFlavor() == Abi::WindowsMsvc2017Flavor
|
||||
|| abi.osFlavor() == Abi::WindowsMsvc2019Flavor)
|
||||
&& abi.architecture() == Abi::X86Architecture && abi.wordWidth() == 64
|
||||
&& t->language() == language;
|
||||
});
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *gccToolChain(Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
const Abi abi = t->targetAbi();
|
||||
return abi.os() != Abi::WindowsOS && abi.architecture() == Abi::X86Architecture
|
||||
&& abi.wordWidth() == 64 && t->language() == language;
|
||||
});
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *armGccToolChain(const FilePath &path, Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([&path, language](const ToolChain *t) {
|
||||
return t->compilerCommand() == path && t->language() == language;
|
||||
});
|
||||
if (!toolChain) {
|
||||
ToolChainFactory *gccFactory
|
||||
= Utils::findOrDefault(ToolChainFactory::allToolChainFactories(),
|
||||
[](ToolChainFactory *f) {
|
||||
return f->supportedToolChainType()
|
||||
== ProjectExplorer::Constants::GCC_TOOLCHAIN_TYPEID;
|
||||
});
|
||||
if (gccFactory) {
|
||||
const QList<ToolChain *> detected = gccFactory->detectForImport({path, language});
|
||||
if (!detected.isEmpty()) {
|
||||
toolChain = detected.first();
|
||||
toolChain->setDetection(ToolChain::ManualDetection);
|
||||
toolChain->setDisplayName("Arm GCC");
|
||||
ToolChainManager::registerToolChain(toolChain);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *iarToolChain(const FilePath &path, Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
return t->typeId() == BareMetal::Constants::IAREW_TOOLCHAIN_TYPEID
|
||||
&& t->language() == language;
|
||||
});
|
||||
if (!toolChain) {
|
||||
ToolChainFactory *iarFactory
|
||||
= Utils::findOrDefault(ToolChainFactory::allToolChainFactories(),
|
||||
[](ToolChainFactory *f) {
|
||||
return f->supportedToolChainType()
|
||||
== BareMetal::Constants::IAREW_TOOLCHAIN_TYPEID;
|
||||
});
|
||||
if (iarFactory) {
|
||||
Toolchains detected = iarFactory->autoDetect(ToolchainDetector({}, {}));
|
||||
if (detected.isEmpty())
|
||||
detected = iarFactory->detectForImport({path, language});
|
||||
for (auto tc : detected) {
|
||||
if (tc->language() == language) {
|
||||
toolChain = tc;
|
||||
toolChain->setDetection(ToolChain::ManualDetection);
|
||||
toolChain->setDisplayName("IAREW");
|
||||
ToolChainManager::registerToolChain(toolChain);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
ToolChain *McuToolChainPackage::toolChain(Id language) const
|
||||
{
|
||||
switch (m_type) {
|
||||
case Type::MSVC:
|
||||
return msvcToolChain(language);
|
||||
case Type::GCC:
|
||||
return gccToolChain(language);
|
||||
case Type::IAR: {
|
||||
const FilePath compiler = path().pathAppended("/bin/iccarm").withExecutableSuffix();
|
||||
return iarToolChain(compiler, language);
|
||||
}
|
||||
case Type::ArmGcc:
|
||||
case Type::KEIL:
|
||||
case Type::GHS:
|
||||
case Type::GHSArm:
|
||||
case Type::Unsupported: {
|
||||
const QLatin1String compilerName(
|
||||
language == ProjectExplorer::Constants::C_LANGUAGE_ID ? "gcc" : "g++");
|
||||
const QString comp = QLatin1String(m_type == Type::ArmGcc ? "/bin/arm-none-eabi-%1"
|
||||
: "/bar/foo-keil-%1")
|
||||
.arg(compilerName);
|
||||
const FilePath compiler = path().pathAppended(comp).withExecutableSuffix();
|
||||
|
||||
return armGccToolChain(compiler, language);
|
||||
}
|
||||
default:
|
||||
Q_UNREACHABLE();
|
||||
}
|
||||
}
|
||||
|
||||
QString McuToolChainPackage::toolChainName() const
|
||||
{
|
||||
switch (m_type) {
|
||||
case Type::ArmGcc:
|
||||
return QLatin1String("armgcc");
|
||||
case Type::IAR:
|
||||
return QLatin1String("iar");
|
||||
case Type::KEIL:
|
||||
return QLatin1String("keil");
|
||||
case Type::GHS:
|
||||
return QLatin1String("ghs");
|
||||
case Type::GHSArm:
|
||||
return QLatin1String("ghs-arm");
|
||||
default:
|
||||
return QLatin1String("unsupported");
|
||||
}
|
||||
}
|
||||
|
||||
QString McuToolChainPackage::cmakeToolChainFileName() const
|
||||
{
|
||||
return toolChainName() + QLatin1String(".cmake");
|
||||
}
|
||||
|
||||
QVariant McuToolChainPackage::debuggerId() const
|
||||
{
|
||||
using namespace Debugger;
|
||||
|
||||
QString sub, displayName;
|
||||
DebuggerEngineType engineType;
|
||||
|
||||
switch (m_type) {
|
||||
case Type::ArmGcc: {
|
||||
sub = QString::fromLatin1("bin/arm-none-eabi-gdb-py");
|
||||
displayName = McuPackage::tr("Arm GDB at %1");
|
||||
engineType = Debugger::GdbEngineType;
|
||||
break;
|
||||
}
|
||||
case Type::IAR: {
|
||||
sub = QString::fromLatin1("../common/bin/CSpyBat");
|
||||
displayName = QLatin1String("CSpy");
|
||||
engineType = Debugger::NoEngineType; // support for IAR missing
|
||||
break;
|
||||
}
|
||||
case Type::KEIL: {
|
||||
sub = QString::fromLatin1("UV4/UV4");
|
||||
displayName = QLatin1String("KEIL uVision Debugger");
|
||||
engineType = Debugger::UvscEngineType;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
const FilePath command = path().pathAppended(sub).withExecutableSuffix();
|
||||
if (const DebuggerItem *debugger = DebuggerItemManager::findByCommand(command)) {
|
||||
return debugger->id();
|
||||
}
|
||||
|
||||
DebuggerItem newDebugger;
|
||||
newDebugger.setCommand(command);
|
||||
newDebugger.setUnexpandedDisplayName(displayName.arg(command.toUserOutput()));
|
||||
newDebugger.setEngineType(engineType);
|
||||
return DebuggerItemManager::registerDebugger(newDebugger);
|
||||
}
|
||||
|
||||
McuTarget::McuTarget(const QVersionNumber &qulVersion,
|
||||
const Platform &platform,
|
||||
OS os,
|
||||
const QVector<McuAbstractPackage *> &packages,
|
||||
const McuToolChainPackage *toolChainPackage,
|
||||
int colorDepth)
|
||||
: m_qulVersion(qulVersion)
|
||||
, m_platform(platform)
|
||||
, m_os(os)
|
||||
, m_packages(packages)
|
||||
, m_toolChainPackage(toolChainPackage)
|
||||
, m_colorDepth(colorDepth)
|
||||
{}
|
||||
|
||||
const QVector<McuAbstractPackage *> &McuTarget::packages() const
|
||||
{
|
||||
return m_packages;
|
||||
}
|
||||
|
||||
const McuToolChainPackage *McuTarget::toolChainPackage() const
|
||||
{
|
||||
return m_toolChainPackage;
|
||||
}
|
||||
|
||||
McuTarget::OS McuTarget::os() const
|
||||
{
|
||||
return m_os;
|
||||
}
|
||||
|
||||
const McuTarget::Platform &McuTarget::platform() const
|
||||
{
|
||||
return m_platform;
|
||||
}
|
||||
|
||||
bool McuTarget::isValid() const
|
||||
{
|
||||
return Utils::allOf(packages(), [](McuAbstractPackage *package) {
|
||||
package->updateStatus();
|
||||
return package->validStatus();
|
||||
});
|
||||
}
|
||||
|
||||
void McuTarget::printPackageProblems() const
|
||||
{
|
||||
for (auto package : packages()) {
|
||||
package->updateStatus();
|
||||
if (!package->validStatus()) {
|
||||
printMessage(tr("Error creating kit for target %1, package %2: %3")
|
||||
.arg(McuSupportOptions::kitName(this),
|
||||
package->label(),
|
||||
package->statusText()),
|
||||
true);
|
||||
}
|
||||
if (package->status() == McuAbstractPackage::Status::ValidPackageMismatchedVersion) {
|
||||
printMessage(tr("Warning creating kit for target %1, package %2: %3")
|
||||
.arg(McuSupportOptions::kitName(this),
|
||||
package->label(),
|
||||
package->statusText()),
|
||||
false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const QVersionNumber &McuTarget::qulVersion() const
|
||||
{
|
||||
return m_qulVersion;
|
||||
}
|
||||
|
||||
int McuTarget::colorDepth() const
|
||||
{
|
||||
return m_colorDepth;
|
||||
}
|
||||
|
||||
void McuSdkRepository::deletePackagesAndTargets()
|
||||
{
|
||||
qDeleteAll(packages);
|
||||
@@ -347,6 +70,7 @@ McuSupportOptions::McuSupportOptions(QObject *parent)
|
||||
&McuAbstractPackage::changed,
|
||||
this,
|
||||
&McuSupportOptions::populatePackagesAndTargets);
|
||||
m_automaticKitCreation = automaticKitCreationFromSettings();
|
||||
}
|
||||
|
||||
McuSupportOptions::~McuSupportOptions()
|
||||
@@ -402,7 +126,7 @@ void McuSupportOptions::registerExamples()
|
||||
|
||||
const QVersionNumber &McuSupportOptions::minimalQulVersion()
|
||||
{
|
||||
static const QVersionNumber v({1, 3});
|
||||
static const QVersionNumber v({2, 0});
|
||||
return v;
|
||||
}
|
||||
|
||||
@@ -413,48 +137,16 @@ void McuSupportOptions::setQulDir(const FilePath &dir)
|
||||
if (qtForMCUsSdkPackage->validStatus())
|
||||
Sdk::targetsAndPackages(dir, &sdkRepository);
|
||||
for (const auto &package : qAsConst(sdkRepository.packages))
|
||||
connect(package, &McuAbstractPackage::changed, this, &McuSupportOptions::changed);
|
||||
connect(package, &McuAbstractPackage::changed, this, &McuSupportOptions::packagesChanged);
|
||||
|
||||
emit changed();
|
||||
emit packagesChanged();
|
||||
}
|
||||
|
||||
FilePath McuSupportOptions::qulDirFromSettings()
|
||||
{
|
||||
return Sdk::packagePathFromSettings(Constants::SETTINGS_KEY_PACKAGE_QT_FOR_MCUS_SDK,
|
||||
QSettings::UserScope);
|
||||
}
|
||||
|
||||
static void setKitProperties(const QString &kitName,
|
||||
Kit *k,
|
||||
const McuTarget *mcuTarget,
|
||||
const FilePath &sdkPath)
|
||||
{
|
||||
using namespace Constants;
|
||||
|
||||
k->setUnexpandedDisplayName(kitName);
|
||||
k->setValue(KIT_MCUTARGET_VENDOR_KEY, mcuTarget->platform().vendor);
|
||||
k->setValue(KIT_MCUTARGET_MODEL_KEY, mcuTarget->platform().name);
|
||||
k->setValue(KIT_MCUTARGET_COLORDEPTH_KEY, mcuTarget->colorDepth());
|
||||
k->setValue(KIT_MCUTARGET_SDKVERSION_KEY, mcuTarget->qulVersion().toString());
|
||||
k->setValue(KIT_MCUTARGET_KITVERSION_KEY, KIT_VERSION);
|
||||
k->setValue(KIT_MCUTARGET_OS_KEY, static_cast<int>(mcuTarget->os()));
|
||||
k->setValue(KIT_MCUTARGET_TOOCHAIN_KEY, mcuTarget->toolChainPackage()->toolChainName());
|
||||
k->setAutoDetected(false);
|
||||
k->makeSticky();
|
||||
if (mcuTarget->toolChainPackage()->isDesktopToolchain())
|
||||
k->setDeviceTypeForIcon(DEVICE_TYPE);
|
||||
k->setValue(QtSupport::SuppliesQtQuickImportPath::id(), true);
|
||||
k->setValue(QtSupport::KitQmlImportPath::id(), sdkPath.pathAppended("include/qul").toVariant());
|
||||
k->setValue(QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id(), true);
|
||||
QSet<Id> irrelevant = {
|
||||
SysRootKitAspect::id(),
|
||||
QtSupport::SuppliesQtQuickImportPath::id(),
|
||||
QtSupport::KitQmlImportPath::id(),
|
||||
QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id(),
|
||||
};
|
||||
if (!kitNeedsQtVersion())
|
||||
irrelevant.insert(QtSupport::QtKitAspect::id());
|
||||
k->setIrrelevantAspects(irrelevant);
|
||||
QSettings::UserScope,
|
||||
{});
|
||||
}
|
||||
|
||||
void McuSupportOptions::remapQul2xCmakeVars(Kit *kit, const EnvironmentItems &envItems)
|
||||
@@ -472,7 +164,6 @@ void McuSupportOptions::remapQul2xCmakeVars(Kit *kit, const EnvironmentItems &en
|
||||
CMakeConfigurationKitAspect::setConfiguration(kit, config);
|
||||
}
|
||||
|
||||
|
||||
static void setKitToolchains(Kit *k, const McuToolChainPackage *tcPackage)
|
||||
{
|
||||
switch (tcPackage->type()) {
|
||||
@@ -569,15 +260,7 @@ void McuSupportOptions::setKitEnvironment(Kit *k,
|
||||
processPackage(package);
|
||||
processPackage(qtForMCUsSdkPackage);
|
||||
|
||||
// Clang not needed in version 1.7+
|
||||
if (mcuTarget->qulVersion() < QVersionNumber{1, 7}) {
|
||||
const QString path = QLatin1String(HostOsInfo::isWindowsHost() ? "Path" : "PATH");
|
||||
pathAdditions.append("${" + path + "}");
|
||||
pathAdditions.append(Core::ICore::libexecPath("clang/bin").toUserOutput());
|
||||
changes.append({path, pathAdditions.join(HostOsInfo::pathListSeparator())});
|
||||
}
|
||||
|
||||
if (kitNeedsQtVersion())
|
||||
if (McuSupportOptions::kitsNeedQtVersion())
|
||||
changes.append({QLatin1String("LD_LIBRARY_PATH"), "%{Qt:QT_INSTALL_LIBS}"});
|
||||
|
||||
// Hack, this problem should be solved in lower layer
|
||||
@@ -657,7 +340,7 @@ static void setKitCMakeOptions(Kit *k, const McuTarget *mcuTarget, const FilePat
|
||||
if (!cMakeToolchainFile.exists()) {
|
||||
printMessage(McuTarget::tr(
|
||||
"Warning for target %1: missing CMake toolchain file expected at %2.")
|
||||
.arg(McuSupportOptions::kitName(mcuTarget),
|
||||
.arg(McuKitManager::kitName(mcuTarget),
|
||||
cMakeToolchainFile.toUserOutput()),
|
||||
false);
|
||||
}
|
||||
@@ -667,19 +350,16 @@ static void setKitCMakeOptions(Kit *k, const McuTarget *mcuTarget, const FilePat
|
||||
config.append(CMakeConfigItem("QUL_GENERATORS", generatorsPath.toString().toUtf8()));
|
||||
if (!generatorsPath.exists()) {
|
||||
printMessage(McuTarget::tr("Warning for target %1: missing QulGenerators expected at %2.")
|
||||
.arg(McuSupportOptions::kitName(mcuTarget), generatorsPath.toUserOutput()),
|
||||
.arg(McuKitManager::kitName(mcuTarget), generatorsPath.toUserOutput()),
|
||||
false);
|
||||
}
|
||||
|
||||
config.append(CMakeConfigItem("QUL_PLATFORM", mcuTarget->platform().name.toUtf8()));
|
||||
|
||||
if (mcuTarget->qulVersion() <= QVersionNumber{1, 3} // OS variable was removed in Qul 1.4
|
||||
&& mcuTarget->os() == McuTarget::OS::FreeRTOS)
|
||||
config.append(CMakeConfigItem("OS", "FreeRTOS"));
|
||||
if (mcuTarget->colorDepth() != McuTarget::UnspecifiedColorDepth)
|
||||
config.append(CMakeConfigItem("QUL_COLOR_DEPTH",
|
||||
QString::number(mcuTarget->colorDepth()).toLatin1()));
|
||||
if (kitNeedsQtVersion())
|
||||
if (McuSupportOptions::kitsNeedQtVersion())
|
||||
config.append(CMakeConfigItem("CMAKE_PREFIX_PATH", "%{Qt:QT_INSTALL_PREFIX}"));
|
||||
CMakeConfigurationKitAspect::setConfiguration(k, config);
|
||||
|
||||
@@ -695,134 +375,11 @@ static void setKitCMakeOptions(Kit *k, const McuTarget *mcuTarget, const FilePat
|
||||
|
||||
static void setKitQtVersionOptions(Kit *k)
|
||||
{
|
||||
if (!kitNeedsQtVersion())
|
||||
if (!McuSupportOptions::kitsNeedQtVersion())
|
||||
QtSupport::QtKitAspect::setQtVersion(k, nullptr);
|
||||
// else: auto-select a Qt version
|
||||
}
|
||||
|
||||
QString McuSupportOptions::kitName(const McuTarget *mcuTarget)
|
||||
{
|
||||
QString os;
|
||||
if (mcuTarget->qulVersion() <= QVersionNumber{1, 3}
|
||||
&& mcuTarget->os() == McuTarget::OS::FreeRTOS)
|
||||
// Starting from Qul 1.4 each OS is a separate platform
|
||||
os = QLatin1String(" FreeRTOS");
|
||||
|
||||
const McuToolChainPackage *tcPkg = mcuTarget->toolChainPackage();
|
||||
const QString compilerName = tcPkg && !tcPkg->isDesktopToolchain()
|
||||
? QString::fromLatin1(" (%1)").arg(
|
||||
tcPkg->toolChainName().toUpper())
|
||||
: "";
|
||||
const QString colorDepth = mcuTarget->colorDepth() != McuTarget::UnspecifiedColorDepth
|
||||
? QString::fromLatin1(" %1bpp").arg(mcuTarget->colorDepth())
|
||||
: "";
|
||||
const QString targetName = mcuTarget->platform().displayName.isEmpty()
|
||||
? mcuTarget->platform().name
|
||||
: mcuTarget->platform().displayName;
|
||||
return QString::fromLatin1("Qt for MCUs %1.%2 - %3%4%5%6")
|
||||
.arg(QString::number(mcuTarget->qulVersion().majorVersion()),
|
||||
QString::number(mcuTarget->qulVersion().minorVersion()),
|
||||
targetName,
|
||||
os,
|
||||
colorDepth,
|
||||
compilerName);
|
||||
}
|
||||
|
||||
QList<Kit *> McuSupportOptions::existingKits(const McuTarget *mcuTarget)
|
||||
{
|
||||
using namespace Constants;
|
||||
return Utils::filtered(KitManager::kits(), [mcuTarget](Kit *kit) {
|
||||
return kit->value(KIT_MCUTARGET_KITVERSION_KEY) == KIT_VERSION
|
||||
&& (!mcuTarget
|
||||
|| (kit->value(KIT_MCUTARGET_VENDOR_KEY) == mcuTarget->platform().vendor
|
||||
&& kit->value(KIT_MCUTARGET_MODEL_KEY) == mcuTarget->platform().name
|
||||
&& kit->value(KIT_MCUTARGET_COLORDEPTH_KEY) == mcuTarget->colorDepth()
|
||||
&& kit->value(KIT_MCUTARGET_OS_KEY).toInt()
|
||||
== static_cast<int>(mcuTarget->os())
|
||||
&& kit->value(KIT_MCUTARGET_TOOCHAIN_KEY)
|
||||
== mcuTarget->toolChainPackage()->toolChainName()));
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> McuSupportOptions::matchingKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget, qtForMCUsSdkPackage](Kit *kit) {
|
||||
return kitUpToDate(kit, mcuTarget, qtForMCUsSdkPackage);
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> McuSupportOptions::upgradeableKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget, qtForMCUsSdkPackage](Kit *kit) {
|
||||
return !kitUpToDate(kit, mcuTarget, qtForMCUsSdkPackage);
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> McuSupportOptions::kitsWithMismatchedDependencies(const McuTarget *mcuTarget)
|
||||
{
|
||||
return Utils::filtered(existingKits(mcuTarget), [mcuTarget](Kit *kit) {
|
||||
const auto environment = Utils::NameValueDictionary(
|
||||
Utils::NameValueItem::toStringList(EnvironmentKitAspect::environmentChanges(kit)));
|
||||
return Utils::anyOf(mcuTarget->packages(), [&environment](const McuAbstractPackage *package) {
|
||||
return !package->environmentVariableName().isEmpty() &&
|
||||
environment.value(package->environmentVariableName()) != package->path().toUserOutput();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
QList<Kit *> McuSupportOptions::outdatedKits()
|
||||
{
|
||||
return Utils::filtered(KitManager::kits(), [](Kit *kit) {
|
||||
return !kit->value(Constants::KIT_MCUTARGET_VENDOR_KEY).isNull()
|
||||
&& kit->value(Constants::KIT_MCUTARGET_KITVERSION_KEY) != KIT_VERSION;
|
||||
});
|
||||
}
|
||||
|
||||
void McuSupportOptions::removeOutdatedKits()
|
||||
{
|
||||
for (auto kit : McuSupportOptions::outdatedKits())
|
||||
KitManager::deregisterKit(kit);
|
||||
}
|
||||
|
||||
Kit *McuSupportOptions::newKit(const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdk)
|
||||
{
|
||||
const auto init = [mcuTarget, qtForMCUsSdk](Kit *k) {
|
||||
KitGuard kitGuard(k);
|
||||
|
||||
setKitProperties(kitName(mcuTarget), k, mcuTarget, qtForMCUsSdk->path());
|
||||
setKitDevice(k, mcuTarget);
|
||||
setKitToolchains(k, mcuTarget->toolChainPackage());
|
||||
setKitDebugger(k, mcuTarget->toolChainPackage());
|
||||
setKitEnvironment(k, mcuTarget, qtForMCUsSdk);
|
||||
setKitDependencies(k, mcuTarget, qtForMCUsSdk);
|
||||
setKitCMakeOptions(k, mcuTarget, qtForMCUsSdk->path());
|
||||
setKitQtVersionOptions(k);
|
||||
|
||||
k->setup();
|
||||
k->fix();
|
||||
};
|
||||
|
||||
return KitManager::registerKit(init);
|
||||
}
|
||||
|
||||
void printMessage(const QString &message, bool important)
|
||||
{
|
||||
const QString displayMessage = QCoreApplication::translate("QtForMCUs", "Qt for MCUs: %1")
|
||||
.arg(message);
|
||||
if (important)
|
||||
Core::MessageManager::writeFlashing(displayMessage);
|
||||
else
|
||||
Core::MessageManager::writeSilently(displayMessage);
|
||||
}
|
||||
|
||||
QVersionNumber McuSupportOptions::kitQulVersion(const Kit *kit)
|
||||
{
|
||||
return QVersionNumber::fromString(
|
||||
kit->value(McuSupport::Constants::KIT_MCUTARGET_SDKVERSION_KEY).toString());
|
||||
}
|
||||
|
||||
static FilePath kitDependencyPath(const Kit *kit, const QString &variableName)
|
||||
{
|
||||
for (const NameValueItem &nameValueItem : EnvironmentKitAspect::environmentChanges(kit)) {
|
||||
@@ -832,21 +389,7 @@ static FilePath kitDependencyPath(const Kit *kit, const QString &variableName)
|
||||
return FilePath();
|
||||
}
|
||||
|
||||
bool McuSupportOptions::kitUpToDate(const Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage)
|
||||
{
|
||||
return kitQulVersion(kit) == mcuTarget->qulVersion()
|
||||
&& kitDependencyPath(kit, qtForMCUsSdkPackage->environmentVariableName()).toUserOutput()
|
||||
== qtForMCUsSdkPackage->path().toUserOutput();
|
||||
}
|
||||
|
||||
void McuSupportOptions::deletePackagesAndTargets()
|
||||
{
|
||||
sdkRepository.deletePackagesAndTargets();
|
||||
}
|
||||
|
||||
McuSupportOptions::UpgradeOption McuSupportOptions::askForKitUpgrades()
|
||||
McuKitManager::UpgradeOption McuSupportOptions::askForKitUpgrades()
|
||||
{
|
||||
QMessageBox upgradePopup(Core::ICore::dialogParent());
|
||||
upgradePopup.setStandardButtons(QMessageBox::Cancel);
|
||||
@@ -859,86 +402,17 @@ McuSupportOptions::UpgradeOption McuSupportOptions::askForKitUpgrades()
|
||||
upgradePopup.exec();
|
||||
|
||||
if (upgradePopup.clickedButton() == keepButton)
|
||||
return Keep;
|
||||
return McuKitManager::UpgradeOption::Keep;
|
||||
|
||||
if (upgradePopup.clickedButton() == replaceButton)
|
||||
return Replace;
|
||||
return McuKitManager::UpgradeOption::Replace;
|
||||
|
||||
return Ignore;
|
||||
return McuKitManager::UpgradeOption::Ignore;
|
||||
}
|
||||
|
||||
void McuSupportOptions::createAutomaticKits()
|
||||
void McuSupportOptions::deletePackagesAndTargets()
|
||||
{
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
const auto createKits = [qtForMCUsPackage]() {
|
||||
if (qtForMCUsPackage->automaticKitCreationEnabled()) {
|
||||
qtForMCUsPackage->updateStatus();
|
||||
if (!qtForMCUsPackage->validStatus()) {
|
||||
switch (qtForMCUsPackage->status()) {
|
||||
case McuAbstractPackage::Status::ValidPathInvalidPackage: {
|
||||
const QString displayPath = FilePath::fromString(qtForMCUsPackage->detectionPath())
|
||||
.toUserOutput();
|
||||
printMessage(tr("Path %1 exists, but does not contain %2.")
|
||||
.arg(qtForMCUsPackage->path().toUserOutput(), displayPath),
|
||||
true);
|
||||
break;
|
||||
}
|
||||
case McuAbstractPackage::Status::InvalidPath: {
|
||||
printMessage(tr("Path %1 does not exist. Add the path in Tools > Options > "
|
||||
"Devices > MCU.")
|
||||
.arg(qtForMCUsPackage->path().toUserOutput()),
|
||||
true);
|
||||
break;
|
||||
}
|
||||
case McuAbstractPackage::Status::EmptyPath: {
|
||||
printMessage(tr("Missing %1. Add the path in Tools > Options > Devices > MCU.")
|
||||
.arg(qtForMCUsPackage->detectionPath()),
|
||||
true);
|
||||
return;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (CMakeProjectManager::CMakeToolManager::cmakeTools().isEmpty()) {
|
||||
printMessage(tr("No CMake tool was detected. Add a CMake tool in Tools > Options > "
|
||||
"Kits > CMake."),
|
||||
true);
|
||||
return;
|
||||
}
|
||||
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
|
||||
bool needsUpgrade = false;
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
// if kit already exists, skip
|
||||
if (!matchingKits(target, qtForMCUsPackage).empty())
|
||||
continue;
|
||||
if (!upgradeableKits(target, qtForMCUsPackage).empty()) {
|
||||
// if kit exists but wrong version/path
|
||||
needsUpgrade = true;
|
||||
} else {
|
||||
// if no kits for this target, create
|
||||
if (target->isValid())
|
||||
newKit(target, qtForMCUsPackage);
|
||||
target->printPackageProblems();
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
|
||||
if (needsUpgrade)
|
||||
McuSupportPlugin::askUserAboutMcuSupportKitsUpgrade();
|
||||
}
|
||||
};
|
||||
|
||||
createKits();
|
||||
delete qtForMCUsPackage;
|
||||
sdkRepository.deletePackagesAndTargets();
|
||||
}
|
||||
|
||||
void McuSupportOptions::checkUpgradeableKits()
|
||||
@@ -947,144 +421,44 @@ void McuSupportOptions::checkUpgradeableKits()
|
||||
return;
|
||||
|
||||
if (Utils::anyOf(sdkRepository.mcuTargets, [this](const McuTarget *target) {
|
||||
return !upgradeableKits(target, this->qtForMCUsSdkPackage).empty()
|
||||
&& matchingKits(target, this->qtForMCUsSdkPackage).empty();
|
||||
return !McuKitManager::upgradeableKits(target, this->qtForMCUsSdkPackage).empty()
|
||||
&& McuKitManager::matchingKits(target, this->qtForMCUsSdkPackage).empty();
|
||||
}))
|
||||
upgradeKits(askForKitUpgrades());
|
||||
McuKitManager::upgradeKitsByCreatingNewPackage(askForKitUpgrades());
|
||||
}
|
||||
|
||||
void McuSupportOptions::upgradeKits(UpgradeOption upgradeOption)
|
||||
bool McuSupportOptions::kitsNeedQtVersion()
|
||||
{
|
||||
if (upgradeOption == Ignore)
|
||||
return;
|
||||
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
auto dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
if (!matchingKits(target, qtForMCUsPackage).empty())
|
||||
// already up-to-date
|
||||
continue;
|
||||
|
||||
const auto kits = upgradeableKits(target, qtForMCUsPackage);
|
||||
if (!kits.empty()) {
|
||||
if (upgradeOption == Replace)
|
||||
for (auto existingKit : kits)
|
||||
KitManager::deregisterKit(existingKit);
|
||||
|
||||
if (target->isValid())
|
||||
newKit(target, qtForMCUsPackage);
|
||||
target->printPackageProblems();
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
delete qtForMCUsPackage;
|
||||
// Only on Windows, Qt is linked into the distributed qul Desktop libs. Also, the host tools
|
||||
// are missing the Qt runtime libraries on non-Windows.
|
||||
return !HostOsInfo::isWindowsHost();
|
||||
}
|
||||
|
||||
void McuSupportOptions::upgradeKitInPlace(ProjectExplorer::Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdk)
|
||||
bool McuSupportOptions::automaticKitCreationEnabled() const
|
||||
{
|
||||
setKitProperties(kitName(mcuTarget), kit, mcuTarget, qtForMCUsSdk->path());
|
||||
setKitEnvironment(kit, mcuTarget, qtForMCUsSdk);
|
||||
setKitDependencies(kit, mcuTarget, qtForMCUsSdk);
|
||||
return m_automaticKitCreation;
|
||||
}
|
||||
|
||||
void McuSupportOptions::fixKitsDependencies()
|
||||
void McuSupportOptions::setAutomaticKitCreationEnabled(const bool enabled)
|
||||
{
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
for (const auto &target : qAsConst(repo.mcuTargets)) {
|
||||
if (target->isValid()) {
|
||||
for (auto* kit : kitsWithMismatchedDependencies(target)) {
|
||||
updateKitEnvironment(kit, target);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
delete qtForMCUsPackage;
|
||||
m_automaticKitCreation = enabled;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fix/update existing kits if needed
|
||||
*/
|
||||
void McuSupportOptions::fixExistingKits()
|
||||
void McuSupportOptions::writeGeneralSettings() const
|
||||
{
|
||||
for (Kit *kit : KitManager::kits()) {
|
||||
if (!kit->hasValue(Constants::KIT_MCUTARGET_KITVERSION_KEY))
|
||||
continue;
|
||||
const QString key = QLatin1String(Constants::SETTINGS_GROUP) + '/'
|
||||
+ QLatin1String(Constants::SETTINGS_KEY_AUTOMATIC_KIT_CREATION);
|
||||
QSettings *settings = Core::ICore::settings(QSettings::UserScope);
|
||||
settings->setValue(key, m_automaticKitCreation);
|
||||
}
|
||||
|
||||
if (kit->isAutoDetected()) {
|
||||
kit->setAutoDetected(false);
|
||||
}
|
||||
|
||||
// Check if the MCU kits are flagged as supplying a QtQuick import path, in order
|
||||
// to tell the QMLJS code-model that it won't need to add a fall-back import
|
||||
// path.
|
||||
const auto bringsQtQuickImportPath = QtSupport::SuppliesQtQuickImportPath::id();
|
||||
auto irrelevantAspects = kit->irrelevantAspects();
|
||||
if (!irrelevantAspects.contains(bringsQtQuickImportPath)) {
|
||||
irrelevantAspects.insert(bringsQtQuickImportPath);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->hasValue(bringsQtQuickImportPath)) {
|
||||
kit->setValue(bringsQtQuickImportPath, true);
|
||||
}
|
||||
|
||||
// Check if the MCU kit supplies its import path.
|
||||
const auto kitQmlImportPath = QtSupport::KitQmlImportPath::id();
|
||||
if (!irrelevantAspects.contains(kitQmlImportPath)) {
|
||||
irrelevantAspects.insert(kitQmlImportPath);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->hasValue(kitQmlImportPath)) {
|
||||
auto config = CMakeProjectManager::CMakeConfigurationKitAspect::configuration(kit);
|
||||
for (const auto &cfgItem : qAsConst(config)) {
|
||||
if (cfgItem.key == "QUL_GENERATORS") {
|
||||
auto idx = cfgItem.value.indexOf("/lib/cmake/Qul");
|
||||
auto qulDir = cfgItem.value.left(idx);
|
||||
kit->setValue(kitQmlImportPath, QVariant(qulDir + "/include/qul"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check if the MCU kit has the flag for merged header/qml-import paths set.
|
||||
const auto mergedPaths = QtSupport::KitHasMergedHeaderPathsWithQmlImportPaths::id();
|
||||
if (!irrelevantAspects.contains(mergedPaths)) {
|
||||
irrelevantAspects.insert(mergedPaths);
|
||||
kit->setIrrelevantAspects(irrelevantAspects);
|
||||
}
|
||||
if (!kit->value(mergedPaths, false).toBool()) {
|
||||
kit->setValue(mergedPaths, true);
|
||||
}
|
||||
}
|
||||
|
||||
// Fix kit dependencies for known targets
|
||||
auto qtForMCUsPackage = Sdk::createQtForMCUsPackage();
|
||||
qtForMCUsPackage->updateStatus();
|
||||
if (qtForMCUsPackage->validStatus()) {
|
||||
FilePath dir = qtForMCUsPackage->path();
|
||||
McuSdkRepository repo;
|
||||
Sdk::targetsAndPackages(dir, &repo);
|
||||
for (const auto &target : qAsConst(repo.mcuTargets))
|
||||
for (auto kit : existingKits(target)) {
|
||||
if (McuDependenciesKitAspect::dependencies(kit).isEmpty()) {
|
||||
setKitDependencies(kit, target, qtForMCUsPackage);
|
||||
}
|
||||
}
|
||||
|
||||
repo.deletePackagesAndTargets();
|
||||
}
|
||||
delete qtForMCUsPackage;
|
||||
bool McuSupportOptions::automaticKitCreationFromSettings()
|
||||
{
|
||||
QSettings *settings = Core::ICore::settings(QSettings::UserScope);
|
||||
const QString key = QLatin1String(Constants::SETTINGS_GROUP) + '/'
|
||||
+ QLatin1String(Constants::SETTINGS_KEY_AUTOMATIC_KIT_CREATION);
|
||||
const bool automaticKitCreation = settings->value(key, true).toBool();
|
||||
return automaticKitCreation;
|
||||
}
|
||||
|
||||
} // namespace Internal
|
||||
|
@@ -26,6 +26,9 @@
|
||||
#pragma once
|
||||
|
||||
#include <utils/environmentfwd.h>
|
||||
#include "mcusupport_global.h"
|
||||
#include "mcukitmanager.h"
|
||||
|
||||
#include <QObject>
|
||||
#include <QVector>
|
||||
#include <QVersionNumber>
|
||||
@@ -48,49 +51,7 @@ namespace Internal {
|
||||
|
||||
class McuAbstractPackage;
|
||||
class McuToolChainPackage;
|
||||
|
||||
void printMessage(const QString &message, bool important);
|
||||
|
||||
class McuTarget : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum class OS { Desktop, BareMetal, FreeRTOS };
|
||||
|
||||
struct Platform
|
||||
{
|
||||
QString name;
|
||||
QString displayName;
|
||||
QString vendor;
|
||||
};
|
||||
|
||||
enum { UnspecifiedColorDepth = -1 };
|
||||
|
||||
McuTarget(const QVersionNumber &qulVersion,
|
||||
const Platform &platform,
|
||||
OS os,
|
||||
const QVector<McuAbstractPackage *> &packages,
|
||||
const McuToolChainPackage *toolChainPackage,
|
||||
int colorDepth = UnspecifiedColorDepth);
|
||||
|
||||
const QVersionNumber &qulVersion() const;
|
||||
const QVector<McuAbstractPackage *> &packages() const;
|
||||
const McuToolChainPackage *toolChainPackage() const;
|
||||
const Platform &platform() const;
|
||||
OS os() const;
|
||||
int colorDepth() const;
|
||||
bool isValid() const;
|
||||
void printPackageProblems() const;
|
||||
|
||||
private:
|
||||
const QVersionNumber m_qulVersion;
|
||||
const Platform m_platform;
|
||||
const OS m_os;
|
||||
const QVector<McuAbstractPackage *> m_packages;
|
||||
const McuToolChainPackage *m_toolChainPackage;
|
||||
const int m_colorDepth;
|
||||
}; // class McuTarget
|
||||
class McuTarget;
|
||||
|
||||
class McuSdkRepository
|
||||
{
|
||||
@@ -106,8 +67,6 @@ class McuSupportOptions : public QObject
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum UpgradeOption { Ignore, Keep, Replace };
|
||||
|
||||
explicit McuSupportOptions(QObject *parent = nullptr);
|
||||
~McuSupportOptions() override;
|
||||
|
||||
@@ -115,47 +74,36 @@ public:
|
||||
McuSdkRepository sdkRepository;
|
||||
|
||||
void setQulDir(const Utils::FilePath &dir);
|
||||
static void setKitEnvironment(ProjectExplorer::Kit *, const McuTarget *, const McuAbstractPackage *);
|
||||
static void setKitEnvironment(ProjectExplorer::Kit *,
|
||||
const McuTarget *,
|
||||
const McuAbstractPackage *);
|
||||
static void updateKitEnvironment(ProjectExplorer::Kit *, const McuTarget *);
|
||||
static void remapQul2xCmakeVars(ProjectExplorer::Kit *, const Utils::EnvironmentItems &);
|
||||
static Utils::FilePath qulDirFromSettings();
|
||||
static McuKitManager::UpgradeOption askForKitUpgrades();
|
||||
|
||||
static QString kitName(const McuTarget *mcuTarget);
|
||||
|
||||
static QList<ProjectExplorer::Kit *> existingKits(const McuTarget *mcuTarget);
|
||||
static QList<ProjectExplorer::Kit *> matchingKits(const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
static QList<ProjectExplorer::Kit *> upgradeableKits(const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
static QList<ProjectExplorer::Kit *> kitsWithMismatchedDependencies(const McuTarget *mcuTarget);
|
||||
static QList<ProjectExplorer::Kit *> outdatedKits();
|
||||
static void removeOutdatedKits();
|
||||
static ProjectExplorer::Kit *newKit(const McuTarget *mcuTarget, const McuAbstractPackage *qtForMCUsSdk);
|
||||
static void createAutomaticKits();
|
||||
static UpgradeOption askForKitUpgrades();
|
||||
static void upgradeKits(UpgradeOption upgradeOption);
|
||||
static void upgradeKitInPlace(ProjectExplorer::Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdk);
|
||||
static void fixKitsDependencies();
|
||||
void checkUpgradeableKits();
|
||||
static void fixExistingKits();
|
||||
void populatePackagesAndTargets();
|
||||
static void registerQchFiles();
|
||||
static void registerExamples();
|
||||
|
||||
static const QVersionNumber &minimalQulVersion();
|
||||
|
||||
static QVersionNumber kitQulVersion(const ProjectExplorer::Kit *kit);
|
||||
static bool kitUpToDate(const ProjectExplorer::Kit *kit,
|
||||
const McuTarget *mcuTarget,
|
||||
const McuAbstractPackage *qtForMCUsSdkPackage);
|
||||
void checkUpgradeableKits();
|
||||
void populatePackagesAndTargets();
|
||||
|
||||
static bool kitsNeedQtVersion();
|
||||
|
||||
bool automaticKitCreationEnabled() const;
|
||||
void setAutomaticKitCreationEnabled(const bool enabled);
|
||||
void writeGeneralSettings() const;
|
||||
static bool automaticKitCreationFromSettings();
|
||||
private:
|
||||
void deletePackagesAndTargets();
|
||||
|
||||
bool m_automaticKitCreation = true;
|
||||
signals:
|
||||
void changed();
|
||||
void packagesChanged();
|
||||
};
|
||||
|
||||
|
||||
} // namespace Internal
|
||||
} // namespace McuSupport
|
||||
|
@@ -24,10 +24,12 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcusupportoptionspage.h"
|
||||
#include "mcukitmanager.h"
|
||||
#include "mcupackage.h"
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcusupportoptions.h"
|
||||
#include "mcusupportsdk.h"
|
||||
#include "mcutarget.h"
|
||||
|
||||
#include <cmakeprojectmanager/cmakeprojectconstants.h>
|
||||
#include <cmakeprojectmanager/cmaketoolmanager.h>
|
||||
@@ -121,8 +123,10 @@ McuSupportOptionsWidget::McuSupportOptionsWidget()
|
||||
&QComboBox::currentTextChanged,
|
||||
this,
|
||||
&McuSupportOptionsWidget::showMcuTargetPackages);
|
||||
connect(m_options.qtForMCUsSdkPackage, &McuAbstractPackage::changed,
|
||||
this, &McuSupportOptionsWidget::populateMcuTargetsComboBox);
|
||||
connect(m_options.qtForMCUsSdkPackage,
|
||||
&McuAbstractPackage::changed,
|
||||
this,
|
||||
&McuSupportOptionsWidget::populateMcuTargetsComboBox);
|
||||
}
|
||||
|
||||
{
|
||||
@@ -142,7 +146,7 @@ McuSupportOptionsWidget::McuSupportOptionsWidget()
|
||||
m_kitAutomaticCreationCheckBox = new QCheckBox(
|
||||
tr("Automatically create kits for all available targets on start"));
|
||||
connect(m_kitAutomaticCreationCheckBox, &QCheckBox::stateChanged, this, [this](int state) {
|
||||
m_options.qtForMCUsSdkPackage->setAutomaticKitCreationEnabled(
|
||||
m_options.setAutomaticKitCreationEnabled(
|
||||
state == Qt::CheckState::Checked);
|
||||
});
|
||||
mainLayout->addWidget(m_kitAutomaticCreationCheckBox);
|
||||
@@ -158,16 +162,16 @@ McuSupportOptionsWidget::McuSupportOptionsWidget()
|
||||
m_kitCreationPushButton = new QPushButton(tr("Create Kit"));
|
||||
m_kitCreationPushButton->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
||||
connect(m_kitCreationPushButton, &QPushButton::clicked, this, [this] {
|
||||
McuSupportOptions::newKit(currentMcuTarget(), m_options.qtForMCUsSdkPackage);
|
||||
McuKitManager::newKit(currentMcuTarget(), m_options.qtForMCUsSdkPackage);
|
||||
McuSupportOptions::registerQchFiles();
|
||||
updateStatus();
|
||||
});
|
||||
m_kitUpdatePushButton = new QPushButton(tr("Update Kit"));
|
||||
m_kitUpdatePushButton->setSizePolicy(m_kitCreationPushButton->sizePolicy());
|
||||
connect(m_kitUpdatePushButton, &QPushButton::clicked, this, [this] {
|
||||
for (auto kit : McuSupportOptions::upgradeableKits(currentMcuTarget(),
|
||||
m_options.qtForMCUsSdkPackage))
|
||||
m_options.upgradeKitInPlace(kit, currentMcuTarget(), m_options.qtForMCUsSdkPackage);
|
||||
for (auto kit :
|
||||
McuKitManager::upgradeableKits(currentMcuTarget(), m_options.qtForMCUsSdkPackage))
|
||||
McuKitManager::upgradeKitInPlace(kit, currentMcuTarget(), m_options.qtForMCUsSdkPackage);
|
||||
updateStatus();
|
||||
});
|
||||
vLayout->addWidget(m_kitCreationPushButton);
|
||||
@@ -176,7 +180,10 @@ McuSupportOptionsWidget::McuSupportOptionsWidget()
|
||||
|
||||
mainLayout->addStretch();
|
||||
|
||||
connect(&m_options, &McuSupportOptions::changed, this, &McuSupportOptionsWidget::updateStatus);
|
||||
connect(&m_options,
|
||||
&McuSupportOptions::packagesChanged,
|
||||
this,
|
||||
&McuSupportOptionsWidget::updateStatus);
|
||||
|
||||
showMcuTargetPackages();
|
||||
}
|
||||
@@ -215,12 +222,10 @@ void McuSupportOptionsWidget::updateStatus()
|
||||
m_kitUpdatePushButton->setVisible(mcuTargetValid);
|
||||
if (mcuTargetValid) {
|
||||
const bool hasMatchingKits
|
||||
= !McuSupportOptions::matchingKits(mcuTarget, m_options.qtForMCUsSdkPackage)
|
||||
.isEmpty();
|
||||
const bool hasUpgradeableKits
|
||||
= !hasMatchingKits
|
||||
&& !McuSupportOptions::upgradeableKits(mcuTarget, m_options.qtForMCUsSdkPackage)
|
||||
.isEmpty();
|
||||
= !McuKitManager::matchingKits(mcuTarget, m_options.qtForMCUsSdkPackage).isEmpty();
|
||||
const bool hasUpgradeableKits = !hasMatchingKits &&
|
||||
!McuKitManager::upgradeableKits(
|
||||
mcuTarget, m_options.qtForMCUsSdkPackage).isEmpty();
|
||||
|
||||
m_kitCreationPushButton->setEnabled(!hasMatchingKits);
|
||||
m_kitUpdatePushButton->setEnabled(hasUpgradeableKits);
|
||||
@@ -241,8 +246,7 @@ void McuSupportOptionsWidget::updateStatus()
|
||||
}
|
||||
|
||||
// Automatic Kit creation
|
||||
m_kitAutomaticCreationCheckBox->setChecked(
|
||||
m_options.qtForMCUsSdkPackage->automaticKitCreationEnabled());
|
||||
m_kitAutomaticCreationCheckBox->setChecked(m_options.automaticKitCreationEnabled());
|
||||
|
||||
// Status label in the bottom
|
||||
{
|
||||
@@ -296,14 +300,14 @@ void McuSupportOptionsWidget::apply()
|
||||
{
|
||||
bool pathsChanged = false;
|
||||
|
||||
m_options.qtForMCUsSdkPackage->writeGeneralSettings();
|
||||
m_options.writeGeneralSettings();
|
||||
pathsChanged |= m_options.qtForMCUsSdkPackage->writeToSettings();
|
||||
for (auto package : qAsConst(m_options.sdkRepository.packages))
|
||||
pathsChanged |= package->writeToSettings();
|
||||
|
||||
if (pathsChanged) {
|
||||
m_options.checkUpgradeableKits();
|
||||
m_options.fixKitsDependencies();
|
||||
McuKitManager::fixKitsDependencies();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -313,7 +317,7 @@ void McuSupportOptionsWidget::populateMcuTargetsComboBox()
|
||||
m_mcuTargetsComboBox->clear();
|
||||
m_mcuTargetsComboBox->addItems(
|
||||
Utils::transform<QStringList>(m_options.sdkRepository.mcuTargets,
|
||||
[](McuTarget *t) { return McuSupportOptions::kitName(t); }));
|
||||
[](McuTarget *t) { return McuKitManager::kitName(t); }));
|
||||
updateStatus();
|
||||
}
|
||||
|
||||
|
@@ -28,6 +28,7 @@
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcusupportdevice.h"
|
||||
#include "mcusupportoptions.h"
|
||||
#include "mcukitmanager.h"
|
||||
#include "mcusupportoptionspage.h"
|
||||
#include "mcusupportrunconfiguration.h"
|
||||
|
||||
@@ -38,6 +39,7 @@
|
||||
#include <coreplugin/coreconstants.h>
|
||||
#include <coreplugin/icontext.h>
|
||||
#include <coreplugin/icore.h>
|
||||
#include <coreplugin/messagemanager.h>
|
||||
|
||||
#include <projectexplorer/devicesupport/devicemanager.h>
|
||||
#include <projectexplorer/jsonwizard/jsonwizardfactory.h>
|
||||
@@ -53,6 +55,16 @@ using namespace ProjectExplorer;
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
void printMessage(const QString &message, bool important)
|
||||
{
|
||||
const QString displayMessage = QCoreApplication::translate("QtForMCUs", "Qt for MCUs: %1")
|
||||
.arg(message);
|
||||
if (important)
|
||||
Core::MessageManager::writeFlashing(displayMessage);
|
||||
else
|
||||
Core::MessageManager::writeSilently(displayMessage);
|
||||
}
|
||||
|
||||
class McuSupportPluginPrivate
|
||||
{
|
||||
public:
|
||||
@@ -65,7 +77,7 @@ public:
|
||||
McuDependenciesKitAspect environmentPathsKitAspect;
|
||||
}; // class McuSupportPluginPrivate
|
||||
|
||||
static McuSupportPluginPrivate* dd{nullptr};
|
||||
static McuSupportPluginPrivate *dd{nullptr};
|
||||
|
||||
McuSupportPlugin::~McuSupportPlugin()
|
||||
{
|
||||
@@ -93,9 +105,9 @@ void McuSupportPlugin::extensionsInitialized()
|
||||
ProjectExplorer::DeviceManager::instance()->addDevice(McuSupportDevice::create());
|
||||
|
||||
connect(KitManager::instance(), &KitManager::kitsLoaded, []() {
|
||||
McuSupportOptions::removeOutdatedKits();
|
||||
McuSupportOptions::createAutomaticKits();
|
||||
McuSupportOptions::fixExistingKits();
|
||||
McuKitManager::removeOutdatedKits();
|
||||
McuKitManager::createAutomaticKits();
|
||||
McuKitManager::fixExistingKits();
|
||||
McuSupportPlugin::askUserAboutMcuSupportKitsSetup();
|
||||
});
|
||||
}
|
||||
@@ -106,7 +118,7 @@ void McuSupportPlugin::askUserAboutMcuSupportKitsSetup()
|
||||
|
||||
if (!ICore::infoBar()->canInfoBeAdded(setupMcuSupportKits)
|
||||
|| McuSupportOptions::qulDirFromSettings().isEmpty()
|
||||
|| !McuSupportOptions::existingKits(nullptr).isEmpty())
|
||||
|| !McuKitManager::existingKits(nullptr).isEmpty())
|
||||
return;
|
||||
|
||||
Utils::InfoBarEntry info(setupMcuSupportKits,
|
||||
@@ -130,18 +142,19 @@ void McuSupportPlugin::askUserAboutMcuSupportKitsUpgrade()
|
||||
Utils::InfoBarEntry info(upgradeMcuSupportKits,
|
||||
tr("New version of Qt for MCUs detected. Upgrade existing Kits?"),
|
||||
Utils::InfoBarEntry::GlobalSuppression::Enabled);
|
||||
static McuKitManager::UpgradeOption selectedOption = McuKitManager::UpgradeOption::Keep;
|
||||
|
||||
static McuSupportOptions::UpgradeOption selectedOption;
|
||||
const QStringList options = {tr("Create new kits"), tr("Replace existing kits")};
|
||||
selectedOption = McuSupportOptions::UpgradeOption::Keep;
|
||||
info.setComboInfo(options, [options](const QString &selected) {
|
||||
selectedOption = options.indexOf(selected) == 0 ? McuSupportOptions::UpgradeOption::Keep
|
||||
: McuSupportOptions::UpgradeOption::Replace;
|
||||
selectedOption = options.indexOf(selected) == 0 ? McuKitManager::UpgradeOption::Keep
|
||||
: McuKitManager::UpgradeOption::Replace;
|
||||
});
|
||||
|
||||
info.addCustomButton(tr("Proceed"), [upgradeMcuSupportKits] {
|
||||
ICore::infoBar()->removeInfo(upgradeMcuSupportKits);
|
||||
QTimer::singleShot(0, []() { McuSupportOptions::upgradeKits(selectedOption); });
|
||||
QTimer::singleShot(0, []() {
|
||||
McuKitManager::upgradeKitsByCreatingNewPackage(selectedOption);
|
||||
});
|
||||
});
|
||||
|
||||
ICore::infoBar()->addInfo(info);
|
||||
|
@@ -31,6 +31,8 @@
|
||||
|
||||
namespace McuSupport::Internal {
|
||||
|
||||
void printMessage(const QString &message, bool important);
|
||||
|
||||
class McuSupportPlugin final : public ExtensionSystem::IPlugin
|
||||
{
|
||||
Q_OBJECT
|
||||
|
@@ -24,10 +24,13 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcusupportsdk.h"
|
||||
#include "mcukitmanager.h"
|
||||
#include "mcupackage.h"
|
||||
#include "mcusupportconstants.h"
|
||||
#include "mcusupportoptions.h"
|
||||
#include "mcusupportplugin.h"
|
||||
#include "mcusupportversiondetection.h"
|
||||
#include "mcutarget.h"
|
||||
#include "mcutargetdescription.h"
|
||||
|
||||
#include <baremetal/baremetalconstants.h>
|
||||
@@ -527,10 +530,9 @@ protected:
|
||||
|
||||
QVector<McuTarget *> mcuTargets;
|
||||
McuToolChainPackage *tcPkg = tcPkgs.value(desc.toolchain.id);
|
||||
if (tcPkg) {
|
||||
if (QVersionNumber::fromString(desc.qulVersion) >= QVersionNumber({1, 8}))
|
||||
if (tcPkg)
|
||||
tcPkg->setVersions(desc.toolchain.versions);
|
||||
} else
|
||||
else
|
||||
tcPkg = createUnsupportedToolChainPackage();
|
||||
for (int colorDepth : desc.platform.colorDepths) {
|
||||
QVector<McuAbstractPackage *> required3rdPartyPkgs;
|
||||
@@ -551,7 +553,6 @@ protected:
|
||||
boardSdkPkgs.insert(desc.boardSdk.envVar, boardSdkPkg);
|
||||
}
|
||||
auto boardSdkPkg = boardSdkPkgs.value(desc.boardSdk.envVar);
|
||||
if (QVersionNumber::fromString(desc.qulVersion) >= QVersionNumber({1, 8}))
|
||||
boardSdkPkg->setVersions(desc.boardSdk.versions);
|
||||
boardSdkDefaultPath = boardSdkPkg->defaultPath();
|
||||
required3rdPartyPkgs.append(boardSdkPkg);
|
||||
@@ -641,9 +642,12 @@ static QFileInfoList targetDescriptionFiles(const Utils::FilePath &dir)
|
||||
return kitsDir.entryInfoList();
|
||||
}
|
||||
|
||||
static McuTargetDescription parseDescriptionJsonCommon(const QString &qulVersion,
|
||||
const QJsonObject &target)
|
||||
McuTargetDescription parseDescriptionJson(const QByteArray &data)
|
||||
{
|
||||
const QJsonDocument document = QJsonDocument::fromJson(data);
|
||||
const QJsonObject target = document.object();
|
||||
const QString qulVersion = target.value("qulVersion").toString();
|
||||
const QJsonObject platform = target.value("platform").toObject();
|
||||
const QString compatVersion = target.value("compatVersion").toString();
|
||||
const QJsonObject toolchain = target.value("toolchain").toObject();
|
||||
const QJsonObject boardSdk = target.value("boardSdk").toObject();
|
||||
@@ -660,9 +664,23 @@ static McuTargetDescription parseDescriptionJsonCommon(const QString &qulVersion
|
||||
return version.toString();
|
||||
});
|
||||
|
||||
const QVariantList colorDepths = platform.value("colorDepths").toArray().toVariantList();
|
||||
const auto colorDepthsVector = Utils::transform<QVector<int>>(colorDepths,
|
||||
[&](const QVariant &colorDepth) {
|
||||
return colorDepth.toInt();
|
||||
});
|
||||
const QString platformName = platform.value("platformName").toString();
|
||||
|
||||
return {qulVersion,
|
||||
compatVersion,
|
||||
{},
|
||||
{
|
||||
platform.value("id").toString(),
|
||||
platformName,
|
||||
platform.value("vendor").toString(),
|
||||
colorDepthsVector,
|
||||
platformName == "Desktop" ? McuTargetDescription::TargetType::Desktop
|
||||
: McuTargetDescription::TargetType::MCU,
|
||||
},
|
||||
{
|
||||
toolchain.value("id").toString(),
|
||||
toolchainVersionsList,
|
||||
@@ -679,86 +697,36 @@ static McuTargetDescription parseDescriptionJsonCommon(const QString &qulVersion
|
||||
}};
|
||||
}
|
||||
|
||||
static McuTargetDescription parseDescriptionJsonV1x(const QString &qulVersion,
|
||||
const QJsonObject &target)
|
||||
{
|
||||
auto description = parseDescriptionJsonCommon(qulVersion, target);
|
||||
|
||||
const QVariantList colorDepths = target.value("colorDepths").toArray().toVariantList();
|
||||
const auto colorDepthsVector = Utils::transform<QVector<int>>(colorDepths,
|
||||
[&](const QVariant &colorDepth) {
|
||||
return colorDepth.toInt();
|
||||
});
|
||||
|
||||
description.platform = {target.value("platform").toString(),
|
||||
target.value("platformName").toString(),
|
||||
target.value("platformVendor").toString(),
|
||||
colorDepthsVector,
|
||||
description.boardSdk.envVar.isEmpty()
|
||||
? McuTargetDescription::TargetType::Desktop
|
||||
: McuTargetDescription::TargetType::MCU};
|
||||
return description;
|
||||
}
|
||||
|
||||
static McuTargetDescription parseDescriptionJsonV2x(const QString &qulVersion,
|
||||
const QJsonObject &target)
|
||||
{
|
||||
const QJsonObject platform = target.value("platform").toObject();
|
||||
|
||||
const QVariantList colorDepths = platform.value("colorDepths").toArray().toVariantList();
|
||||
const auto colorDepthsVector = Utils::transform<QVector<int>>(colorDepths,
|
||||
[&](const QVariant &colorDepth) {
|
||||
return colorDepth.toInt();
|
||||
});
|
||||
const QString platformName = platform.value("platformName").toString();
|
||||
McuTargetDescription description = parseDescriptionJsonCommon(qulVersion, target);
|
||||
description.platform = {
|
||||
platform.value("id").toString(),
|
||||
platformName,
|
||||
platform.value("vendor").toString(),
|
||||
colorDepthsVector,
|
||||
platformName == "Desktop" ? McuTargetDescription::TargetType::Desktop
|
||||
: McuTargetDescription::TargetType::MCU,
|
||||
};
|
||||
|
||||
return description;
|
||||
}
|
||||
|
||||
McuTargetDescription parseDescriptionJson(const QByteArray &data)
|
||||
{
|
||||
const QJsonDocument document = QJsonDocument::fromJson(data);
|
||||
const QJsonObject target = document.object();
|
||||
|
||||
const QString qulVersion = target.value("qulVersion").toString();
|
||||
|
||||
switch (QVersionNumber::fromString(qulVersion).majorVersion()) {
|
||||
case 1:
|
||||
return parseDescriptionJsonV1x(qulVersion, target);
|
||||
case 2:
|
||||
return parseDescriptionJsonV2x(qulVersion, target);
|
||||
default:
|
||||
return {qulVersion};
|
||||
}
|
||||
}
|
||||
|
||||
// https://doc.qt.io/qtcreator/creator-developing-mcu.html#supported-qt-for-mcus-sdks
|
||||
const QHash<QString, QString> oldSdkQtcRequiredVersion = {
|
||||
static const QString legacySupportVersionFor(const QString &sdkVersion)
|
||||
{
|
||||
static const QHash<QString, QString> oldSdkQtcRequiredVersion = {
|
||||
{{"1.0"}, {"4.11.x"}},
|
||||
{{"1.1"}, {"4.12.0 or 4.12.1"}},
|
||||
{{"1.2"}, {"4.12.2 or 4.12.3"}},
|
||||
};
|
||||
{{"1.2"}, {"4.12.2 or 4.12.3"}}
|
||||
};
|
||||
if (oldSdkQtcRequiredVersion.contains(sdkVersion))
|
||||
return oldSdkQtcRequiredVersion.value(sdkVersion);
|
||||
|
||||
if (QVersionNumber::fromString(sdkVersion).majorVersion() == 1)
|
||||
return "4.12.4 up to 6.0";
|
||||
|
||||
return QString();
|
||||
}
|
||||
|
||||
|
||||
bool checkDeprecatedSdkError(const Utils::FilePath &qulDir, QString &message)
|
||||
{
|
||||
const McuPackagePathVersionDetector versionDetector("(?<=\\bQtMCUs.)(\\d+\\.\\d+)");
|
||||
const QString sdkDetectedVersion = versionDetector.parseVersion(qulDir.toString());
|
||||
const QString legacyVersion = legacySupportVersionFor(sdkDetectedVersion);
|
||||
|
||||
if (oldSdkQtcRequiredVersion.contains(sdkDetectedVersion)) {
|
||||
if (!legacyVersion.isEmpty()) {
|
||||
message = McuTarget::tr("Qt for MCUs SDK version %1 detected, "
|
||||
"only supported by Qt Creator version %2. "
|
||||
"This version of Qt Creator requires Qt for MCUs %3 or greater.")
|
||||
.arg(sdkDetectedVersion,
|
||||
oldSdkQtcRequiredVersion.value(sdkDetectedVersion),
|
||||
legacyVersion,
|
||||
McuSupportOptions::minimalQulVersion().toString());
|
||||
return true;
|
||||
}
|
||||
@@ -787,10 +755,11 @@ void targetsAndPackages(const Utils::FilePath &dir, McuSdkRepository *repo)
|
||||
continue;
|
||||
}
|
||||
if (QVersionNumber::fromString(desc.qulVersion) < McuSupportOptions::minimalQulVersion()) {
|
||||
const QString legacyVersion = legacySupportVersionFor(desc.qulVersion);
|
||||
const QString qtcSupportText
|
||||
= oldSdkQtcRequiredVersion.contains(desc.qulVersion)
|
||||
= !legacyVersion.isEmpty()
|
||||
? McuTarget::tr("Detected version \"%1\", only supported by Qt Creator %2.")
|
||||
.arg(desc.qulVersion, oldSdkQtcRequiredVersion.value(desc.qulVersion))
|
||||
.arg(desc.qulVersion, legacyVersion)
|
||||
: McuTarget::tr("Unsupported version \"%1\".").arg(desc.qulVersion);
|
||||
printMessage(McuTarget::tr("Skipped %1. %2 Qt for MCUs version >= %3 required.")
|
||||
.arg(QDir::toNativeSeparators(pth.fileNameWithPathComponents(1)),
|
||||
@@ -818,68 +787,13 @@ void targetsAndPackages(const Utils::FilePath &dir, McuSdkRepository *repo)
|
||||
}
|
||||
}
|
||||
|
||||
// Workaround for missing JSON file for Desktop target.
|
||||
// Desktop JSON file is shipped starting from Qul 1.5.
|
||||
// This whole section could be removed when minimalQulVersion will reach 1.5 or above
|
||||
{
|
||||
const bool hasDesktopDescription
|
||||
= contains(descriptions, [](const McuTargetDescription &desc) {
|
||||
return desc.platform.type == McuTargetDescription::TargetType::Desktop;
|
||||
});
|
||||
|
||||
if (!hasDesktopDescription) {
|
||||
QVector<FilePath> desktopLibs;
|
||||
if (HostOsInfo::isWindowsHost()) {
|
||||
desktopLibs << dir / "lib/QulQuickUltralite_QT_32bpp_Windows_Release.lib"; // older versions of QUL (<1.5?)
|
||||
desktopLibs
|
||||
<< dir / "lib/QulQuickUltralitePlatform_QT_32bpp_Windows_msvc_Release.lib"; // newer versions of QUL
|
||||
} else {
|
||||
desktopLibs << dir / "lib/libQulQuickUltralite_QT_32bpp_Linux_Debug.a"; // older versions of QUL (<1.5?)
|
||||
desktopLibs << dir / "lib/libQulQuickUltralitePlatform_QT_32bpp_Linux_gnu_Debug.a"; // newer versions of QUL
|
||||
}
|
||||
|
||||
if (anyOf(desktopLibs, [](const FilePath &desktopLib) { return desktopLib.exists(); })) {
|
||||
McuTargetDescription desktopDescription;
|
||||
desktopDescription.qulVersion
|
||||
= descriptions.empty() ? McuSupportOptions::minimalQulVersion().toString()
|
||||
: descriptions.first().qulVersion;
|
||||
desktopDescription.platform.id = "Qt";
|
||||
desktopDescription.platform.name = "Desktop";
|
||||
desktopDescription.platform.vendor = "Qt";
|
||||
desktopDescription.platform.colorDepths = {32};
|
||||
desktopDescription.toolchain.id = HostOsInfo::isWindowsHost() ? QString("msvc")
|
||||
: QString("gcc");
|
||||
desktopDescription.platform.type = McuTargetDescription::TargetType::Desktop;
|
||||
descriptions.prepend(desktopDescription);
|
||||
} else {
|
||||
// show error only on 1.x SDKs, but skip on 2.x
|
||||
const FilePath desktopLibV2
|
||||
= HostOsInfo::isWindowsHost()
|
||||
? dir / "lib/QulPlatform_qt_32bpp_Windows_msvc_Release.lib"
|
||||
: dir / "lib/libQulPlatform_qt_32bpp_Linux_gnu_Release.a";
|
||||
if (dir.exists() && !desktopLibV2.exists())
|
||||
printMessage(
|
||||
McuTarget::tr(
|
||||
"Skipped creating fallback desktop kit: Could not find any of %1.")
|
||||
.arg(transform(desktopLibs,
|
||||
[](const auto &path) {
|
||||
return QDir::toNativeSeparators(
|
||||
path.fileNameWithPathComponents(1));
|
||||
})
|
||||
.toList()
|
||||
.join(" or ")),
|
||||
false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
repo->mcuTargets.append(targetsFromDescriptions(descriptions, &(repo->packages)));
|
||||
|
||||
// Keep targets sorted lexicographically
|
||||
std::sort(repo->mcuTargets.begin(),
|
||||
repo->mcuTargets.end(),
|
||||
[](const McuTarget *lhs, const McuTarget *rhs) {
|
||||
return McuSupportOptions::kitName(lhs) < McuSupportOptions::kitName(rhs);
|
||||
return McuKitManager::kitName(lhs) < McuKitManager::kitName(rhs);
|
||||
});
|
||||
}
|
||||
|
||||
|
@@ -33,7 +33,7 @@
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
constexpr int MAX_COMPATIBILITY_VERSION {1};
|
||||
constexpr int MAX_COMPATIBILITY_VERSION{1};
|
||||
|
||||
class McuSdkRepository;
|
||||
class McuAbstractPackage;
|
||||
@@ -51,13 +51,14 @@ bool checkDeprecatedSdkError(const Utils::FilePath &qulDir, QString &message);
|
||||
void targetsAndPackages(const Utils::FilePath &qulDir, McuSdkRepository *repo);
|
||||
|
||||
McuTargetDescription parseDescriptionJson(const QByteArray &);
|
||||
QVector<McuTarget *> targetsFromDescriptions(const QList<McuTargetDescription> &, QVector<McuAbstractPackage *> *);
|
||||
QVector<McuTarget *> targetsFromDescriptions(const QList<McuTargetDescription> &,
|
||||
QVector<McuAbstractPackage *> *);
|
||||
|
||||
Utils::FilePath kitsPath(const Utils::FilePath &dir);
|
||||
|
||||
Utils::FilePath packagePathFromSettings(const QString &settingsKey,
|
||||
QSettings::Scope scope = QSettings::UserScope,
|
||||
const Utils::FilePath &defaultPath = {});
|
||||
QSettings::Scope scope,
|
||||
const Utils::FilePath &defaultPath);
|
||||
} // namespace Sdk
|
||||
} // namespace Internal
|
||||
} // namespace McuSupport
|
||||
|
290
src/plugins/mcusupport/mcutarget.cpp
Normal file
290
src/plugins/mcusupport/mcutarget.cpp
Normal file
@@ -0,0 +1,290 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
**
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcutarget.h"
|
||||
#include "mcupackage.h"
|
||||
#include "mcukitmanager.h"
|
||||
|
||||
#include "mcusupportplugin.h"
|
||||
|
||||
#include <baremetal/baremetalconstants.h>
|
||||
#include <debugger/debuggeritem.h>
|
||||
#include <debugger/debuggeritemmanager.h>
|
||||
#include <projectexplorer/projectexplorerconstants.h>
|
||||
#include <projectexplorer/toolchain.h>
|
||||
#include <projectexplorer/toolchainmanager.h>
|
||||
|
||||
using namespace ProjectExplorer;
|
||||
using namespace Utils;
|
||||
|
||||
namespace McuSupport::Internal {
|
||||
|
||||
static ToolChain *msvcToolChain(Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
const Abi abi = t->targetAbi();
|
||||
// TODO: Should Abi::WindowsMsvc2022Flavor be added too?
|
||||
return (abi.osFlavor() == Abi::WindowsMsvc2017Flavor
|
||||
|| abi.osFlavor() == Abi::WindowsMsvc2019Flavor)
|
||||
&& abi.architecture() == Abi::X86Architecture && abi.wordWidth() == 64
|
||||
&& t->language() == language;
|
||||
});
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *gccToolChain(Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
const Abi abi = t->targetAbi();
|
||||
return abi.os() != Abi::WindowsOS && abi.architecture() == Abi::X86Architecture
|
||||
&& abi.wordWidth() == 64 && t->language() == language;
|
||||
});
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *armGccToolChain(const FilePath &path, Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([&path, language](const ToolChain *t) {
|
||||
return t->compilerCommand() == path && t->language() == language;
|
||||
});
|
||||
if (!toolChain) {
|
||||
ToolChainFactory *gccFactory
|
||||
= Utils::findOrDefault(ToolChainFactory::allToolChainFactories(),
|
||||
[](ToolChainFactory *f) {
|
||||
return f->supportedToolChainType()
|
||||
== ProjectExplorer::Constants::GCC_TOOLCHAIN_TYPEID;
|
||||
});
|
||||
if (gccFactory) {
|
||||
const QList<ToolChain *> detected = gccFactory->detectForImport({path, language});
|
||||
if (!detected.isEmpty()) {
|
||||
toolChain = detected.first();
|
||||
toolChain->setDetection(ToolChain::ManualDetection);
|
||||
toolChain->setDisplayName("Arm GCC");
|
||||
ToolChainManager::registerToolChain(toolChain);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
static ToolChain *iarToolChain(const FilePath &path, Id language)
|
||||
{
|
||||
ToolChain *toolChain = ToolChainManager::toolChain([language](const ToolChain *t) {
|
||||
return t->typeId() == BareMetal::Constants::IAREW_TOOLCHAIN_TYPEID
|
||||
&& t->language() == language;
|
||||
});
|
||||
if (!toolChain) {
|
||||
ToolChainFactory *iarFactory
|
||||
= Utils::findOrDefault(ToolChainFactory::allToolChainFactories(),
|
||||
[](ToolChainFactory *f) {
|
||||
return f->supportedToolChainType()
|
||||
== BareMetal::Constants::IAREW_TOOLCHAIN_TYPEID;
|
||||
});
|
||||
if (iarFactory) {
|
||||
Toolchains detected = iarFactory->autoDetect(ToolchainDetector({}, {}));
|
||||
if (detected.isEmpty())
|
||||
detected = iarFactory->detectForImport({path, language});
|
||||
for (auto tc : detected) {
|
||||
if (tc->language() == language) {
|
||||
toolChain = tc;
|
||||
toolChain->setDetection(ToolChain::ManualDetection);
|
||||
toolChain->setDisplayName("IAREW");
|
||||
ToolChainManager::registerToolChain(toolChain);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return toolChain;
|
||||
}
|
||||
|
||||
ToolChain *McuToolChainPackage::toolChain(Id language) const
|
||||
{
|
||||
switch (m_type) {
|
||||
case Type::MSVC:
|
||||
return msvcToolChain(language);
|
||||
case Type::GCC:
|
||||
return gccToolChain(language);
|
||||
case Type::IAR: {
|
||||
const FilePath compiler = path().pathAppended("/bin/iccarm").withExecutableSuffix();
|
||||
return iarToolChain(compiler, language);
|
||||
}
|
||||
case Type::ArmGcc:
|
||||
case Type::KEIL:
|
||||
case Type::GHS:
|
||||
case Type::GHSArm:
|
||||
case Type::Unsupported: {
|
||||
const QLatin1String compilerName(
|
||||
language == ProjectExplorer::Constants::C_LANGUAGE_ID ? "gcc" : "g++");
|
||||
const QString comp = QLatin1String(m_type == Type::ArmGcc ? "/bin/arm-none-eabi-%1"
|
||||
: "/bar/foo-keil-%1")
|
||||
.arg(compilerName);
|
||||
const FilePath compiler = path().pathAppended(comp).withExecutableSuffix();
|
||||
|
||||
return armGccToolChain(compiler, language);
|
||||
}
|
||||
default:
|
||||
Q_UNREACHABLE();
|
||||
}
|
||||
}
|
||||
|
||||
QString McuToolChainPackage::toolChainName() const
|
||||
{
|
||||
switch (m_type) {
|
||||
case Type::ArmGcc:
|
||||
return QLatin1String("armgcc");
|
||||
case Type::IAR:
|
||||
return QLatin1String("iar");
|
||||
case Type::KEIL:
|
||||
return QLatin1String("keil");
|
||||
case Type::GHS:
|
||||
return QLatin1String("ghs");
|
||||
case Type::GHSArm:
|
||||
return QLatin1String("ghs-arm");
|
||||
default:
|
||||
return QLatin1String("unsupported");
|
||||
}
|
||||
}
|
||||
|
||||
QString McuToolChainPackage::cmakeToolChainFileName() const
|
||||
{
|
||||
return toolChainName() + QLatin1String(".cmake");
|
||||
}
|
||||
|
||||
QVariant McuToolChainPackage::debuggerId() const
|
||||
{
|
||||
using namespace Debugger;
|
||||
|
||||
QString sub, displayName;
|
||||
DebuggerEngineType engineType;
|
||||
|
||||
switch (m_type) {
|
||||
case Type::ArmGcc: {
|
||||
sub = QString::fromLatin1("bin/arm-none-eabi-gdb-py");
|
||||
displayName = McuPackage::tr("Arm GDB at %1");
|
||||
engineType = Debugger::GdbEngineType;
|
||||
break;
|
||||
}
|
||||
case Type::IAR: {
|
||||
sub = QString::fromLatin1("../common/bin/CSpyBat");
|
||||
displayName = QLatin1String("CSpy");
|
||||
engineType = Debugger::NoEngineType; // support for IAR missing
|
||||
break;
|
||||
}
|
||||
case Type::KEIL: {
|
||||
sub = QString::fromLatin1("UV4/UV4");
|
||||
displayName = QLatin1String("KEIL uVision Debugger");
|
||||
engineType = Debugger::UvscEngineType;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
const FilePath command = path().pathAppended(sub).withExecutableSuffix();
|
||||
if (const DebuggerItem *debugger = DebuggerItemManager::findByCommand(command)) {
|
||||
return debugger->id();
|
||||
}
|
||||
|
||||
DebuggerItem newDebugger;
|
||||
newDebugger.setCommand(command);
|
||||
newDebugger.setUnexpandedDisplayName(displayName.arg(command.toUserOutput()));
|
||||
newDebugger.setEngineType(engineType);
|
||||
return DebuggerItemManager::registerDebugger(newDebugger);
|
||||
}
|
||||
|
||||
McuTarget::McuTarget(const QVersionNumber &qulVersion,
|
||||
const Platform &platform,
|
||||
OS os,
|
||||
const QVector<McuAbstractPackage *> &packages,
|
||||
const McuToolChainPackage *toolChainPackage,
|
||||
int colorDepth)
|
||||
: m_qulVersion(qulVersion)
|
||||
, m_platform(platform)
|
||||
, m_os(os)
|
||||
, m_packages(packages)
|
||||
, m_toolChainPackage(toolChainPackage)
|
||||
, m_colorDepth(colorDepth)
|
||||
{}
|
||||
|
||||
const QVector<McuAbstractPackage *> &McuTarget::packages() const
|
||||
{
|
||||
return m_packages;
|
||||
}
|
||||
|
||||
const McuToolChainPackage *McuTarget::toolChainPackage() const
|
||||
{
|
||||
return m_toolChainPackage;
|
||||
}
|
||||
|
||||
McuTarget::OS McuTarget::os() const
|
||||
{
|
||||
return m_os;
|
||||
}
|
||||
|
||||
const McuTarget::Platform &McuTarget::platform() const
|
||||
{
|
||||
return m_platform;
|
||||
}
|
||||
|
||||
bool McuTarget::isValid() const
|
||||
{
|
||||
return Utils::allOf(packages(), [](McuAbstractPackage *package) {
|
||||
package->updateStatus();
|
||||
return package->validStatus();
|
||||
});
|
||||
}
|
||||
|
||||
void McuTarget::printPackageProblems() const
|
||||
{
|
||||
for (auto package : packages()) {
|
||||
package->updateStatus();
|
||||
if (!package->validStatus())
|
||||
printMessage(tr("Error creating kit for target %1, package %2: %3")
|
||||
.arg(McuKitManager::kitName(this),
|
||||
package->label(),
|
||||
package->statusText()),
|
||||
true);
|
||||
if (package->status() == McuAbstractPackage::Status::ValidPackageMismatchedVersion)
|
||||
printMessage(tr("Warning creating kit for target %1, package %2: %3")
|
||||
.arg(McuKitManager::kitName(this),
|
||||
package->label(),
|
||||
package->statusText()),
|
||||
false);
|
||||
}
|
||||
}
|
||||
|
||||
const QVersionNumber &McuTarget::qulVersion() const
|
||||
{
|
||||
return m_qulVersion;
|
||||
}
|
||||
|
||||
int McuTarget::colorDepth() const
|
||||
{
|
||||
return m_colorDepth;
|
||||
}
|
||||
|
||||
} // namespace McuSupport::Internal
|
89
src/plugins/mcusupport/mcutarget.h
Normal file
89
src/plugins/mcusupport/mcutarget.h
Normal file
@@ -0,0 +1,89 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2022 The Qt Company Ltd.
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of Qt Creator.
|
||||
**
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <QObject>
|
||||
#include <QVersionNumber>
|
||||
|
||||
namespace ProjectExplorer {
|
||||
class ToolChain;
|
||||
}
|
||||
|
||||
namespace Utils {
|
||||
class PathChooser;
|
||||
class InfoLabel;
|
||||
} // namespace Utils
|
||||
|
||||
namespace McuSupport {
|
||||
namespace Internal {
|
||||
|
||||
class McuAbstractPackage;
|
||||
class McuToolChainPackage;
|
||||
|
||||
class McuTarget : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum class OS { Desktop, BareMetal, FreeRTOS };
|
||||
|
||||
struct Platform
|
||||
{
|
||||
QString name;
|
||||
QString displayName;
|
||||
QString vendor;
|
||||
};
|
||||
|
||||
enum { UnspecifiedColorDepth = -1 };
|
||||
|
||||
McuTarget(const QVersionNumber &qulVersion,
|
||||
const Platform &platform,
|
||||
OS os,
|
||||
const QVector<McuAbstractPackage *> &packages,
|
||||
const McuToolChainPackage *toolChainPackage,
|
||||
int colorDepth = UnspecifiedColorDepth);
|
||||
|
||||
const QVersionNumber &qulVersion() const;
|
||||
const QVector<McuAbstractPackage *> &packages() const;
|
||||
const McuToolChainPackage *toolChainPackage() const;
|
||||
const Platform &platform() const;
|
||||
OS os() const;
|
||||
int colorDepth() const;
|
||||
bool isValid() const;
|
||||
void printPackageProblems() const;
|
||||
|
||||
private:
|
||||
const QVersionNumber m_qulVersion;
|
||||
const Platform m_platform;
|
||||
const OS m_os;
|
||||
const QVector<McuAbstractPackage *> m_packages;
|
||||
const McuToolChainPackage *m_toolChainPackage;
|
||||
const int m_colorDepth;
|
||||
}; // class McuTarget
|
||||
|
||||
|
||||
} // namespace Internal
|
||||
} // namespace McuSupport
|
@@ -27,8 +27,8 @@
|
||||
|
||||
#include "mcuabstractpackage.h"
|
||||
|
||||
#include <utils/filepath.h>
|
||||
#include <gmock/gmock.h>
|
||||
#include <utils/filepath.h>
|
||||
|
||||
namespace McuSupport::Internal {
|
||||
|
||||
@@ -45,19 +45,13 @@ public:
|
||||
|
||||
MOCK_METHOD(Status, status, (), (const));
|
||||
MOCK_METHOD(bool, validStatus, (), (const));
|
||||
MOCK_METHOD(void, setDownloadUrl, (const QString &) );
|
||||
MOCK_METHOD(void, setEnvironmentVariableName, (const QString &) );
|
||||
MOCK_METHOD(const QString&, environmentVariableName, (), (const));
|
||||
MOCK_METHOD(const QString &, environmentVariableName, (), (const));
|
||||
MOCK_METHOD(void, setAddToPath, (bool) );
|
||||
MOCK_METHOD(bool, addToPath, (), (const));
|
||||
MOCK_METHOD(void, writeGeneralSettings, (), (const));
|
||||
MOCK_METHOD(bool, writeToSettings, (), (const));
|
||||
MOCK_METHOD(void, setRelativePathModifier, (const QString &) );
|
||||
MOCK_METHOD(void, setVersions, (const QStringList &) );
|
||||
|
||||
MOCK_METHOD(bool, automaticKitCreationEnabled, (), (const));
|
||||
MOCK_METHOD(void, setAutomaticKitCreationEnabled, (const bool enabled));
|
||||
|
||||
MOCK_METHOD(QWidget *, widget, ());
|
||||
}; // class PackageMock
|
||||
} // namespace McuSupport::Internal
|
||||
|
@@ -23,9 +23,10 @@
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include "mcutargetdescription.h"
|
||||
#include "nxp_1064_json.h"
|
||||
#include "unittest.h"
|
||||
#include "mcutargetdescription.h"
|
||||
#include "mcukitmanager.h"
|
||||
#include "nxp_1064_json.h"
|
||||
#include "utils/filepath.h"
|
||||
#include <cmakeprojectmanager/cmakeconfigitem.h>
|
||||
#include <cmakeprojectmanager/cmakekitinformation.h>
|
||||
@@ -55,7 +56,7 @@ void McuSupportTest::test_parseBasicInfoFromJson()
|
||||
{
|
||||
const auto description = Sdk::parseDescriptionJson(nxp_1064_json);
|
||||
|
||||
QVERIFY(not description.freeRTOS.envVar.isEmpty());
|
||||
QVERIFY(!description.freeRTOS.envVar.isEmpty());
|
||||
QVERIFY(description.freeRTOS.boardSdkSubDir.isEmpty());
|
||||
}
|
||||
|
||||
@@ -65,7 +66,7 @@ void McuSupportTest::test_addNewKit()
|
||||
|
||||
QSignalSpy kitAddedSpy(&kitManager, &KitManager::kitAdded);
|
||||
|
||||
auto *newKit{McuSupportOptions::newKit(&mcuTarget, &freeRtosPackage)};
|
||||
auto *newKit{McuKitManager::newKit(&mcuTarget, &freeRtosPackage)};
|
||||
QVERIFY(newKit != nullptr);
|
||||
|
||||
QCOMPARE(kitAddedSpy.count(), 1);
|
||||
@@ -85,13 +86,13 @@ void McuSupportTest::test_addFreeRtosCmakeVarToKit()
|
||||
|
||||
QVERIFY(kit.hasValue(EnvironmentKitAspect::id()));
|
||||
QVERIFY(kit.isValid());
|
||||
QVERIFY(not kit.allKeys().empty());
|
||||
QVERIFY(!kit.allKeys().empty());
|
||||
|
||||
const auto &cmakeConfig{CMakeConfigurationKitAspect::configuration(&kit)};
|
||||
QCOMPARE(cmakeConfig.size(), 1);
|
||||
|
||||
CMakeConfigItem expectedCmakeVar{freeRtosCmakeVar.toLocal8Bit(),
|
||||
defaultfreeRtosPath.toLocal8Bit()};
|
||||
FilePath::fromString(defaultfreeRtosPath).toUserOutput().toLocal8Bit()};
|
||||
QVERIFY(cmakeConfig.contains(expectedCmakeVar));
|
||||
}
|
||||
|
||||
|
@@ -25,10 +25,11 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "mcupackage.h"
|
||||
#include "mcutarget.h"
|
||||
#include "mcusupportoptions.h"
|
||||
#include "mcusupportplugin.h"
|
||||
#include "mcusupportsdk.h"
|
||||
#include "mcupackage.h"
|
||||
#include "packagemock.h"
|
||||
|
||||
#include <projectexplorer/kit.h>
|
||||
|
@@ -4,20 +4,7 @@ project(%{ProjectName} VERSION 0.0.1 LANGUAGES C CXX ASM ASM_MASM)
|
||||
|
||||
find_package(Qul)
|
||||
|
||||
if(Qul_VERSION VERSION_GREATER_EQUAL "1.7")
|
||||
qul_add_target(%{ProjectName})
|
||||
else()
|
||||
add_executable(%{ProjectName})
|
||||
target_link_libraries(%{ProjectName}
|
||||
Qul::QuickUltralite
|
||||
Qul::QuickUltralitePlatform)
|
||||
endif()
|
||||
|
||||
qul_add_target(%{ProjectName})
|
||||
qul_target_qml_sources(%{ProjectName} %{MainQmlFile})
|
||||
app_target_setup_os(%{ProjectName})
|
||||
|
||||
if(Qul_VERSION VERSION_GREATER_EQUAL "2.0")
|
||||
app_target_default_entrypoint(%{ProjectName} %{RootItemName})
|
||||
else()
|
||||
app_target_default_main(%{ProjectName} %{RootItemName})
|
||||
endif()
|
||||
app_target_default_entrypoint(%{ProjectName} %{RootItemName})
|
||||
|
@@ -73,7 +73,7 @@ MercurialSettingsPage::MercurialSettingsPage(MercurialSettings *settings)
|
||||
setId(VcsBase::Constants::VCS_ID_MERCURIAL);
|
||||
setDisplayName(MercurialSettings::tr("Mercurial"));
|
||||
setCategory(VcsBase::Constants::VCS_SETTINGS_CATEGORY);
|
||||
setSettings(m_settings);
|
||||
setSettings(settings);
|
||||
|
||||
setLayouter([settings](QWidget *widget) {
|
||||
MercurialSettings &s = *settings;
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user