diff --git a/src/FirmwarePlugin/APM/APMFirmwarePlugin.cc b/src/FirmwarePlugin/APM/APMFirmwarePlugin.cc index 7a4156c7b8d..5e7f3d76007 100644 --- a/src/FirmwarePlugin/APM/APMFirmwarePlugin.cc +++ b/src/FirmwarePlugin/APM/APMFirmwarePlugin.cc @@ -522,7 +522,7 @@ void APMFirmwarePlugin::_getParameterMetaDataVersionInfo(const QString& metaData } -QList APMFirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) +QList APMFirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) const { QList supportedCommands = { MAV_CMD_NAV_WAYPOINT, diff --git a/src/FirmwarePlugin/APM/APMFirmwarePlugin.h b/src/FirmwarePlugin/APM/APMFirmwarePlugin.h index 91c0bdd0706..0feb863b6f5 100644 --- a/src/FirmwarePlugin/APM/APMFirmwarePlugin.h +++ b/src/FirmwarePlugin/APM/APMFirmwarePlugin.h @@ -45,7 +45,7 @@ class APMFirmwarePlugin : public FirmwarePlugin // Overrides from FirmwarePlugin QList componentsForVehicle(AutoPilotPlugin* vehicle) override; - QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) override; + QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) const override; AutoPilotPlugin* autopilotPlugin (Vehicle* vehicle) override; bool isCapable (const Vehicle *vehicle, FirmwareCapabilities capabilities) override; diff --git a/src/FirmwarePlugin/FirmwarePlugin.cc b/src/FirmwarePlugin/FirmwarePlugin.cc index 739061ebba6..3fcf5203c77 100644 --- a/src/FirmwarePlugin/FirmwarePlugin.cc +++ b/src/FirmwarePlugin/FirmwarePlugin.cc @@ -161,7 +161,7 @@ bool FirmwarePlugin::sendHomePositionToVehicle(void) return false; } -QList FirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t /* vehicleClass */) +QList FirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t /* vehicleClass */) const { // Generic supports all commands return QList(); diff --git a/src/FirmwarePlugin/FirmwarePlugin.h b/src/FirmwarePlugin/FirmwarePlugin.h index 7591280b2d6..e76ab25cf2f 100644 --- a/src/FirmwarePlugin/FirmwarePlugin.h +++ b/src/FirmwarePlugin/FirmwarePlugin.h @@ -261,7 +261,7 @@ class FirmwarePlugin : public QObject virtual FactMetaData* _getMetaDataForFact(QObject* /*parameterMetaData*/, const QString& /*name*/, FactMetaData::ValueType_t /* type */, MAV_TYPE /*vehicleType*/) { return nullptr; } /// List of supported mission commands. Empty list for all commands supported. - virtual QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass); + virtual QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) const; /// Returns the name of the mission command json override file for the specified vehicle type. /// @param vehicleClass Vehicle class to return file for, VehicleClassGeneric is a request for overrides for all vehicle types diff --git a/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.cc b/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.cc index 218acd82c87..270209d3214 100644 --- a/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.cc +++ b/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.cc @@ -260,7 +260,7 @@ void PX4FirmwarePlugin::_getParameterMetaDataVersionInfo(const QString& metaData return PX4ParameterMetaData::getParameterMetaDataVersionInfo(metaDataFile, majorVersion, minorVersion); } -QList PX4FirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) +QList PX4FirmwarePlugin::supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) const { QList supportedCommands = { MAV_CMD_NAV_WAYPOINT, diff --git a/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.h b/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.h index c82777f33df..2b3936c4c46 100644 --- a/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.h +++ b/src/FirmwarePlugin/PX4/PX4FirmwarePlugin.h @@ -26,7 +26,7 @@ class PX4FirmwarePlugin : public FirmwarePlugin // Overrides from FirmwarePlugin QList componentsForVehicle(AutoPilotPlugin* vehicle) override; - QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) override; + QList supportedMissionCommands(QGCMAVLink::VehicleClass_t vehicleClass) const override; AutoPilotPlugin* autopilotPlugin (Vehicle* vehicle) override; bool isCapable (const Vehicle *vehicle, FirmwareCapabilities capabilities) override; diff --git a/src/MissionManager/KMLPlanDomDocument.cc b/src/MissionManager/KMLPlanDomDocument.cc index a5ac0f42fea..06e6a8aefae 100644 --- a/src/MissionManager/KMLPlanDomDocument.cc +++ b/src/MissionManager/KMLPlanDomDocument.cc @@ -47,7 +47,7 @@ void KMLPlanDomDocument::_addFlightPath(Vehicle* vehicle, QList rg QList rgFlightCoords; QGeoCoordinate homeCoord = rgMissionItems[0]->coordinate(); for (const MissionItem* item : rgMissionItems) { - const MissionCommandUIInfo* uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, item->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, item->command()); if (uiInfo) { double altAdjustment = item->frame() == MAV_FRAME_GLOBAL ? 0 : homeCoord.altitude(); // Used to convert to amsl if (uiInfo->isTakeoffCommand() && !vehicle->fixedWing()) { diff --git a/src/MissionManager/MissionCommandTree.cc b/src/MissionManager/MissionCommandTree.cc index 7b2881f163c..f76ea9a4a5c 100644 --- a/src/MissionManager/MissionCommandTree.cc +++ b/src/MissionManager/MissionCommandTree.cc @@ -8,70 +8,68 @@ ****************************************************************************/ #include "MissionCommandTree.h" -#include "Vehicle.h" -#include "FirmwarePluginManager.h" -#include "QGCApplication.h" #include "FirmwarePlugin.h" -#include "MissionCommandUIInfo.h" +#include "FirmwarePluginManager.h" #include "MissionCommandList.h" +#include "MissionCommandUIInfo.h" +#include "QGCLoggingCategory.h" +#include "Vehicle.h" +#include #include -MissionCommandTree::MissionCommandTree(QGCApplication* app, QGCToolbox* toolbox, bool unitTest) - : QGCTool (app, toolbox) - , _allCommandsCategory (tr("All commands")) - , _settingsManager (nullptr) - , _unitTest (unitTest) -{ -} +QGC_LOGGING_CATEGORY(MissionCommandTreeLog, "qgc.missionmanager.missioncommandtree"); + +Q_APPLICATION_STATIC(MissionCommandTree, _missionCommandTreeInstance); -void MissionCommandTree::setToolbox(QGCToolbox* toolbox) +MissionCommandTree::MissionCommandTree(bool unitTest, QObject *parent) + : QObject(parent) { - QGCTool::setToolbox(toolbox); + // qCDebug(MissionCommandTreeLog) << Q_FUNC_INFO << this; - _settingsManager = toolbox->settingsManager(); + (void) qmlRegisterUncreatableType("QGroundControl", 1, 0, "MissionCommandTree", "Reference only"); -#ifdef UNITTEST_BUILD - if (_unitTest) { + if (unitTest) { // Load unit testing tree - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassGeneric] = new MissionCommandList(":/unittest/UT-MavCmdInfoCommon.json", true, this); - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassFixedWing] = new MissionCommandList(":/unittest/UT-MavCmdInfoFixedWing.json", false, this); - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassMultiRotor] = new MissionCommandList(":/unittest/UT-MavCmdInfoMultiRotor.json", false, this); - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassVTOL] = new MissionCommandList(":/unittest/UT-MavCmdInfoVTOL.json", false, this); - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassSub] = new MissionCommandList(":/unittest/UT-MavCmdInfoSub.json", false, this); - _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassRoverBoat] = new MissionCommandList(":/unittest/UT-MavCmdInfoRover.json", false, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassGeneric] = new MissionCommandList(":/unittest/UT-MavCmdInfoCommon.json", true, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassFixedWing] = new MissionCommandList(":/unittest/UT-MavCmdInfoFixedWing.json", false, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassMultiRotor] = new MissionCommandList(":/unittest/UT-MavCmdInfoMultiRotor.json", false, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassVTOL] = new MissionCommandList(":/unittest/UT-MavCmdInfoVTOL.json", false, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassSub] = new MissionCommandList(":/unittest/UT-MavCmdInfoSub.json", false, this); + _staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassRoverBoat] = new MissionCommandList(":/unittest/UT-MavCmdInfoRover.json", false, this); } else { -#endif // Load all levels of hierarchy for (const QGCMAVLink::FirmwareClass_t firmwareClass: FirmwarePluginManager::instance()->supportedFirmwareClasses()) { - FirmwarePlugin* plugin = FirmwarePluginManager::instance()->firmwarePluginForAutopilot(QGCMAVLink::firmwareClassToAutopilot(firmwareClass), MAV_TYPE_QUADROTOR); - + const FirmwarePlugin *const plugin = FirmwarePluginManager::instance()->firmwarePluginForAutopilot(QGCMAVLink::firmwareClassToAutopilot(firmwareClass), MAV_TYPE_QUADROTOR); for (const QGCMAVLink::VehicleClass_t vehicleClass: QGCMAVLink::allVehicleClasses()) { - QString overrideFile = plugin->missionCommandOverrides(vehicleClass); + const QString overrideFile = plugin->missionCommandOverrides(vehicleClass); if (!overrideFile.isEmpty()) { - _staticCommandTree[firmwareClass][vehicleClass] = new MissionCommandList(overrideFile, firmwareClass == QGCMAVLink::FirmwareClassGeneric && vehicleClass == QGCMAVLink::VehicleClassGeneric /* baseCommandList */, this); + const bool baseCommandList = ((firmwareClass == QGCMAVLink::FirmwareClassGeneric) && (vehicleClass == QGCMAVLink::VehicleClassGeneric)); + _staticCommandTree[firmwareClass][vehicleClass] = new MissionCommandList(overrideFile, baseCommandList, this); } } } -#ifdef UNITTEST_BUILD } -#endif +} + +MissionCommandTree::~MissionCommandTree() +{ + // qCDebug(MissionCommandTreeLog) << Q_FUNC_INFO << this; +} - qmlRegisterUncreatableType("QGroundControl", 1, 0, "MissionCommandTree", "Reference only"); +MissionCommandTree *MissionCommandTree::instance() +{ + return _missionCommandTreeInstance(); } -/// Add the next level of the hierarchy to a collapsed tree. -/// @param cmdList List of mission commands to collapse into ui info -/// @param collapsedTree Tree we are collapsing into -void MissionCommandTree::_collapseHierarchy(const MissionCommandList* cmdList, - QMap& collapsedTree) +void MissionCommandTree::_collapseHierarchy(const MissionCommandList *cmdList, QMap &collapsedTree) const { if (!cmdList) { return; } - for (MAV_CMD command: cmdList->commandIds()) { - MissionCommandUIInfo* uiInfo = cmdList->getUIInfo(command); + for (const MAV_CMD command: cmdList->commandIds()) { + MissionCommandUIInfo *const uiInfo = cmdList->getUIInfo(command); if (uiInfo) { if (collapsedTree.contains(command)) { collapsedTree[command]->_overrideInfo(uiInfo); @@ -82,7 +80,7 @@ void MissionCommandTree::_collapseHierarchy(const MissionCommandList* } } -void MissionCommandTree::_buildAllCommands(Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode) +void MissionCommandTree::_buildAllCommands(Vehicle *vehicle, QGCMAVLink::VehicleClass_t vtolMode) { QGCMAVLink::FirmwareClass_t firmwareClass; QGCMAVLink::VehicleClass_t vehicleClass; @@ -94,7 +92,7 @@ void MissionCommandTree::_buildAllCommands(Vehicle* vehicle, QGCMAVLink::Vehicle return; } - QMap& collapsedTree = _allCommands[firmwareClass][vehicleClass]; + QMap &collapsedTree = _allCommands[firmwareClass][vehicleClass]; // Base of the tree is all commands _collapseHierarchy(_staticCommandTree[MAV_AUTOPILOT_GENERIC][QGCMAVLink::VehicleClassGeneric], collapsedTree); @@ -116,18 +114,19 @@ void MissionCommandTree::_buildAllCommands(Vehicle* vehicle, QGCMAVLink::Vehicle // Build category list from supported commands QList supportedCommands = vehicle->firmwarePlugin()->supportedMissionCommands(vehicleClass); - for (MAV_CMD cmd: collapsedTree.keys()) { + for (const MAV_CMD cmd: collapsedTree.keys()) { if (supportedCommands.contains(cmd)) { - QString newCategory = collapsedTree[cmd]->category(); + const QString newCategory = collapsedTree[cmd]->category(); if (!_supportedCategories[firmwareClass][vehicleClass].contains(newCategory)) { _supportedCategories[firmwareClass][vehicleClass].append(newCategory); } } } + _supportedCategories[firmwareClass][vehicleClass].append(_allCommandsCategory); } -QStringList MissionCommandTree::_availableCategoriesForVehicle(Vehicle* vehicle) +QStringList MissionCommandTree::_availableCategoriesForVehicle(Vehicle *vehicle) { QGCMAVLink::FirmwareClass_t firmwareClass; QGCMAVLink::VehicleClass_t vehicleClass; @@ -138,83 +137,82 @@ QStringList MissionCommandTree::_availableCategoriesForVehicle(Vehicle* vehicle) return _supportedCategories[firmwareClass][vehicleClass]; } -QString MissionCommandTree::friendlyName(MAV_CMD command) +QString MissionCommandTree::friendlyName(MAV_CMD command) const { - MissionCommandList * commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; - MissionCommandUIInfo* uiInfo = commandList->getUIInfo(command); + const MissionCommandList *const commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; + const MissionCommandUIInfo *const uiInfo = commandList->getUIInfo(command); - if (uiInfo) { - return uiInfo->friendlyName(); - } else { - return QStringLiteral("MAV_CMD(%1)").arg((int)command); - } + return uiInfo ? uiInfo->friendlyName() : QStringLiteral("MAV_CMD(%1)").arg(static_cast(command)); } -QString MissionCommandTree::rawName(MAV_CMD command) +QString MissionCommandTree::rawName(MAV_CMD command) const { - MissionCommandList * commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; - MissionCommandUIInfo* uiInfo = commandList->getUIInfo(command); + const MissionCommandList *const commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; + const MissionCommandUIInfo *const uiInfo = commandList->getUIInfo(command); - if (uiInfo) { - return uiInfo->rawName(); - } else { - return QStringLiteral("MAV_CMD(%1)").arg((int)command); - } + return uiInfo ? uiInfo->rawName() : QStringLiteral("MAV_CMD(%1)").arg(static_cast(command)); } -bool MissionCommandTree::isLandCommand(MAV_CMD command) +bool MissionCommandTree::isLandCommand(MAV_CMD command) const { - MissionCommandList * commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; - MissionCommandUIInfo* uiInfo = commandList->getUIInfo(command); + const MissionCommandList *const commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; + const MissionCommandUIInfo *const uiInfo = commandList->getUIInfo(command); - return uiInfo ? uiInfo->isLandCommand() : false; + return (uiInfo && uiInfo->isLandCommand()); } -bool MissionCommandTree::isTakeoffCommand(MAV_CMD command) +bool MissionCommandTree::isTakeoffCommand(MAV_CMD command) const { - MissionCommandList * commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; - MissionCommandUIInfo* uiInfo = commandList->getUIInfo(command); + const MissionCommandList *const commandList = _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]; + const MissionCommandUIInfo *const uiInfo = commandList->getUIInfo(command); - return uiInfo ? uiInfo->isTakeoffCommand() : false; + return (uiInfo && uiInfo->isTakeoffCommand()); } -const QList& MissionCommandTree::allCommandIds(void) const +const QList &MissionCommandTree::allCommandIds() const { return _staticCommandTree[QGCMAVLink::FirmwareClassGeneric][QGCMAVLink::VehicleClassGeneric]->commandIds(); } -const MissionCommandUIInfo* MissionCommandTree::getUIInfo(Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode, MAV_CMD command) +const MissionCommandUIInfo *MissionCommandTree::getUIInfo(Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode, MAV_CMD command) { QGCMAVLink::FirmwareClass_t firmwareClass; - QGCMAVLink::VehicleClass_t vehicleClass; + QGCMAVLink::VehicleClass_t vehicleClass; _firmwareAndVehicleClassInfo(vehicle, vtolMode, firmwareClass, vehicleClass); _buildAllCommands(vehicle, vtolMode); - const QMap& infoMap = _allCommands[firmwareClass][vehicleClass]; + MissionCommandUIInfo *result = nullptr; + + const QMap &infoMap = _allCommands[firmwareClass][vehicleClass]; if (infoMap.contains(command)) { - return infoMap[command]; - } else { - return nullptr; + result = infoMap[command]; } + + return result; } -QVariantList MissionCommandTree::getCommandsForCategory(Vehicle* vehicle, const QString& category, bool showFlyThroughCommands) +QStringList MissionCommandTree::categoriesForVehicle(Vehicle *vehicle) +{ + return _availableCategoriesForVehicle(vehicle); +} + +QVariantList MissionCommandTree::getCommandsForCategory(Vehicle *vehicle, const QString &category, bool showFlyThroughCommands) { QGCMAVLink::FirmwareClass_t firmwareClass; - QGCMAVLink::VehicleClass_t vehicleClass; + QGCMAVLink::VehicleClass_t vehicleClass; _firmwareAndVehicleClassInfo(vehicle, QGCMAVLink::VehicleClassGeneric, firmwareClass, vehicleClass); _buildAllCommands(vehicle, QGCMAVLink::VehicleClassGeneric); // vehicle can be null in which case _firmwareAndVehicleClassInfo will tell of the firmware/vehicle type for the offline editing vehicle. // We then use that to get a firmware plugin so we can get the list of supported commands. - FirmwarePlugin* firmwarePlugin = FirmwarePluginManager::instance()->firmwarePluginForAutopilot(QGCMAVLink::firmwareClassToAutopilot(firmwareClass), QGCMAVLink::vehicleClassToMavType(vehicleClass)); - QList supportedCommands = firmwarePlugin->supportedMissionCommands(vehicleClass); + const FirmwarePlugin *const firmwarePlugin = FirmwarePluginManager::instance()->firmwarePluginForAutopilot(QGCMAVLink::firmwareClassToAutopilot(firmwareClass), QGCMAVLink::vehicleClassToMavType(vehicleClass)); + const QList supportedCommands = firmwarePlugin->supportedMissionCommands(vehicleClass); + const QMap commandMap = _allCommands[firmwareClass][vehicleClass]; QVariantList list; - QMap commandMap = _allCommands[firmwareClass][vehicleClass]; - for (MAV_CMD command: commandMap.keys()) { + for (const MAV_CMD command: commandMap.keys()) { if (supportedCommands.isEmpty() || supportedCommands.contains(command)) { MissionCommandUIInfo* uiInfo = commandMap[command]; if ((uiInfo->category() == category || category == _allCommandsCategory) && (showFlyThroughCommands || !uiInfo->specifiesCoordinate() || uiInfo->isStandaloneCoordinate())) { @@ -226,11 +224,11 @@ QVariantList MissionCommandTree::getCommandsForCategory(Vehicle* vehicle, const return list; } -void MissionCommandTree::_firmwareAndVehicleClassInfo(Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode, QGCMAVLink::FirmwareClass_t& firmwareClass, QGCMAVLink::VehicleClass_t& vehicleClass) const +void MissionCommandTree::_firmwareAndVehicleClassInfo(Vehicle *vehicle, QGCMAVLink::VehicleClass_t vtolMode, QGCMAVLink::FirmwareClass_t &firmwareClass, QGCMAVLink::VehicleClass_t &vehicleClass) const { firmwareClass = QGCMAVLink::firmwareClass(vehicle->firmwareType()); vehicleClass = QGCMAVLink::vehicleClass(vehicle->vehicleType()); - if (vehicleClass == QGCMAVLink::VehicleClassVTOL && vtolMode != QGCMAVLink::VehicleClassGeneric) { + if ((vehicleClass == QGCMAVLink::VehicleClassVTOL) && (vtolMode != QGCMAVLink::VehicleClassGeneric)) { vehicleClass = vtolMode; } } diff --git a/src/MissionManager/MissionCommandTree.h b/src/MissionManager/MissionCommandTree.h index ed4b46deccd..b33b52a4d63 100644 --- a/src/MissionManager/MissionCommandTree.h +++ b/src/MissionManager/MissionCommandTree.h @@ -9,18 +9,17 @@ #pragma once -#include "QGCToolbox.h" #include "QGCMAVLink.h" -#include +#include #include +#include +#include +#include -class MissionCommandUIInfo; class MissionCommandList; -class SettingsManager; -#ifdef UNITTEST_BUILD class MissionCommandTreeTest; -#endif +class MissionCommandUIInfo; class Vehicle; /// Manages a hierarchy of MissionCommandUIInfo. @@ -42,57 +41,63 @@ class Vehicle; /// When ui info is requested for a specific vehicle the static hierarchy in _staticCommandTree is collapsed into the set of available commands in /// _allCommands taking into account the appropriate set of overrides for the MAV_AUTOPILOT/MAV_TYPE combination associated with the vehicle. /// -class MissionCommandTree : public QGCTool +class MissionCommandTree : public QObject { Q_OBJECT - + QML_ELEMENT + QML_UNCREATABLE("") + Q_MOC_INCLUDE("Vehicle.h") + + friend class MissionCommandTreeTest; + public: - MissionCommandTree(QGCApplication* app, QGCToolbox* toolbox, bool unitTest = false); + /// Constructs an MissionCommandTree object. + /// @param unitTest Unit Tests are Running. + /// @param parent The parent QObject. + explicit MissionCommandTree(bool unitTest = false, QObject *parent = nullptr); - /// Returns the friendly name for the specified command - QString friendlyName(MAV_CMD command); + /// Destructor for the MissionCommandTree class. + ~MissionCommandTree(); - /// Returns the raw name for the specified command - QString rawName(MAV_CMD command); + /// Gets the singleton instance of MissionCommandTree. + /// @return The singleton instance. + static MissionCommandTree *instance(); - bool isLandCommand(MAV_CMD command); - bool isTakeoffCommand(MAV_CMD command); + Q_INVOKABLE QStringList categoriesForVehicle(Vehicle *vehicle); - const QList& allCommandIds(void) const; + /// @param showFlyThroughCommands - true: all commands shows, false: filter out commands which the vehicle flies through (specifiedCoordinate=true, standaloneCoordinate=false) + Q_INVOKABLE QVariantList getCommandsForCategory(Vehicle *vehicle, const QString &category, bool showFlyThroughCommands); - Q_INVOKABLE QStringList categoriesForVehicle(Vehicle* vehicle) { return _availableCategoriesForVehicle(vehicle); } + /// Returns the friendly name for the specified command + QString friendlyName(MAV_CMD command) const; - const MissionCommandUIInfo* getUIInfo(Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode, MAV_CMD command); + /// Returns the raw name for the specified command + QString rawName(MAV_CMD command) const; - /// @param showFlyThroughCommands - true: all commands shows, false: filter out commands which the vehicle flies through (specifiedCoordinate=true, standaloneCoordinate=false) - Q_INVOKABLE QVariantList getCommandsForCategory(Vehicle* vehicle, const QString& category, bool showFlyThroughCommands); + bool isLandCommand(MAV_CMD command) const; + bool isTakeoffCommand(MAV_CMD command) const; - // Overrides from QGCTool - virtual void setToolbox(QGCToolbox* toolbox); + const QList &allCommandIds() const; -private: - void _collapseHierarchy (const MissionCommandList* cmdList, QMap& collapsedTree); - void _buildAllCommands (Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode); - QStringList _availableCategoriesForVehicle (Vehicle* vehicle); - void _firmwareAndVehicleClassInfo (Vehicle* vehicle, QGCMAVLink::VehicleClass_t vtolMode, QGCMAVLink::FirmwareClass_t& firmwareClass, QGCMAVLink::VehicleClass_t& vehicleClass) const; + const MissionCommandUIInfo *getUIInfo(Vehicle *vehicle, QGCMAVLink::VehicleClass_t vtolMode, MAV_CMD command); private: - QString _allCommandsCategory; ///< Category which contains all available commands - QList _allCommandIds; ///< List of all known command ids (not vehicle specific) - SettingsManager* _settingsManager; - bool _unitTest; ///< true: running in unit test mode + /// Add the next level of the hierarchy to a collapsed tree. + /// @param cmdList List of mission commands to collapse into ui info + /// @param collapsedTree Tree we are collapsing into + void _collapseHierarchy(const MissionCommandList *cmdList, QMap &collapsedTree) const; + void _buildAllCommands(Vehicle *vehicle, QGCMAVLink::VehicleClass_t vtolMode); + QStringList _availableCategoriesForVehicle(Vehicle *vehicle); + void _firmwareAndVehicleClassInfo(Vehicle *vehicle, QGCMAVLink::VehicleClass_t vtolMode, QGCMAVLink::FirmwareClass_t &firmwareClass, QGCMAVLink::VehicleClass_t &vehicleClass) const; + + const QString _allCommandsCategory = tr("All commands"); ///< Category which contains all available commands /// Full hierarchy - QMap> _staticCommandTree; + QMap> _staticCommandTree; /// Collapsed hierarchy for specific vehicle type - QMap>> _allCommands; + QMap>> _allCommands; /// Collapsed hierarchy for specific vehicle type - QMap> _supportedCategories; - - -#ifdef UNITTEST_BUILD - friend class MissionCommandTreeTest; -#endif + QMap> _supportedCategories; }; diff --git a/src/MissionManager/MissionController.cc b/src/MissionManager/MissionController.cc index a2034c75b01..8754f4abd01 100644 --- a/src/MissionManager/MissionController.cc +++ b/src/MissionManager/MissionController.cc @@ -306,7 +306,7 @@ VisualMissionItem* MissionController::_insertSimpleMissionItemWorker(QGeoCoordin _initVisualItem(newItem); if (newItem->specifiesAltitude()) { - if (!qgcApp()->toolbox()->missionCommandTree()->isLandCommand(command)) { + if (!MissionCommandTree::instance()->isLandCommand(command)) { double prevAltitude; QGroundControlQmlGlobal::AltMode prevAltMode; diff --git a/src/MissionManager/MissionManager.cc b/src/MissionManager/MissionManager.cc index 3b8ef5fc935..d6f41ee83ba 100644 --- a/src/MissionManager/MissionManager.cc +++ b/src/MissionManager/MissionManager.cc @@ -96,11 +96,11 @@ void MissionManager::generateResumeMission(int resumeIndex) resumeIndex = qMax(0, qMin(resumeIndex, _missionItems.count() - 1)); // Adjust resume index to be a location based command - const MissionCommandUIInfo* uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(_vehicle, _vehicle->vehicleClass(), _missionItems[resumeIndex]->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_vehicle, _vehicle->vehicleClass(), _missionItems[resumeIndex]->command()); if (!uiInfo || uiInfo->isStandaloneCoordinate() || !uiInfo->specifiesCoordinate()) { // We have to back up to the last command which the vehicle flies through while (--resumeIndex > 0) { - uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(_vehicle, _vehicle->vehicleClass(), _missionItems[resumeIndex]->command()); + uiInfo = MissionCommandTree::instance()->getUIInfo(_vehicle, _vehicle->vehicleClass(), _missionItems[resumeIndex]->command()); if (uiInfo && (uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate())) { // Found it break; @@ -135,7 +135,7 @@ void MissionManager::generateResumeMission(int resumeIndex) int prefixCommandCount = 0; for (int i=0; i<_missionItems.count(); i++) { MissionItem* oldItem = _missionItems[i]; - const MissionCommandUIInfo* uiInfo = qgcApp()->toolbox()->missionCommandTree()->getUIInfo(_vehicle, _vehicle->vehicleClass(), oldItem->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_vehicle, _vehicle->vehicleClass(), oldItem->command()); if ((i == 0 && addHomePosition) || i >= resumeIndex || includedResumeCommands.contains(oldItem->command()) || (uiInfo && uiInfo->isTakeoffCommand())) { if (i < resumeIndex) { prefixCommandCount++; diff --git a/src/MissionManager/PlanManager.cc b/src/MissionManager/PlanManager.cc index 9174a40b783..6976616585f 100644 --- a/src/MissionManager/PlanManager.cc +++ b/src/MissionManager/PlanManager.cc @@ -20,7 +20,6 @@ QGC_LOGGING_CATEGORY(PlanManagerLog, "PlanManagerLog") PlanManager::PlanManager(Vehicle* vehicle, MAV_MISSION_TYPE planType) : QObject (vehicle) , _vehicle (vehicle) - , _missionCommandTree (qgcApp()->toolbox()->missionCommandTree()) , _planType (planType) , _ackTimeoutTimer (nullptr) , _expectedAck (AckNone) @@ -697,7 +696,7 @@ QString PlanManager::_lastMissionReqestString(MAV_MISSION_RESULT result) if (_lastMissionRequest >= 0 && _lastMissionRequest < _writeMissionItems.count()) { MissionItem* item = _writeMissionItems[_lastMissionRequest]; - prefix = tr("Item #%1 Command: %2").arg(_lastMissionRequest).arg(_missionCommandTree->friendlyName(item->command())); + prefix = tr("Item #%1 Command: %2").arg(_lastMissionRequest).arg(MissionCommandTree::instance()->friendlyName(item->command())); switch (result) { case MAV_MISSION_UNSUPPORTED_FRAME: diff --git a/src/MissionManager/PlanManager.h b/src/MissionManager/PlanManager.h index 2745bb13fcc..bcf3502b450 100644 --- a/src/MissionManager/PlanManager.h +++ b/src/MissionManager/PlanManager.h @@ -17,7 +17,6 @@ #include "QGCMAVLink.h" class Vehicle; -class MissionCommandTree; Q_DECLARE_LOGGING_CATEGORY(PlanManagerLog) @@ -133,7 +132,6 @@ private slots: protected: Vehicle* _vehicle = nullptr; - MissionCommandTree* _missionCommandTree = nullptr; MAV_MISSION_TYPE _planType; QTimer* _ackTimeoutTimer = nullptr; diff --git a/src/MissionManager/SimpleMissionItem.cc b/src/MissionManager/SimpleMissionItem.cc index 0c9edf661fc..f754c891676 100644 --- a/src/MissionManager/SimpleMissionItem.cc +++ b/src/MissionManager/SimpleMissionItem.cc @@ -33,7 +33,6 @@ FactMetaData* SimpleMissionItem::_longitudeMetaData = nullptr; SimpleMissionItem::SimpleMissionItem(PlanMasterController* masterController, bool flyView, bool forLoad) : VisualMissionItem (masterController, flyView) - , _commandTree (qgcApp()->toolbox()->missionCommandTree()) , _supportedCommandFact (0, "Command:", FactMetaData::valueTypeUint32) , _altitudeFact (0, "Altitude", FactMetaData::valueTypeDouble) , _amslAltAboveTerrainFact (0, "Alt above terrain", FactMetaData::valueTypeDouble) @@ -62,7 +61,6 @@ SimpleMissionItem::SimpleMissionItem(PlanMasterController* masterController, boo SimpleMissionItem::SimpleMissionItem(PlanMasterController* masterController, bool flyView, const MissionItem& missionItem) : VisualMissionItem (masterController, flyView) , _missionItem (missionItem) - , _commandTree (qgcApp()->toolbox()->missionCommandTree()) , _supportedCommandFact (0, "Command:", FactMetaData::valueTypeUint32) , _altitudeFact (0, "Altitude", FactMetaData::valueTypeDouble) , _amslAltAboveTerrainFact (0, "Alt above terrain", FactMetaData::valueTypeDouble) @@ -209,9 +207,8 @@ void SimpleMissionItem::_setupMetaData(void) enumStrings.clear(); enumValues.clear(); - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); - for (const MAV_CMD command: commandTree->allCommandIds()) { - enumStrings.append(commandTree->rawName(command)); + for (const MAV_CMD command: MissionCommandTree::instance()->allCommandIds()) { + enumStrings.append(MissionCommandTree::instance()->rawName(command)); enumValues.append(QVariant((int)command)); } _commandMetaData = new FactMetaData(FactMetaData::valueTypeUint32); @@ -329,7 +326,7 @@ bool SimpleMissionItem::load(const QJsonObject& json, int sequenceNumber, QStrin bool SimpleMissionItem::isStandaloneCoordinate(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->isStandaloneCoordinate(); } else { @@ -339,7 +336,7 @@ bool SimpleMissionItem::isStandaloneCoordinate(void) const bool SimpleMissionItem::specifiesCoordinate(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->specifiesCoordinate(); } else { @@ -349,7 +346,7 @@ bool SimpleMissionItem::specifiesCoordinate(void) const bool SimpleMissionItem::specifiesAltitudeOnly(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->specifiesAltitudeOnly(); } else { @@ -359,7 +356,7 @@ bool SimpleMissionItem::specifiesAltitudeOnly(void) const QString SimpleMissionItem::commandDescription(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->description(); } else { @@ -370,7 +367,7 @@ QString SimpleMissionItem::commandDescription(void) const QString SimpleMissionItem::commandName(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->friendlyName(); } else { @@ -445,7 +442,7 @@ void SimpleMissionItem::_rebuildTextFieldFacts(void) Fact* rgParamFacts[7] = { &_missionItem._param1Fact, &_missionItem._param2Fact, &_missionItem._param3Fact, &_missionItem._param4Fact, &_missionItem._param5Fact, &_missionItem._param6Fact, &_missionItem._param7Fact }; FactMetaData* rgParamMetaData[7] = { &_param1MetaData, &_param2MetaData, &_param3MetaData, &_param4MetaData, &_param5MetaData, &_param6MetaData, &_param7MetaData }; - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, command); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, command); if (uiInfo) { for (int i=1; i<=7; i++) { @@ -489,7 +486,7 @@ void SimpleMissionItem::_rebuildNaNFacts(void) Fact* rgParamFacts[7] = { &_missionItem._param1Fact, &_missionItem._param2Fact, &_missionItem._param3Fact, &_missionItem._param4Fact, &_missionItem._param5Fact, &_missionItem._param6Fact, &_missionItem._param7Fact }; FactMetaData* rgParamMetaData[7] = { &_param1MetaData, &_param2MetaData, &_param3MetaData, &_param4MetaData, &_param5MetaData, &_param6MetaData, &_param7MetaData }; - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, command); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, command); if (uiInfo) { for (int i=1; i<=7; i++) { @@ -530,7 +527,7 @@ bool SimpleMissionItem::specifiesAltitude(void) const bool SimpleMissionItem::isLoiterItem() const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, (MAV_CMD)command()); if (uiInfo) { return uiInfo->isLoiterCommand(); } else { @@ -572,7 +569,7 @@ void SimpleMissionItem::_rebuildComboBoxFacts(void) for (int i=1; i<=7; i++) { bool showUI; - const MissionCmdParamInfo* paramInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, command)->getParamInfo(i, showUI); + const MissionCmdParamInfo* paramInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, command)->getParamInfo(i, showUI); if (showUI && paramInfo && paramInfo->enumStrings().count() != 0) { Fact* paramFact = rgParamFacts[i-1]; @@ -601,7 +598,7 @@ void SimpleMissionItem::_rebuildFacts(void) bool SimpleMissionItem::friendlyEditAllowed(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, static_cast(command())); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, static_cast(command())); if (uiInfo && uiInfo->friendlyEdit()) { if (!_missionItem.autoContinue()) { return false; @@ -783,7 +780,7 @@ void SimpleMissionItem::_setDefaultsForCommand(void) } MAV_CMD command = static_cast(this->command()); - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, command); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, command); if (uiInfo) { for (int i=1; i<=7; i++) { bool showUI; @@ -820,7 +817,7 @@ void SimpleMissionItem::_sendFriendlyEditAllowedChanged(void) QString SimpleMissionItem::category(void) const { - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, static_cast(command())); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, static_cast(command())); return uiInfo ? uiInfo->category() : QString(); } @@ -975,7 +972,7 @@ void SimpleMissionItem::appendMissionItems(QList& items, QObject* void SimpleMissionItem::applyNewAltitude(double newAltitude) { MAV_CMD command = static_cast(this->command()); - const MissionCommandUIInfo* uiInfo = _commandTree->getUIInfo(_controllerVehicle, _previousVTOLMode, command); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, _previousVTOLMode, command); if (uiInfo && (uiInfo->specifiesCoordinate() || uiInfo->specifiesAltitudeOnly())) { switch (static_cast(this->command())) { @@ -1043,7 +1040,7 @@ void SimpleMissionItem::_possibleAdditionalTimeDelayChanged(void) bool SimpleMissionItem::isLandCommand(void) const { - return _commandTree->isLandCommand(static_cast(this->command())); + return MissionCommandTree::instance()->isLandCommand(static_cast(this->command())); } QGeoCoordinate SimpleMissionItem::coordinate(void) const diff --git a/src/MissionManager/SimpleMissionItem.h b/src/MissionManager/SimpleMissionItem.h index e452f18b5d3..5f281b356c4 100644 --- a/src/MissionManager/SimpleMissionItem.h +++ b/src/MissionManager/SimpleMissionItem.h @@ -14,7 +14,6 @@ #include "MissionItem.h" #include "QGroundControlQmlGlobal.h" -class MissionCommandTree; class SpeedSection; class CameraSection; @@ -183,7 +182,6 @@ private slots: SpeedSection* _speedSection = nullptr; CameraSection* _cameraSection = nullptr; - MissionCommandTree* _commandTree = nullptr; bool _syncingHeadingDegreesAndParam4 = false; ///< true: already in a sync signal, prevents signal loop Fact _supportedCommandFact; diff --git a/src/MissionManager/TakeoffMissionItem.cc b/src/MissionManager/TakeoffMissionItem.cc index 1a0bab9ec22..769d502ea68 100644 --- a/src/MissionManager/TakeoffMissionItem.cc +++ b/src/MissionManager/TakeoffMissionItem.cc @@ -115,7 +115,7 @@ void TakeoffMissionItem::setCoordinate(const QGeoCoordinate& coordinate) bool TakeoffMissionItem::isTakeoffCommand(MAV_CMD command) { - return qgcApp()->toolbox()->missionCommandTree()->isTakeoffCommand(command); + return MissionCommandTree::instance()->isTakeoffCommand(command); } void TakeoffMissionItem::_initLaunchTakeoffAtSameLocation(void) diff --git a/src/MissionManager/TransectStyleComplexItem.cc b/src/MissionManager/TransectStyleComplexItem.cc index 9debf423624..53d8f2582ca 100644 --- a/src/MissionManager/TransectStyleComplexItem.cc +++ b/src/MissionManager/TransectStyleComplexItem.cc @@ -293,9 +293,8 @@ bool TransectStyleComplexItem::_load(const QJsonObject& complexObject, bool forP // We have to grovel through mission items to determine min/max alt _minAMSLAltitude = qQNaN(); _maxAMSLAltitude = qQNaN(); - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); for (const MissionItem* missionItem: _loadedMissionItems) { - const MissionCommandUIInfo* uiInfo = commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, missionItem->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, missionItem->command()); if (uiInfo && uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate()) { _minAMSLAltitude = std::fmin(_minAMSLAltitude, missionItem->param7()); _maxAMSLAltitude = std::fmax(_maxAMSLAltitude, missionItem->param7()); @@ -605,10 +604,9 @@ void TransectStyleComplexItem::_queryMissionItemCoordHeights(void) } // We need terrain heights below each mission item we fly through which is terrain frame - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); for (const MissionItem* missionItem: _loadedMissionItems) { if (missionItem->frame() == MAV_FRAME_GLOBAL_TERRAIN_ALT) { - const MissionCommandUIInfo* uiInfo = commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, missionItem->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, missionItem->command()); if (uiInfo && uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate()) { _rgFlyThroughMissionItemCoords.append(missionItem->coordinate()); } @@ -1346,10 +1344,9 @@ double TransectStyleComplexItem::amslEntryAlt(void) const case QGroundControlQmlGlobal::AltitudeModeTerrainFrame: if (_loadedMissionItems.count()) { // The first item might not be a waypoint we have to find it. - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); for (int i=0; i<_loadedMissionItems.count(); i++) { MissionItem* item = _loadedMissionItems[i]; - const MissionCommandUIInfo* uiInfo = commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, item->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, item->command()); if (uiInfo && uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate()) { if (_cameraCalc.distanceMode() == QGroundControlQmlGlobal::AltitudeModeCalcAboveTerrain) { // AltitudeModeCalcAboveTerrain has AMSL alt in param 7 @@ -1391,10 +1388,9 @@ double TransectStyleComplexItem::amslExitAlt(void) const case QGroundControlQmlGlobal::AltitudeModeTerrainFrame: if (_loadedMissionItems.count()) { // The last item might not be a waypoint we have to find it. - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); for (int i=_loadedMissionItems.count()-1; i>0; i--) { MissionItem* item = _loadedMissionItems[i]; - const MissionCommandUIInfo* uiInfo = commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, item->command()); + const MissionCommandUIInfo* uiInfo = MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, item->command()); if (uiInfo && uiInfo->specifiesCoordinate() && !uiInfo->isStandaloneCoordinate()) { if (_cameraCalc.distanceMode() == QGroundControlQmlGlobal::AltitudeModeCalcAboveTerrain) { // AltitudeModeCalcAboveTerrain has AMSL alt in param 7 diff --git a/src/QGCApplication.cc b/src/QGCApplication.cc index 3f1a248019e..84ed6a28ec0 100644 --- a/src/QGCApplication.cc +++ b/src/QGCApplication.cc @@ -64,7 +64,6 @@ #include "HorizontalFactValueGrid.h" #include "InstrumentValueData.h" #include "AppMessages.h" -#include "MissionCommandTree.h" #include "QGCMapPolygon.h" #include "QGCMapCircle.h" #include "ParameterManager.h" diff --git a/src/QGCToolbox.cc b/src/QGCToolbox.cc index 719401bb437..24b6f26d12f 100644 --- a/src/QGCToolbox.cc +++ b/src/QGCToolbox.cc @@ -10,7 +10,6 @@ #include "LinkManager.h" #include "MAVLinkProtocol.h" -#include "MissionCommandTree.h" #include "MultiVehicleManager.h" #include "VideoManager.h" #include "MAVLinkLogManager.h" @@ -39,7 +38,6 @@ QGCToolbox::QGCToolbox(QGCApplication* app) _scanAndLoadPlugins(app); _linkManager = new LinkManager (app, this); _mavlinkProtocol = new MAVLinkProtocol (app, this); - _missionCommandTree = new MissionCommandTree (app, this); _multiVehicleManager = new MultiVehicleManager (app, this); _videoManager = new VideoManager (app, this); @@ -60,7 +58,6 @@ void QGCToolbox::setChildToolboxes(void) _corePlugin->setToolbox(this); _linkManager->setToolbox(this); _mavlinkProtocol->setToolbox(this); - _missionCommandTree->setToolbox(this); _multiVehicleManager->setToolbox(this); _videoManager->setToolbox(this); _mavlinkLogManager->setToolbox(this); diff --git a/src/QGCToolbox.h b/src/QGCToolbox.h index e7e8d50a22b..1ba8dcc66ee 100644 --- a/src/QGCToolbox.h +++ b/src/QGCToolbox.h @@ -15,7 +15,6 @@ class LinkManager; class MAVLinkProtocol; -class MissionCommandTree; class MultiVehicleManager; class QGCApplication; class VideoManager; @@ -38,7 +37,6 @@ class QGCToolbox : public QObject { LinkManager* linkManager () { return _linkManager; } MAVLinkProtocol* mavlinkProtocol () { return _mavlinkProtocol; } - MissionCommandTree* missionCommandTree () { return _missionCommandTree; } MultiVehicleManager* multiVehicleManager () { return _multiVehicleManager; } VideoManager* videoManager () { return _videoManager; } MAVLinkLogManager* mavlinkLogManager () { return _mavlinkLogManager; } @@ -57,7 +55,6 @@ class QGCToolbox : public QObject { LinkManager* _linkManager = nullptr; MAVLinkProtocol* _mavlinkProtocol = nullptr; - MissionCommandTree* _missionCommandTree = nullptr; MultiVehicleManager* _multiVehicleManager = nullptr; VideoManager* _videoManager = nullptr; MAVLinkLogManager* _mavlinkLogManager = nullptr; diff --git a/src/QmlControls/QGroundControlQmlGlobal.cc b/src/QmlControls/QGroundControlQmlGlobal.cc index 8e42c29bec6..af0c7530133 100644 --- a/src/QmlControls/QGroundControlQmlGlobal.cc +++ b/src/QmlControls/QGroundControlQmlGlobal.cc @@ -17,6 +17,7 @@ #include "PositionManager.h" #include "QGCMapEngineManager.h" #include "ADSBVehicleManager.h" +#include "MissionCommandTree.h" #ifndef NO_SERIAL_LINK #include "GPSManager.h" #include "GPSRtk.h" @@ -37,6 +38,7 @@ QGroundControlQmlGlobal::QGroundControlQmlGlobal(QGCApplication* app, QGCToolbox , _mapEngineManager(QGCMapEngineManager::instance()) , _adsbVehicleManager(ADSBVehicleManager::instance()) , _qgcPositionManager(QGCPositionManager::instance()) + , _missionCommandTree(MissionCommandTree::instance()) { // We clear the parent on this object since we run into shutdown problems caused by hybrid qml app. Instead we let it leak on shutdown. // setParent(nullptr); @@ -79,7 +81,6 @@ void QGroundControlQmlGlobal::setToolbox(QGCToolbox* toolbox) _linkManager = toolbox->linkManager(); _multiVehicleManager = toolbox->multiVehicleManager(); - _missionCommandTree = toolbox->missionCommandTree(); _videoManager = toolbox->videoManager(); _mavlinkLogManager = toolbox->mavlinkLogManager(); _corePlugin = toolbox->corePlugin(); diff --git a/src/QmlControls/QGroundControlQmlGlobal.h b/src/QmlControls/QGroundControlQmlGlobal.h index 33ba64129fb..71b9a1ef8f0 100644 --- a/src/QmlControls/QGroundControlQmlGlobal.h +++ b/src/QmlControls/QGroundControlQmlGlobal.h @@ -260,11 +260,11 @@ class QGroundControlQmlGlobal : public QGCTool QGCMapEngineManager* _mapEngineManager = nullptr; ADSBVehicleManager* _adsbVehicleManager = nullptr; QGCPositionManager* _qgcPositionManager = nullptr; + MissionCommandTree* _missionCommandTree = nullptr; double _flightMapInitialZoom = 17.0; LinkManager* _linkManager = nullptr; MultiVehicleManager* _multiVehicleManager = nullptr; - MissionCommandTree* _missionCommandTree = nullptr; VideoManager* _videoManager = nullptr; MAVLinkLogManager* _mavlinkLogManager = nullptr; QGCCorePlugin* _corePlugin = nullptr; diff --git a/src/Vehicle/Vehicle.cc b/src/Vehicle/Vehicle.cc index 019c5ea3f51..fc202f1715e 100644 --- a/src/Vehicle/Vehicle.cc +++ b/src/Vehicle/Vehicle.cc @@ -2511,7 +2511,7 @@ void Vehicle::_sendMavCommandWorker( // which ack was associated with which command. if ((targetCompId == MAV_COMP_ID_ALL) || (isMavCommandPending(targetCompId, command) && !_commandCanBeDuplicated(command))) { bool compIdAll = targetCompId == MAV_COMP_ID_ALL; - QString rawCommandName = _toolbox->missionCommandTree()->rawName(command); + QString rawCommandName = MissionCommandTree::instance()->rawName(command); qCDebug(VehicleLog) << QStringLiteral("_sendMavCommandWorker failing %1").arg(compIdAll ? "MAV_COMP_ID_ALL not supported" : "duplicate command") << rawCommandName << param1 << param2 << param3 << param4 << param5 << param6 << param7; @@ -2568,7 +2568,7 @@ void Vehicle::_sendMavCommandFromList(int index) { MavCommandListEntry_t commandEntry = _mavCommandList[index]; - QString rawCommandName = _toolbox->missionCommandTree()->rawName(commandEntry.command); + QString rawCommandName = MissionCommandTree::instance()->rawName(commandEntry.command); if (++_mavCommandList[index].tryCount > commandEntry.maxTries) { qCDebug(VehicleLog) << Q_FUNC_INFO << "giving up after max retries" << rawCommandName; @@ -2668,7 +2668,7 @@ void Vehicle::_handleCommandAck(mavlink_message_t& message) mavlink_command_ack_t ack; mavlink_msg_command_ack_decode(&message, &ack); - QString rawCommandName =_toolbox->missionCommandTree()->rawName(static_cast(ack.command)); + QString rawCommandName = MissionCommandTree::instance()->rawName(static_cast(ack.command)); qCDebug(VehicleLog) << QStringLiteral("_handleCommandAck command(%1) result(%2)").arg(rawCommandName).arg(QGCMAVLink::mavResultToString(static_cast(ack.result))); if (ack.command == MAV_CMD_DO_SET_ROI_LOCATION) { diff --git a/test/MissionManager/CameraSectionTest.cc b/test/MissionManager/CameraSectionTest.cc index dbb161370c5..3f3d570defd 100644 --- a/test/MissionManager/CameraSectionTest.cc +++ b/test/MissionManager/CameraSectionTest.cc @@ -1062,8 +1062,6 @@ void CameraSectionTest::_resetSection(void) /// Test that we can scan the commands associated with the camera section in various orders/combinations. void CameraSectionTest::_testScanForMultipleItems(void) { - MissionCommandTree* commandTree = qgcApp()->toolbox()->missionCommandTree(); - QCOMPARE(_cameraSection->available(), true); int scanIndex = 0; @@ -1086,7 +1084,7 @@ void CameraSectionTest::_testScanForMultipleItems(void) item2->missionItem() = cameraItem->missionItem(); visualItems.append(item1); visualItems.append(item2); - //qDebug() << commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item1->command())->rawName() << commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item2->command())->rawName(); + //qDebug() << MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item1->command())->rawName() << MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item2->command())->rawName(); scanIndex = 0; QCOMPARE(_cameraSection->scanForSection(&visualItems, scanIndex), true); @@ -1107,7 +1105,7 @@ void CameraSectionTest::_testScanForMultipleItems(void) item2->missionItem() = cameraItem->missionItem(); visualItems.append(item1); visualItems.append(item2); - qDebug() << commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item1->command())->rawName() << commandTree->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item2->command())->rawName();; + qDebug() << MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item1->command())->rawName() << MissionCommandTree::instance()->getUIInfo(_controllerVehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)item2->command())->rawName();; scanIndex = 0; QCOMPARE(_cameraSection->scanForSection(&visualItems, scanIndex), true); diff --git a/test/MissionManager/MissionCommandTreeTest.cc b/test/MissionManager/MissionCommandTreeTest.cc index 7ad8d1463ed..a7298861e87 100644 --- a/test/MissionManager/MissionCommandTreeTest.cc +++ b/test/MissionManager/MissionCommandTreeTest.cc @@ -8,48 +8,34 @@ ****************************************************************************/ #include "MissionCommandTreeTest.h" -#include "QGCApplication.h" #include "MissionCommandUIInfo.h" #include "MissionCommandList.h" #include "MissionCommandTree.h" #include "Vehicle.h" -#include "FirmwarePluginManager.h" #include -MissionCommandTreeTest::MissionCommandTreeTest(void) +void MissionCommandTreeTest::init() { - + _commandTree = new MissionCommandTree(true /* unitTest */, this); } -void MissionCommandTreeTest::init(void) +QString MissionCommandTreeTest::_rawName(int id) const { - _commandTree = new MissionCommandTree(qgcApp(), qgcApp()->toolbox(), true /* unitTest */); - _commandTree->setToolbox(qgcApp()->toolbox()); + return QStringLiteral("UNITTEST_%1").arg(id); } -void MissionCommandTreeTest::cleanup(void) +QString MissionCommandTreeTest::_friendlyName(int id) const { - delete _commandTree; + return QStringLiteral("Unit Test %1").arg(id); } -QString MissionCommandTreeTest::_rawName(int id) +QString MissionCommandTreeTest::_paramLabel(int index) const { - return QString("UNITTEST_%1").arg(id); + return QStringLiteral("param%1").arg(index); } -QString MissionCommandTreeTest::_friendlyName(int id) -{ - return QString("Unit Test %1").arg(id); -} - -QString MissionCommandTreeTest::_paramLabel(int index) -{ - return QString("param%1").arg(index); -} - -/// Verifies that all values have been set -void MissionCommandTreeTest::_checkFullInfoMap(const MissionCommandUIInfo* uiInfo) +void MissionCommandTreeTest::_checkFullInfoMap(const MissionCommandUIInfo *const uiInfo) { QVERIFY(uiInfo->_infoMap.contains(MissionCommandUIInfo::_rawNameJsonKey)); QVERIFY(uiInfo->_infoMap.contains(MissionCommandUIInfo::_categoryJsonKey)); @@ -60,12 +46,11 @@ void MissionCommandTreeTest::_checkFullInfoMap(const MissionCommandUIInfo* uiInf QVERIFY(uiInfo->_infoMap.contains(MissionCommandUIInfo::_specifiesCoordinateJsonKey)); } -// Verifies that values match settings for base tree -void MissionCommandTreeTest::_checkBaseValues(const MissionCommandUIInfo* uiInfo, int command) +void MissionCommandTreeTest::_checkBaseValues(const MissionCommandUIInfo *const uiInfo, int command) { QVERIFY(uiInfo != nullptr); _checkFullInfoMap(uiInfo); - QCOMPARE(uiInfo->command(), (MAV_CMD)command); + QCOMPARE(uiInfo->command(), static_cast(command)); QCOMPARE(uiInfo->rawName(), _rawName(command)); QCOMPARE(uiInfo->category(), QStringLiteral("category")); QCOMPARE(uiInfo->description(), QStringLiteral("description")); @@ -75,7 +60,7 @@ void MissionCommandTreeTest::_checkBaseValues(const MissionCommandUIInfo* uiInfo QCOMPARE(uiInfo->specifiesCoordinate(), true); for (int i=1; i<=7; i++) { bool showUI; - const MissionCmdParamInfo* paramInfo = uiInfo->getParamInfo(i, showUI); + const MissionCmdParamInfo *const paramInfo = uiInfo->getParamInfo(i, showUI); QVERIFY(showUI); QVERIFY(paramInfo); QCOMPARE(paramInfo->decimalPlaces(), 1); @@ -92,13 +77,12 @@ void MissionCommandTreeTest::_checkBaseValues(const MissionCommandUIInfo* uiInfo } } -// Verifies that values match settings for an override void MissionCommandTreeTest::_checkOverrideParamValues(const MissionCommandUIInfo* uiInfo, int command, int paramIndex) { - QString overrideString = QString("override fw %1 %2").arg(command).arg(paramIndex); + QString overrideString = QStringLiteral("override fw %1 %2").arg(command).arg(paramIndex); bool showUI; - const MissionCmdParamInfo* paramInfo = uiInfo->getParamInfo(paramIndex, showUI); + const MissionCmdParamInfo *const paramInfo = uiInfo->getParamInfo(paramIndex, showUI); QVERIFY(showUI); QVERIFY(paramInfo); QCOMPARE(paramInfo->decimalPlaces(), 1); @@ -114,7 +98,6 @@ void MissionCommandTreeTest::_checkOverrideParamValues(const MissionCommandUIInf QCOMPARE(paramInfo->units(), overrideString); } -// Verifies that values match settings for an override void MissionCommandTreeTest::_checkOverrideValues(const MissionCommandUIInfo* uiInfo, int command) { bool showUI; @@ -122,7 +105,7 @@ void MissionCommandTreeTest::_checkOverrideValues(const MissionCommandUIInfo* ui QVERIFY(uiInfo != nullptr); _checkFullInfoMap(uiInfo); - QCOMPARE(uiInfo->command(), (MAV_CMD)command); + QCOMPARE(uiInfo->command(), static_cast(command)); QCOMPARE(uiInfo->rawName(), _rawName(command)); QCOMPARE(uiInfo->category(), overrideString); QCOMPARE(uiInfo->description(), overrideString); @@ -141,19 +124,17 @@ void MissionCommandTreeTest::_checkOverrideValues(const MissionCommandUIInfo* ui _checkOverrideParamValues(uiInfo, command, 5); } -void MissionCommandTreeTest::testJsonLoad(void) +void MissionCommandTreeTest::testJsonLoad() { - bool showUI; - // Test loading from the bad command list - MissionCommandList* commandList = _commandTree->_staticCommandTree[MAV_AUTOPILOT_GENERIC][MAV_TYPE_GENERIC]; + MissionCommandList *const commandList = _commandTree->_staticCommandTree[MAV_AUTOPILOT_GENERIC][MAV_TYPE_GENERIC]; QVERIFY(commandList != nullptr); // Command 1 should have all values defaulted, no params - MissionCommandUIInfo* uiInfo = commandList->getUIInfo((MAV_CMD)1); + const MissionCommandUIInfo* uiInfo = commandList->getUIInfo(static_cast(1)); QVERIFY(uiInfo != nullptr); _checkFullInfoMap(uiInfo); - QCOMPARE(uiInfo->command(), (MAV_CMD)1); + QCOMPARE(uiInfo->command(), static_cast(1)); QCOMPARE(uiInfo->rawName(), _rawName(1)); QVERIFY(uiInfo->category() == MissionCommandUIInfo::_advancedCategory); QVERIFY(uiInfo->description().isEmpty()); @@ -161,15 +142,17 @@ void MissionCommandTreeTest::testJsonLoad(void) QCOMPARE(uiInfo->friendlyName(), uiInfo->rawName()); QCOMPARE(uiInfo->isStandaloneCoordinate(), false); QCOMPARE(uiInfo->specifiesCoordinate(), false); + + bool showUI; for (int i=1; i<=7; i++) { QVERIFY(uiInfo->getParamInfo(i, showUI) == nullptr); QCOMPARE(showUI, false); } // Command 2 should all values defaulted for param 1 - uiInfo = commandList->getUIInfo((MAV_CMD)2); + uiInfo = commandList->getUIInfo(static_cast(2)); QVERIFY(uiInfo != nullptr); - const MissionCmdParamInfo* paramInfo = uiInfo->getParamInfo(1, showUI); + const MissionCmdParamInfo *const paramInfo = uiInfo->getParamInfo(1, showUI); QVERIFY(paramInfo); QCOMPARE(showUI, true); QCOMPARE(paramInfo->decimalPlaces(), -1); @@ -185,26 +168,26 @@ void MissionCommandTreeTest::testJsonLoad(void) } // Command 3 should have all values set - _checkBaseValues(commandList->getUIInfo((MAV_CMD)3), 3); + _checkBaseValues(commandList->getUIInfo(static_cast(3)), 3); } -void MissionCommandTreeTest::testOverride(void) +void MissionCommandTreeTest::testOverride() { // Generic/Generic should not have any overrides - Vehicle* vehicle = new Vehicle(MAV_AUTOPILOT_GENERIC, MAV_TYPE_GENERIC, FirmwarePluginManager::instance()); - _checkBaseValues(_commandTree->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)4), 4); + Vehicle* vehicle = new Vehicle(MAV_AUTOPILOT_GENERIC, MAV_TYPE_GENERIC, this); + _checkBaseValues(_commandTree->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, static_cast(4)), 4); delete vehicle; // Generic/FixedWing should have overrides - vehicle = new Vehicle(MAV_AUTOPILOT_GENERIC, MAV_TYPE_FIXED_WING, FirmwarePluginManager::instance()); - _checkOverrideValues(_commandTree->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, (MAV_CMD)4), 4); + vehicle = new Vehicle(MAV_AUTOPILOT_GENERIC, MAV_TYPE_FIXED_WING, this); + _checkOverrideValues(_commandTree->getUIInfo(vehicle, QGCMAVLink::VehicleClassGeneric, static_cast(4)), 4); delete vehicle; } -void MissionCommandTreeTest::testAllTrees(void) +void MissionCommandTreeTest::testAllTrees() { - QList firmwareList; - QList vehicleList; + QList firmwareList; + QList vehicleList; firmwareList << MAV_AUTOPILOT_GENERIC << MAV_AUTOPILOT_PX4 << MAV_AUTOPILOT_ARDUPILOTMEGA; vehicleList << MAV_TYPE_GENERIC << MAV_TYPE_QUADROTOR << MAV_TYPE_FIXED_WING << MAV_TYPE_GROUND_ROVER << MAV_TYPE_SUBMARINE << MAV_TYPE_VTOL_TAILSITTER_QUADROTOR; @@ -212,13 +195,13 @@ void MissionCommandTreeTest::testAllTrees(void) // This will cause all of the variants of collapsed trees to be built for(MAV_AUTOPILOT firmwareType: firmwareList) { for (MAV_TYPE vehicleType: vehicleList) { - if (firmwareType == MAV_AUTOPILOT_ARDUPILOTMEGA && vehicleType == MAV_TYPE_VTOL_TAILSITTER_QUADROTOR) { + if ((firmwareType == MAV_AUTOPILOT_ARDUPILOTMEGA) && (vehicleType == MAV_TYPE_VTOL_TAILSITTER_QUADROTOR)) { // VTOL in ArduPilot shows up as plane so we can test this pair continue; } qDebug() << firmwareType << vehicleType; - Vehicle* vehicle = new Vehicle(firmwareType, vehicleType, FirmwarePluginManager::instance()); - QVERIFY(qgcApp()->toolbox()->missionCommandTree()->getUIInfo(vehicle, QGCMAVLink::VehicleClassMultiRotor, MAV_CMD_NAV_WAYPOINT) != nullptr); + Vehicle *const vehicle = new Vehicle(firmwareType, vehicleType, this); + QVERIFY(MissionCommandTree::instance()->getUIInfo(vehicle, QGCMAVLink::VehicleClassMultiRotor, MAV_CMD_NAV_WAYPOINT) != nullptr); delete vehicle; } } diff --git a/test/MissionManager/MissionCommandTreeTest.h b/test/MissionManager/MissionCommandTreeTest.h index a3ac18ae625..cc06bb1b81f 100644 --- a/test/MissionManager/MissionCommandTreeTest.h +++ b/test/MissionManager/MissionCommandTreeTest.h @@ -7,8 +7,7 @@ * ****************************************************************************/ -#ifndef MissionCommandTreeTest_H -#define MissionCommandTreeTest_H +#pragma once #include "UnitTest.h" @@ -20,27 +19,29 @@ class MissionCommandTreeTest : public UnitTest { Q_OBJECT -public: - MissionCommandTreeTest(void); - private slots: - void init(void); - void cleanup(void); + void init(); - void testJsonLoad(void); - void testOverride(void); - void testAllTrees(void); + void testJsonLoad(); + void testOverride(); + void testAllTrees(); private: - QString _rawName(int id); - QString _friendlyName(int id); - QString _paramLabel(int index); - void _checkFullInfoMap(const MissionCommandUIInfo* uiInfo); - void _checkBaseValues(const MissionCommandUIInfo* uiInfo, int command); - void _checkOverrideValues(const MissionCommandUIInfo* uiInfo, int command); - void _checkOverrideParamValues(const MissionCommandUIInfo* uiInfo, int command, int paramIndex); - - MissionCommandTree* _commandTree; -}; + QString _rawName(int id) const; + QString _friendlyName(int id) const; + QString _paramLabel(int index) const; + + /// Verifies that all values have been set + void _checkFullInfoMap(const MissionCommandUIInfo *uiInfo); + + /// Verifies that values match settings for base tree + void _checkBaseValues(const MissionCommandUIInfo *uiInfo, int command); -#endif + /// Verifies that values match settings for an override + void _checkOverrideValues(const MissionCommandUIInfo *uiInfo, int command); + + // Verifies that values match settings for an override + void _checkOverrideParamValues(const MissionCommandUIInfo *uiInfo, int command, int paramIndex); + + MissionCommandTree *_commandTree = nullptr; +};