Commit 0aea0088 authored by Don Gagne's avatar Don Gagne

Motor Setup/Testing support

parent 6920c117
...@@ -63,6 +63,7 @@ ...@@ -63,6 +63,7 @@
<file alias="LandModeCopter.svg">src/AutoPilotPlugins/PX4/Images/LandModeCopter.svg</file> <file alias="LandModeCopter.svg">src/AutoPilotPlugins/PX4/Images/LandModeCopter.svg</file>
<file alias="LowBattery.svg">src/AutoPilotPlugins/PX4/Images/LowBattery.svg</file> <file alias="LowBattery.svg">src/AutoPilotPlugins/PX4/Images/LowBattery.svg</file>
<file alias="LowBatteryLight.svg">src/AutoPilotPlugins/PX4/Images/LowBatteryLight.svg</file> <file alias="LowBatteryLight.svg">src/AutoPilotPlugins/PX4/Images/LowBatteryLight.svg</file>
<file alias="MotorComponentIcon.png">src/AutoPilotPlugins/Common/MotorComponentIcon.png</file>
<file alias="PowerComponentBattery_01cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_01cell.svg</file> <file alias="PowerComponentBattery_01cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_01cell.svg</file>
<file alias="PowerComponentBattery_02cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_02cell.svg</file> <file alias="PowerComponentBattery_02cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_02cell.svg</file>
<file alias="PowerComponentBattery_03cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_03cell.svg</file> <file alias="PowerComponentBattery_03cell.svg">src/AutoPilotPlugins/PX4/Images/PowerComponentBattery_03cell.svg</file>
......
...@@ -638,6 +638,7 @@ HEADERS+= \ ...@@ -638,6 +638,7 @@ HEADERS+= \
src/AutoPilotPlugins/APM/APMSensorsComponent.h \ src/AutoPilotPlugins/APM/APMSensorsComponent.h \
src/AutoPilotPlugins/APM/APMSensorsComponentController.h \ src/AutoPilotPlugins/APM/APMSensorsComponentController.h \
src/AutoPilotPlugins/APM/APMTuningComponent.h \ src/AutoPilotPlugins/APM/APMTuningComponent.h \
src/AutoPilotPlugins/Common/MotorComponent.h \
src/AutoPilotPlugins/Common/RadioComponentController.h \ src/AutoPilotPlugins/Common/RadioComponentController.h \
src/AutoPilotPlugins/Common/ESP8266ComponentController.h \ src/AutoPilotPlugins/Common/ESP8266ComponentController.h \
src/AutoPilotPlugins/Common/ESP8266Component.h \ src/AutoPilotPlugins/Common/ESP8266Component.h \
...@@ -696,6 +697,7 @@ SOURCES += \ ...@@ -696,6 +697,7 @@ SOURCES += \
src/AutoPilotPlugins/APM/APMSensorsComponent.cc \ src/AutoPilotPlugins/APM/APMSensorsComponent.cc \
src/AutoPilotPlugins/APM/APMSensorsComponentController.cc \ src/AutoPilotPlugins/APM/APMSensorsComponentController.cc \
src/AutoPilotPlugins/APM/APMTuningComponent.cc \ src/AutoPilotPlugins/APM/APMTuningComponent.cc \
src/AutoPilotPlugins/Common/MotorComponent.cc \
src/AutoPilotPlugins/Common/RadioComponentController.cc \ src/AutoPilotPlugins/Common/RadioComponentController.cc \
src/AutoPilotPlugins/Common/ESP8266ComponentController.cc \ src/AutoPilotPlugins/Common/ESP8266ComponentController.cc \
src/AutoPilotPlugins/Common/ESP8266Component.cc \ src/AutoPilotPlugins/Common/ESP8266Component.cc \
......
...@@ -39,6 +39,7 @@ ...@@ -39,6 +39,7 @@
<file alias="MainWindowNative.qml">src/ui/MainWindowNative.qml</file> <file alias="MainWindowNative.qml">src/ui/MainWindowNative.qml</file>
<file alias="MainWindowLeftPanel.qml">src/ui/MainWindowLeftPanel.qml</file> <file alias="MainWindowLeftPanel.qml">src/ui/MainWindowLeftPanel.qml</file>
<file alias="MissionEditor.qml">src/MissionEditor/MissionEditor.qml</file> <file alias="MissionEditor.qml">src/MissionEditor/MissionEditor.qml</file>
<file alias="MotorComponent.qml">src/AutoPilotPlugins/Common/MotorComponent.qml</file>
<file alias="PowerComponent.qml">src/AutoPilotPlugins/PX4/PowerComponent.qml</file> <file alias="PowerComponent.qml">src/AutoPilotPlugins/PX4/PowerComponent.qml</file>
<file alias="PowerComponentSummary.qml">src/AutoPilotPlugins/PX4/PowerComponentSummary.qml</file> <file alias="PowerComponentSummary.qml">src/AutoPilotPlugins/PX4/PowerComponentSummary.qml</file>
<file alias="PX4FlowSensor.qml">src/VehicleSetup/PX4FlowSensor.qml</file> <file alias="PX4FlowSensor.qml">src/VehicleSetup/PX4FlowSensor.qml</file>
...@@ -55,6 +56,8 @@ ...@@ -55,6 +56,8 @@
<file alias="QGroundControl/Controls/MissionItemIndexLabel.qml">src/QmlControls/MissionItemIndexLabel.qml</file> <file alias="QGroundControl/Controls/MissionItemIndexLabel.qml">src/QmlControls/MissionItemIndexLabel.qml</file>
<file alias="QGroundControl/Controls/MissionItemStatus.qml">src/MissionEditor/MissionItemStatus.qml</file> <file alias="QGroundControl/Controls/MissionItemStatus.qml">src/MissionEditor/MissionItemStatus.qml</file>
<file alias="QGroundControl/Controls/MissionCommandDialog.qml">src/QmlControls/MissionCommandDialog.qml</file> <file alias="QGroundControl/Controls/MissionCommandDialog.qml">src/QmlControls/MissionCommandDialog.qml</file>
<file alias="QGroundControl/Controls/MultiRotorMotorDisplay.qml">src/QmlControls/MultiRotorMotorDisplay.qml</file>
<file alias="QGroundControl/Controls/MultiRotorMotorDisplayLegend.qml">src/QmlControls/MultiRotorMotorDisplayLegend.qml</file>
<file alias="QGroundControl/Controls/ModeSwitchDisplay.qml">src/QmlControls/ModeSwitchDisplay.qml</file> <file alias="QGroundControl/Controls/ModeSwitchDisplay.qml">src/QmlControls/ModeSwitchDisplay.qml</file>
<file alias="QGroundControl/Controls/ParameterEditor.qml">src/QmlControls/ParameterEditor.qml</file> <file alias="QGroundControl/Controls/ParameterEditor.qml">src/QmlControls/ParameterEditor.qml</file>
<file alias="QGroundControl/Controls/ParameterEditorDialog.qml">src/QmlControls/ParameterEditorDialog.qml</file> <file alias="QGroundControl/Controls/ParameterEditorDialog.qml">src/QmlControls/ParameterEditorDialog.qml</file>
...@@ -71,6 +74,7 @@ ...@@ -71,6 +74,7 @@
<file alias="QGroundControl/Controls/QGCMovableItem.qml">src/QmlControls/QGCMovableItem.qml</file> <file alias="QGroundControl/Controls/QGCMovableItem.qml">src/QmlControls/QGCMovableItem.qml</file>
<file alias="QGroundControl/Controls/QGCPipable.qml">src/QmlControls/QGCPipable.qml</file> <file alias="QGroundControl/Controls/QGCPipable.qml">src/QmlControls/QGCPipable.qml</file>
<file alias="QGroundControl/Controls/QGCRadioButton.qml">src/QmlControls/QGCRadioButton.qml</file> <file alias="QGroundControl/Controls/QGCRadioButton.qml">src/QmlControls/QGCRadioButton.qml</file>
<file alias="QGroundControl/Controls/QGCSlider.qml">src/QmlControls/QGCSlider.qml</file>
<file alias="QGroundControl/Controls/QGCTextField.qml">src/QmlControls/QGCTextField.qml</file> <file alias="QGroundControl/Controls/QGCTextField.qml">src/QmlControls/QGCTextField.qml</file>
<file alias="QGroundControl/Controls/QGCToolBarButton.qml">src/QmlControls/QGCToolBarButton.qml</file> <file alias="QGroundControl/Controls/QGCToolBarButton.qml">src/QmlControls/QGCToolBarButton.qml</file>
<file alias="QGroundControl/Controls/QGCView.qml">src/QmlControls/QGCView.qml</file> <file alias="QGroundControl/Controls/QGCView.qml">src/QmlControls/QGCView.qml</file>
...@@ -78,6 +82,7 @@ ...@@ -78,6 +82,7 @@
<file alias="QGroundControl/Controls/QGCViewMessage.qml">src/QmlControls/QGCViewMessage.qml</file> <file alias="QGroundControl/Controls/QGCViewMessage.qml">src/QmlControls/QGCViewMessage.qml</file>
<file alias="QGroundControl/Controls/QGCViewPanel.qml">src/QmlControls/QGCViewPanel.qml</file> <file alias="QGroundControl/Controls/QGCViewPanel.qml">src/QmlControls/QGCViewPanel.qml</file>
<file alias="QGroundControl/Controls/RoundButton.qml">src/QmlControls/RoundButton.qml</file> <file alias="QGroundControl/Controls/RoundButton.qml">src/QmlControls/RoundButton.qml</file>
<file alias="QGroundControl/Controls/SetupPage.qml">src/AutoPilotPlugins/Common/SetupPage.qml</file>
<file alias="QGroundControl/Controls/SignalStrength.qml">src/ui/toolbar/SignalStrength.qml</file> <file alias="QGroundControl/Controls/SignalStrength.qml">src/ui/toolbar/SignalStrength.qml</file>
<file alias="QGroundControl/Controls/SliderSwitch.qml">src/QmlControls/SliderSwitch.qml</file> <file alias="QGroundControl/Controls/SliderSwitch.qml">src/QmlControls/SliderSwitch.qml</file>
<file alias="QGroundControl/Controls/SubMenuButton.qml">src/QmlControls/SubMenuButton.qml</file> <file alias="QGroundControl/Controls/SubMenuButton.qml">src/QmlControls/SubMenuButton.qml</file>
...@@ -113,7 +118,6 @@ ...@@ -113,7 +118,6 @@
<file alias="QGroundControl/FlightMap/QGCInstrumentWidget.qml">src/FlightMap/Widgets/QGCInstrumentWidget.qml</file> <file alias="QGroundControl/FlightMap/QGCInstrumentWidget.qml">src/FlightMap/Widgets/QGCInstrumentWidget.qml</file>
<file alias="QGroundControl/FlightMap/QGCInstrumentWidgetAlternate.qml">src/FlightMap/Widgets/QGCInstrumentWidgetAlternate.qml</file> <file alias="QGroundControl/FlightMap/QGCInstrumentWidgetAlternate.qml">src/FlightMap/Widgets/QGCInstrumentWidgetAlternate.qml</file>
<file alias="QGroundControl/FlightMap/QGCPitchIndicator.qml">src/FlightMap/Widgets/QGCPitchIndicator.qml</file> <file alias="QGroundControl/FlightMap/QGCPitchIndicator.qml">src/FlightMap/Widgets/QGCPitchIndicator.qml</file>
<file alias="QGroundControl/FlightMap/QGCSlider.qml">src/FlightMap/Widgets/QGCSlider.qml</file>
<file alias="QGroundControl/FlightMap/QGCVideoBackground.qml">src/FlightMap/QGCVideoBackground.qml</file> <file alias="QGroundControl/FlightMap/QGCVideoBackground.qml">src/FlightMap/QGCVideoBackground.qml</file>
<file alias="QGroundControl/FlightMap/ValuesWidget.qml">src/FlightMap/Widgets/ValuesWidget.qml</file> <file alias="QGroundControl/FlightMap/ValuesWidget.qml">src/FlightMap/Widgets/ValuesWidget.qml</file>
<file alias="QGroundControl/FlightMap/VibrationWidget.qml">src/FlightMap/Widgets/VibrationWidget.qml</file> <file alias="QGroundControl/FlightMap/VibrationWidget.qml">src/FlightMap/Widgets/VibrationWidget.qml</file>
......
...@@ -25,6 +25,7 @@ ...@@ -25,6 +25,7 @@
#include "APMTuningComponent.h" #include "APMTuningComponent.h"
#include "APMSensorsComponent.h" #include "APMSensorsComponent.h"
#include "APMPowerComponent.h" #include "APMPowerComponent.h"
#include "MotorComponent.h"
#include "APMCameraComponent.h" #include "APMCameraComponent.h"
#include "ESP8266Component.h" #include "ESP8266Component.h"
...@@ -36,6 +37,7 @@ APMAutoPilotPlugin::APMAutoPilotPlugin(Vehicle* vehicle, QObject* parent) ...@@ -36,6 +37,7 @@ APMAutoPilotPlugin::APMAutoPilotPlugin(Vehicle* vehicle, QObject* parent)
, _cameraComponent(NULL) , _cameraComponent(NULL)
, _flightModesComponent(NULL) , _flightModesComponent(NULL)
, _powerComponent(NULL) , _powerComponent(NULL)
, _motorComponent(NULL)
, _radioComponent(NULL) , _radioComponent(NULL)
, _safetyComponent(NULL) , _safetyComponent(NULL)
, _sensorsComponent(NULL) , _sensorsComponent(NULL)
...@@ -77,6 +79,12 @@ const QVariantList& APMAutoPilotPlugin::vehicleComponents(void) ...@@ -77,6 +79,12 @@ const QVariantList& APMAutoPilotPlugin::vehicleComponents(void)
_powerComponent->setupTriggerSignals(); _powerComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_powerComponent)); _components.append(QVariant::fromValue((VehicleComponent*)_powerComponent));
if (_vehicle->multiRotor() || _vehicle->vtol()) {
_motorComponent = new MotorComponent(_vehicle, this);
_motorComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_motorComponent));
}
_safetyComponent = new APMSafetyComponent(_vehicle, this); _safetyComponent = new APMSafetyComponent(_vehicle, this);
_safetyComponent->setupTriggerSignals(); _safetyComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_safetyComponent)); _components.append(QVariant::fromValue((VehicleComponent*)_safetyComponent));
......
...@@ -22,6 +22,7 @@ class APMTuningComponent; ...@@ -22,6 +22,7 @@ class APMTuningComponent;
class APMSafetyComponent; class APMSafetyComponent;
class APMSensorsComponent; class APMSensorsComponent;
class APMPowerComponent; class APMPowerComponent;
class MotorComponent;
class APMCameraComponent; class APMCameraComponent;
class ESP8266Component; class ESP8266Component;
...@@ -41,6 +42,7 @@ public: ...@@ -41,6 +42,7 @@ public:
APMCameraComponent* cameraComponent (void) const { return _cameraComponent; } APMCameraComponent* cameraComponent (void) const { return _cameraComponent; }
APMFlightModesComponent* flightModesComponent(void) const { return _flightModesComponent; } APMFlightModesComponent* flightModesComponent(void) const { return _flightModesComponent; }
APMPowerComponent* powerComponent (void) const { return _powerComponent; } APMPowerComponent* powerComponent (void) const { return _powerComponent; }
MotorComponent* motorComponent (void) const { return _motorComponent; }
APMRadioComponent* radioComponent (void) const { return _radioComponent; } APMRadioComponent* radioComponent (void) const { return _radioComponent; }
APMSafetyComponent* safetyComponent (void) const { return _safetyComponent; } APMSafetyComponent* safetyComponent (void) const { return _safetyComponent; }
APMSensorsComponent* sensorsComponent (void) const { return _sensorsComponent; } APMSensorsComponent* sensorsComponent (void) const { return _sensorsComponent; }
...@@ -59,6 +61,7 @@ private: ...@@ -59,6 +61,7 @@ private:
APMCameraComponent* _cameraComponent; APMCameraComponent* _cameraComponent;
APMFlightModesComponent* _flightModesComponent; APMFlightModesComponent* _flightModesComponent;
APMPowerComponent* _powerComponent; APMPowerComponent* _powerComponent;
MotorComponent* _motorComponent;
APMRadioComponent* _radioComponent; APMRadioComponent* _radioComponent;
APMSafetyComponent* _safetyComponent; APMSafetyComponent* _safetyComponent;
APMSensorsComponent* _sensorsComponent; APMSensorsComponent* _sensorsComponent;
......
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
#include "MotorComponent.h"
#include "APMAutoPilotPlugin.h"
#include "APMAirframeComponent.h"
MotorComponent::MotorComponent(Vehicle* vehicle, AutoPilotPlugin* autopilot, QObject* parent) :
VehicleComponent(vehicle, autopilot, parent),
_name(tr("Motors"))
{
}
QString MotorComponent::name(void) const
{
return _name;
}
QString MotorComponent::description(void) const
{
return tr("Motors Setup is used to manually test motor control and direction.");
}
QString MotorComponent::iconResource(void) const
{
return QStringLiteral("/qmlimages/MotorComponentIcon.png");
}
bool MotorComponent::requiresSetup(void) const
{
return false;
}
bool MotorComponent::setupComplete(void) const
{
return true;
}
QStringList MotorComponent::setupCompleteChangedTriggerList(void) const
{
return QStringList();
}
QUrl MotorComponent::setupSource(void) const
{
return QUrl::fromUserInput(QStringLiteral("qrc:/qml/MotorComponent.qml"));
}
QUrl MotorComponent::summaryQmlSource(void) const
{
return QUrl();
}
QString MotorComponent::prerequisiteSetup(void) const
{
return QString();
}
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
#ifndef MotorComponent_H
#define MotorComponent_H
#include "VehicleComponent.h"
#include "Fact.h"
class MotorComponent : public VehicleComponent
{
Q_OBJECT
public:
MotorComponent(Vehicle* vehicle, AutoPilotPlugin* autopilot, QObject* parent = NULL);
// Virtuals from VehicleComponent
QStringList setupCompleteChangedTriggerList(void) const final;
// Virtuals from VehicleComponent
QString name(void) const final;
QString description(void) const final;
QString iconResource(void) const final;
bool requiresSetup(void) const final;
bool setupComplete(void) const final;
QUrl setupSource(void) const final;
QUrl summaryQmlSource(void) const final;
QString prerequisiteSetup(void) const final;
private:
const QString _name;
};
#endif
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
import QtQuick 2.5
import QtQuick.Controls 1.2
import QtQuick.Dialogs 1.2
import QGroundControl 1.0
import QGroundControl.Controls 1.0
import QGroundControl.FactSystem 1.0
import QGroundControl.ScreenTools 1.0
SetupPage {
id: motorPage
pageComponent: pageComponent
readonly property int _barHeight: 10
readonly property int _barWidth: 5
readonly property int _sliderHeight: 10
FactPanelController {
id: controller
factPanel: motorPage.viewPanel
}
Component {
id: pageComponent
Column {
spacing: 10
Row {
id: motorSliders
enabled: safetySwitch.checked
spacing: ScreenTools.defaultFontPixelWidth * 4
Repeater {
id: sliderRepeater
model: controller.vehicle.motorCount == -1 ? 8 : controller.vehicle.motorCount
Column {
property alias motorSlider: slider
Timer {
interval: 250
running: true
repeat: true
property real _lastValue: 0
onTriggered: {
if (_lastValue != slider.value) {
controller.vehicle.motorTest(index + 1, slider.value, 1)
}
}
}
QGCLabel {
anchors.horizontalCenter: parent.horizontalCenter
text: index + 1
}
QGCSlider {
id: slider
height: ScreenTools.defaultFontPixelHeight * _sliderHeight
orientation: Qt.Vertical
maximumValue: 100
value: 0
}
} // Column
} // Repeater
Column {
QGCLabel {
anchors.horizontalCenter: parent.horizontalCenter
text: qsTr("All")
}
QGCSlider {
id: allSlider
height: ScreenTools.defaultFontPixelHeight * _sliderHeight
orientation: Qt.Vertical
maximumValue: 100
value: 0
onValueChanged: {
for (var sliderIndex=0; sliderIndex<sliderRepeater.count; sliderIndex++) {
sliderRepeater.itemAt(sliderIndex).motorSlider.value = allSlider.value
}
}
}
} // Column
MultiRotorMotorDisplay {
anchors.top: parent.top
anchors.bottom: parent.bottom
width: height
motorCount: controller.vehicle.motorCount
xConfig: controller.vehicle.xConfigMotors
coaxial: controller.vehicle.coaxialMotors
}
MultiRotorMotorDisplayLegend {
anchors.top: parent.top
anchors.bottom: parent.bottom
width: height
}
} // Row
QGCLabel {
anchors.left: parent.left
anchors.right: parent.right
wrapMode: Text.WordWrap
text: qsTr("Moving the sliders will causes the motors to spin. Make sure you remove all props.")
}
Row {
spacing: ScreenTools.defaultFontPixelWidth
Switch {
id: safetySwitch
onClicked: {
if (!checked) {
for (var sliderIndex=0; sliderIndex<sliderRepeater.count; sliderIndex++) {
sliderRepeater.itemAt(sliderIndex).motorSlider.value = 0
}
allSlider.value = 0
}
}
}
QGCLabel {
color: qgcPal.warningText
text: qsTr("Propellors are removed - Enable motor sliders")
}
} // Row
} // Column
} // Component
} // SetupPahe
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
import QtQuick 2.5
import QtQuick.Controls 1.2
import QtQuick.Dialogs 1.2
import QGroundControl 1.0
import QGroundControl.FactSystem 1.0
import QGroundControl.FactControls 1.0
import QGroundControl.Palette 1.0
import QGroundControl.Controls 1.0
import QGroundControl.ScreenTools 1.0
import QGroundControl.Controllers 1.0
/// Base view control for all Setup pages
QGCView {
id: setupView
viewPanel: setupPanel
property alias pageComponent: pageLoader.sourceComponent
property real _margins: ScreenTools.defaultFontPixelHeight / 2
QGCPalette { id: qgcPal; colorGroupEnabled: setupPanel.enabled }
QGCViewPanel {
id: setupPanel
anchors.fill: parent
QGCFlickable {
anchors.fill: parent
contentWidth: pageLoader.item.x + pageLoader.item.width
contentHeight: pageLoader.item.y + pageLoader.item.height
clip: true
Column {
id: headingColumn
anchors.left: parent.left
anchors.right: parent.right
spacing: _margins
QGCLabel {
font.pointSize: ScreenTools.largeFontPointSize
text: vehicleComponent.name + " " + qsTr("Setup")
visible: !ScreenTools.isShortScreen
}
QGCLabel {
anchors.left: parent.left
anchors.right: parent.right
wrapMode: Text.WordWrap
text: vehicleComponent.description
visible: !ScreenTools.isShortScreen
}
}
Loader {
anchors.topMargin: _margins
anchors.top: headingColumn.bottom
id: pageLoader
}
}
}
}
...@@ -22,16 +22,17 @@ ...@@ -22,16 +22,17 @@
/// @brief This is the AutoPilotPlugin implementatin for the MAV_AUTOPILOT_PX4 type. /// @brief This is the AutoPilotPlugin implementatin for the MAV_AUTOPILOT_PX4 type.
/// @author Don Gagne <don@thegagnes.com> /// @author Don Gagne <don@thegagnes.com>
PX4AutoPilotPlugin::PX4AutoPilotPlugin(Vehicle* vehicle, QObject* parent) : PX4AutoPilotPlugin::PX4AutoPilotPlugin(Vehicle* vehicle, QObject* parent)
AutoPilotPlugin(vehicle, parent), : AutoPilotPlugin(vehicle, parent)
_airframeComponent(NULL), , _airframeComponent(NULL)
_radioComponent(NULL), , _radioComponent(NULL)
_esp8266Component(NULL), , _esp8266Component(NULL)
_flightModesComponent(NULL), , _flightModesComponent(NULL)
_sensorsComponent(NULL), , _sensorsComponent(NULL)
_safetyComponent(NULL), , _safetyComponent(NULL)
_powerComponent(NULL), , _powerComponent(NULL)
_incorrectParameterVersion(false) , _motorComponent(NULL)
, _incorrectParameterVersion(false)
{ {
Q_ASSERT(vehicle); Q_ASSERT(vehicle);
...@@ -74,6 +75,13 @@ const QVariantList& PX4AutoPilotPlugin::vehicleComponents(void) ...@@ -74,6 +75,13 @@ const QVariantList& PX4AutoPilotPlugin::vehicleComponents(void)
_powerComponent->setupTriggerSignals(); _powerComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_powerComponent)); _components.append(QVariant::fromValue((VehicleComponent*)_powerComponent));
#if 0
// Coming soon
_motorComponent = new MotorComponent(_vehicle, this);
_motorComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_motorComponent));
#endif
_safetyComponent = new SafetyComponent(_vehicle, this); _safetyComponent = new SafetyComponent(_vehicle, this);
_safetyComponent->setupTriggerSignals(); _safetyComponent->setupTriggerSignals();
_components.append(QVariant::fromValue((VehicleComponent*)_safetyComponent)); _components.append(QVariant::fromValue((VehicleComponent*)_safetyComponent));
......
...@@ -21,6 +21,7 @@ ...@@ -21,6 +21,7 @@
#include "SafetyComponent.h" #include "SafetyComponent.h"
#include "CameraComponent.h" #include "CameraComponent.h"
#include "PowerComponent.h" #include "PowerComponent.h"
#include "MotorComponent.h"
#include "PX4TuningComponent.h" #include "PX4TuningComponent.h"
#include "Vehicle.h" #include "Vehicle.h"
...@@ -50,6 +51,7 @@ public: ...@@ -50,6 +51,7 @@ public:
SafetyComponent* safetyComponent(void) { return _safetyComponent; } SafetyComponent* safetyComponent(void) { return _safetyComponent; }
CameraComponent* cameraComponent(void) { return _cameraComponent; } CameraComponent* cameraComponent(void) { return _cameraComponent; }
PowerComponent* powerComponent(void) { return _powerComponent; } PowerComponent* powerComponent(void) { return _powerComponent; }
MotorComponent* motorComponent(void) { return _motorComponent; }
PX4TuningComponent* tuningComponent(void) { return _tuningComponent; } PX4TuningComponent* tuningComponent(void) { return _tuningComponent; }
public slots: public slots:
...@@ -67,6 +69,7 @@ private: ...@@ -67,6 +69,7 @@ private:
SafetyComponent* _safetyComponent; SafetyComponent* _safetyComponent;
CameraComponent* _cameraComponent; CameraComponent* _cameraComponent;
PowerComponent* _powerComponent; PowerComponent* _powerComponent;
MotorComponent* _motorComponent;
PX4TuningComponent* _tuningComponent; PX4TuningComponent* _tuningComponent;
bool _incorrectParameterVersion; ///< true: parameter version incorrect, setup not allowed bool _incorrectParameterVersion; ///< true: parameter version incorrect, setup not allowed
}; };
......
...@@ -122,7 +122,6 @@ APMCustomMode::APMCustomMode(uint32_t mode, bool settable) : ...@@ -122,7 +122,6 @@ APMCustomMode::APMCustomMode(uint32_t mode, bool settable) :
{ {
} }
void APMCustomMode::setEnumToStringMapping(const QMap<uint32_t, QString>& enumToString) void APMCustomMode::setEnumToStringMapping(const QMap<uint32_t, QString>& enumToString)
{ {
_enumToString = enumToString; _enumToString = enumToString;
...@@ -138,8 +137,10 @@ QString APMCustomMode::modeString() const ...@@ -138,8 +137,10 @@ QString APMCustomMode::modeString() const
} }
APMFirmwarePlugin::APMFirmwarePlugin(void) APMFirmwarePlugin::APMFirmwarePlugin(void)
: _coaxialMotors(false)
, _textSeverityAdjustmentNeeded(false)
{ {
_textSeverityAdjustmentNeeded = false;
} }
bool APMFirmwarePlugin::isCapable(FirmwareCapabilities capabilities) bool APMFirmwarePlugin::isCapable(FirmwareCapabilities capabilities)
...@@ -380,6 +381,15 @@ bool APMFirmwarePlugin::_handleStatusText(Vehicle* vehicle, mavlink_message_t* m ...@@ -380,6 +381,15 @@ bool APMFirmwarePlugin::_handleStatusText(Vehicle* vehicle, mavlink_message_t* m
// Start TCP video handshake with ARTOO // Start TCP video handshake with ARTOO
_soloVideoHandshake(vehicle); _soloVideoHandshake(vehicle);
} else if (messageText.contains(APM_FRAME_REXP)) {
// We need to parse the Frame: message in order to determine whether the motors are coaxial or not
QRegExp frameTypeRegex("^Frame: (\\S*)");
if (frameTypeRegex.indexIn(messageText) != -1) {
QString frameType = frameTypeRegex.cap(1);
if (!frameType.isEmpty() && (frameType == QStringLiteral("Y6") || frameType == QStringLiteral("OCTA_QUAD") || frameType == QStringLiteral("COAX"))) {
_coaxialMotors = true;
}
}
} }
if (messageText.startsWith("PreArm")) { if (messageText.startsWith("PreArm")) {
......
...@@ -99,6 +99,8 @@ protected: ...@@ -99,6 +99,8 @@ protected:
APMFirmwarePlugin(void); APMFirmwarePlugin(void);
void setSupportedModes(QList<APMCustomMode> supportedModes); void setSupportedModes(QList<APMCustomMode> supportedModes);
bool _coaxialMotors;
private slots: private slots:
void _artooSocketError(QAbstractSocket::SocketError socketError); void _artooSocketError(QAbstractSocket::SocketError socketError);
......
...@@ -197,3 +197,14 @@ void ArduCopterFirmwarePlugin::setGuidedMode(Vehicle* vehicle, bool guidedMode) ...@@ -197,3 +197,14 @@ void ArduCopterFirmwarePlugin::setGuidedMode(Vehicle* vehicle, bool guidedMode)
pauseVehicle(vehicle); pauseVehicle(vehicle);
} }
} }
bool ArduCopterFirmwarePlugin::multiRotorCoaxialMotors(Vehicle* vehicle)
{
Q_UNUSED(vehicle);
return _coaxialMotors;
}
bool ArduCopterFirmwarePlugin::multiRotorXConfig(Vehicle* vehicle)
{
return vehicle->autopilotPlugin()->getParameterFact(FactSystem::defaultComponentId, "FRAME")->rawValue().toInt() != 0;
}
...@@ -64,6 +64,8 @@ public: ...@@ -64,6 +64,8 @@ public:
void guidedModeChangeAltitude(Vehicle* vehicle, double altitudeRel) final; void guidedModeChangeAltitude(Vehicle* vehicle, double altitudeRel) final;
const FirmwarePlugin::remapParamNameMajorVersionMap_t& paramNameRemapMajorVersionMap(void) const final { return _remapParamName; } const FirmwarePlugin::remapParamNameMajorVersionMap_t& paramNameRemapMajorVersionMap(void) const final { return _remapParamName; }
virtual int remapParamNameHigestMinorVersionNumber(int majorVersionNumber) const final; virtual int remapParamNameHigestMinorVersionNumber(int majorVersionNumber) const final;
virtual bool multiRotorCoaxialMotors(Vehicle* vehicle) final;
virtual bool multiRotorXConfig(Vehicle* vehicle) final;
private: private:
static bool _remapParamNameIntialized; static bool _remapParamNameIntialized;
......
...@@ -181,6 +181,12 @@ public: ...@@ -181,6 +181,12 @@ public:
/// Returns the highest major version number that is known to the remap for this specified major version. /// Returns the highest major version number that is known to the remap for this specified major version.
virtual int remapParamNameHigestMinorVersionNumber(int majorVersionNumber) const; virtual int remapParamNameHigestMinorVersionNumber(int majorVersionNumber) const;
/// @return true: Motors are coaxial like an X8 config, false: Quadcopter for example
virtual bool multiRotorCoaxialMotors(Vehicle* vehicle) { Q_UNUSED(vehicle); return false; }
/// @return true: X confiuration, false: Plus configuration
virtual bool multiRotorXConfig(Vehicle* vehicle) { Q_UNUSED(vehicle); return false; }
}; };
#endif #endif
/****************************************************************************
**
** Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of Digia Plc and its Subsidiary(-ies) nor the names
** of its contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
import QtQuick 2.1
import QGroundControl.Controls 1.0
import QGroundControl.ScreenTools 1.0
Item {
id: slider;
height: 12
property real value // value is read/write.
property real minimum: 0
property real maximum: 1
property int length: width - handle.width
Rectangle {
anchors.fill: parent
radius: ScreenTools.defaultFontPixelHeight * (0.5)
color: Qt.rgba(0,0,0,0.65);
}
Rectangle {
anchors.left: parent.left
anchors.leftMargin: ScreenTools.defaultFontPixelHeight * (0.33)
radius: ScreenTools.defaultFontPixelHeight * (0.33)
height: ScreenTools.defaultFontPixelHeight * (0.33)
width: handle.x - x
color: "#69bb17"
anchors.verticalCenter: parent.verticalCenter
}
Rectangle {
id: labelRect
width: label.width
height: label.height + ScreenTools.defaultFontPixelHeight * (0.33)
radius: ScreenTools.defaultFontPixelHeight * (0.33)
smooth: true
color: Qt.rgba(1,1,1,0.75);
border.width: ScreenTools.defaultFontPixelHeight * (0.083)
border.color: Qt.rgba(0,0,0,0.45);
anchors.bottom: handle.top
anchors.bottomMargin: ScreenTools.defaultFontPixelHeight * (0.33)
visible: mouseRegion.pressed
x: Math.max(Math.min(handle.x + (handle.width - width ) / 2, slider.width - width), 0)
QGCLabel{
id: label
color: "black"
text: slider.value.toFixed(2)
width: font.pointSize * 3.5
anchors.horizontalCenter: labelRect.horizontalCenter
horizontalAlignment: Text.AlignHCenter
anchors.verticalCenter: labelRect.verticalCenter
}
}
Rectangle {
id: handle;
smooth: true
width: ScreenTools.defaultFontPixelHeight * (2.16);
y: (slider.height - height) / 2;
x: (slider.value - slider.minimum) * slider.length / (slider.maximum - slider.minimum)
height: width
radius: width / 2
gradient: normalGradient
border.width: 2
border.color: "white"
Gradient {
id: normalGradient
GradientStop { position: 0.0; color: "#b0b0b0" }
GradientStop { position: 0.66; color: "#909090" }
GradientStop { position: 1.0; color: "#545454" }
}
MouseArea {
id: mouseRegion
hoverEnabled: false
anchors.fill: parent; drag.target: parent
drag.axis: Drag.XAxis; drag.minimumX: 0; drag.maximumX: slider.length
preventStealing: true
onPositionChanged: { slider.value = (slider.maximum - slider.minimum) * handle.x / slider.length + slider.minimum; }
}
}
}
import QtQuick 2.2
import QGroundControl.Palette 1.0
import QGroundControl.ScreenTools 1.0
Item {
id: motorRoot
property int motorCount: 4 // Number of motors on vehicle
property bool xConfig: true // true: X configuration, false: Plus configuration
property bool coaxial: true // true: motors on top bottom of same arm, false: motors only on top of arm
property bool _unsupportedConfig: motorCount == 3 || (motorCount == 6 && coaxial) // Tricopters NYI
property var _qgcPal: QGCPalette { colorGroupEnabled: enabled }
property real _rotorRadius: motorRoot.height / 8
property int _motorsPerSide: motorCount / (coaxial ? 2 : 1)
readonly property string _cwColor: "green"
readonly property string _ccwColor: "blue"
readonly property var _motorColors4Plus: [ _ccwColor, _cwColor ]
readonly property var _motorColors4X: [ _cwColor, _ccwColor ]
readonly property var _motorColors6: [ _cwColor, _ccwColor ]
readonly property var _motorColors8: [ _cwColor, _ccwColor ]
readonly property var _motorColors4Top: [ _cwColor, _ccwColor ]
readonly property var _motorColors4Bottom: [ _ccwColor, _cwColor ]
readonly property var _motorNumbers4Plus: [ 1, 4, 2, 3 ]
readonly property var _motorNumbers4X: [ 4, 2, 3, 1 ]
readonly property var _motorNumbers6Plus: [ 6, 2, 3, 5, 1, 4 ]
readonly property var _motorNumbers6X: [ 1, 4, 6, 2, 3, 5 ]
readonly property var _motorNumbers8: [ 8, 4, 2, 6, 7, 5, 1, 3 ]
readonly property var _motorNumbers4Top: [ 4, 3, 2, 1 ]
readonly property var _motorNumbers4Bottom: [ 7, 8, 5, 6 ]
Component.onCompleted: {
if (coaxial) {
topMotors.motorNumbers = _motorNumbers4Top
bottomMotors.motorNumbers = _motorNumbers4Bottom
} else {
switch (motorCount) {
case 4:
topMotors.motorNumbers = xConfig ? _motorNumbers4X : _motorNumbers4Plus
topMotors.motorColors = xConfig ? _motorColors4X : _motorColors4Plus
break
case 6:
topMotors.motorNumbers = xConfig ? _motorNumbers6X : _motorNumbers6Plus
topMotors.motorColors = _motorColors6
break
default:
case 8:
topMotors.motorNumbers = _motorNumbers8
topMotors.motorColors = _motorColors8
break
}
bottomMotors.motorNumbers = _motorNumbers8
}
}
Component {
id: motorDisplayComponent
Repeater {
id: motorRepeater
model: _motorsPerSide
Item {
x: motorRepeater.width / 2 + _armXCenter - rotor.radius
y: motorRepeater.height / 2 + _armYCenter - rotor.radius
width: _rotorRadius * 2
height: _rotorRadius * 2
property real _armOffsetRadians: ((2 * Math.PI) / _motorsPerSide)
property real _armOffsetIndexRadians: (_armOffsetRadians * index) + ((xConfig && _motorsPerSide != 6) || (!xConfig && _motorsPerSide == 6) ? _armOffsetRadians / 2 : 0)
property real _armLength: (motorRepeater.height / 2) - (_rotorRadius * (xConfig && _motorsPerSide == 4 ? 0 : 1))
property real _armXCenter: Math.cos(_armOffsetIndexRadians) * _armLength // adjacent = cos * hypotenuse
property real _armYCenter: Math.sin(_armOffsetIndexRadians) * _armLength // opposite = sin * hypotenuse
Rectangle {id: rotor
anchors.fill: parent
radius: _rotorRadius
color: motorColors[index & 1]
opacity: topCoaxial ? 0.65 : 1.0
border.color: topCoaxial ? "black" : color
readonly property bool topCoaxial: topMotors && coaxial
}
Rectangle {
anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenter: parent.verticalCenter
width: radius *2
height: radius *2
radius: ScreenTools.defaultFontPixelHeight / 2
color: "white"
border.color: "black"
QGCLabel {
anchors.fill: parent
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignHCenter
text: motorNumbers[index]
color: parent.border.color
}
}
} // Item
} // Repeater
} // Component - MotorDisplayComponent
Item {
anchors.fill: parent
visible: !_unsupportedConfig
Loader {
id: bottomMotors
anchors.topMargin: ScreenTools.defaultFontPixelHeight
anchors.fill: parent
sourceComponent: motorDisplayComponent
visible: coaxial
property bool topMotors: false
property var motorNumbers: _motorNumbers8
property var motorColors: _motorColors4Bottom
}
Loader {
id: topMotors
anchors.fill: parent
anchors.bottomMargin: coaxial ? ScreenTools.defaultFontPixelHeight : 0
sourceComponent: motorDisplayComponent
property bool topMotors: true
property var motorNumbers: _motorNumbers8
property var motorColors: _motorColors4Top
}
// Body direction
Canvas {
anchors.fill: parent
property real _centerX : width / 2
property real _centerY : height / 2
onPaint: {
var ctx = getContext("2d");
ctx.lineWidth = 3
ctx.strokeStyle = _qgcPal.text
ctx.translate(_centerX, _centerY)
ctx.moveTo(0, -_rotorRadius / 2);
ctx.lineTo(_rotorRadius / 2, _rotorRadius);
ctx.lineTo(-_rotorRadius / 2, _rotorRadius);
ctx.lineTo(0, -_rotorRadius / 2);
ctx.stroke();
}
}
} // Item
} // Item
import QtQuick 2.2
import QGroundControl.Palette 1.0
import QGroundControl.ScreenTools 1.0
Item {
id: legendRoot
property var _qgcPal: QGCPalette { colorGroupEnabled: enabled }
property real _rotorRadius: legendRoot.height / 16
readonly property string _cwColor: "green"
readonly property string _ccwColor: "blue"
Item {
id: cwItem
anchors.left: parent.left
anchors.right: parent.right
height: legendRoot.height / 2
Rectangle {
id: cwRotor
anchors.left: parent.left
anchors.verticalCenter: parent.verticalCenter
width: _rotorRadius * 2
height: _rotorRadius * 2
radius: _rotorRadius
color: _cwColor
}
QGCLabel {
anchors.leftMargin: ScreenTools.defaultFontPixelWidth
anchors.left: cwRotor.right
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: parent.bottom
verticalAlignment: Text.AlignVCenter
wrapMode: Text.WordWrap
text: qsTr("Clockwise rotation, use pusher propellor")
}
}
Item {
id: ccwItem
anchors.top: cwItem.bottom
anchors.bottom: parent.bottom
anchors.left: parent.left
anchors.right: parent.right
Rectangle {
id: ccwRotor
anchors.left: parent.left
anchors.verticalCenter: parent.verticalCenter
width: _rotorRadius * 2
height: _rotorRadius * 2
radius: _rotorRadius
color: _ccwColor
}
QGCLabel {
anchors.leftMargin: ScreenTools.defaultFontPixelWidth
anchors.left: ccwRotor.right
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: parent.bottom
verticalAlignment: Text.AlignVCenter
wrapMode: Text.WordWrap
text: qsTr("Counter-Clockwise rotation, use normal propellor")
}
}
} // Item
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
import QtQuick 2.2
import QtQuick.Controls 1.2
import QtQuick.Controls.Styles 1.2
import QtQuick.Controls.Private 1.0
import QGroundControl.Palette 1.0
import QGroundControl.ScreenTools 1.0
Slider {
property var _qgcPal: QGCPalette { colorGroupEnabled: enabled }
style: SliderStyle {
groove: Item {
property color fillColor: "#49d"
anchors.verticalCenter: parent.verticalCenter
implicitWidth: Math.round(TextSingleton.implicitHeight * 4.5)
implicitHeight: Math.max(6, Math.round(TextSingleton.implicitHeight * 0.3))
Rectangle {
radius: height/2
anchors.fill: parent
border.width: 1
border.color: "#888"
gradient: Gradient {
GradientStop { color: "#bbb" ; position: 0 }
GradientStop { color: "#ccc" ; position: 0.6 }
GradientStop { color: "#ccc" ; position: 1 }
}
}
Item {
clip: true
width: styleData.handlePosition
height: parent.height
Rectangle {
anchors.fill: parent
border.color: Qt.darker(fillColor, 1.2)
radius: height/2
gradient: Gradient {
GradientStop {color: Qt.lighter(fillColor, 1.3) ; position: 0}
GradientStop {color: fillColor ; position: 1.4}
}
}
}
}
}
}
...@@ -13,6 +13,8 @@ MissionItemEditor 1.0 MissionItemEditor.qml ...@@ -13,6 +13,8 @@ MissionItemEditor 1.0 MissionItemEditor.qml
MissionItemIndexLabel 1.0 MissionItemIndexLabel.qml MissionItemIndexLabel 1.0 MissionItemIndexLabel.qml
MissionItemStatus 1.0 MissionItemStatus.qml MissionItemStatus 1.0 MissionItemStatus.qml
ModeSwitchDisplay 1.0 ModeSwitchDisplay.qml ModeSwitchDisplay 1.0 ModeSwitchDisplay.qml
MultiRotorMotorDisplay 1.0 MultiRotorMotorDisplay.qml
MultiRotorMotorDisplayLegend 1.0 MultiRotorMotorDisplayLegend.qml
ParameterEditor 1.0 ParameterEditor.qml ParameterEditor 1.0 ParameterEditor.qml
ParameterEditorDialog 1.0 ParameterEditorDialog.qml ParameterEditorDialog 1.0 ParameterEditorDialog.qml
RCChannelMonitor 1.0 RCChannelMonitor.qml RCChannelMonitor 1.0 RCChannelMonitor.qml
...@@ -26,6 +28,7 @@ QGCMobileFileDialog 1.0 QGCMobileFileDialog.qml ...@@ -26,6 +28,7 @@ QGCMobileFileDialog 1.0 QGCMobileFileDialog.qml
QGCMovableItem 1.0 QGCMovableItem.qml QGCMovableItem 1.0 QGCMovableItem.qml
QGCPipable 1.0 QGCPipable.qml QGCPipable 1.0 QGCPipable.qml
QGCRadioButton 1.0 QGCRadioButton.qml QGCRadioButton 1.0 QGCRadioButton.qml
QGCSlider 1.0 QGCSlider.qml
QGCTextField 1.0 QGCTextField.qml QGCTextField 1.0 QGCTextField.qml
QGCToolBarButton 1.0 QGCToolBarButton.qml QGCToolBarButton 1.0 QGCToolBarButton.qml
QGCView 1.0 QGCView.qml QGCView 1.0 QGCView.qml
...@@ -33,6 +36,7 @@ QGCViewDialog 1.0 QGCViewDialog.qml ...@@ -33,6 +36,7 @@ QGCViewDialog 1.0 QGCViewDialog.qml
QGCViewMessage 1.0 QGCViewMessage.qml QGCViewMessage 1.0 QGCViewMessage.qml
QGCViewPanel 1.0 QGCViewPanel.qml QGCViewPanel 1.0 QGCViewPanel.qml
RoundButton 1.0 RoundButton.qml RoundButton 1.0 RoundButton.qml
SetupPage 1.0 SetupPage.qml
SignalStrength 1.0 SignalStrength.qml SignalStrength 1.0 SignalStrength.qml
SliderSwitch 1.0 SliderSwitch.qml SliderSwitch 1.0 SliderSwitch.qml
SubMenuButton 1.0 SubMenuButton.qml SubMenuButton 1.0 SubMenuButton.qml
......
...@@ -916,6 +916,37 @@ void Vehicle::_updateNavigationControllerData(UASInterface *uas, float, float, f ...@@ -916,6 +916,37 @@ void Vehicle::_updateNavigationControllerData(UASInterface *uas, float, float, f
} }
} }
int Vehicle::motorCount(void)
{
switch (_vehicleType) {
case MAV_TYPE_HELICOPTER:
return 1;
case MAV_TYPE_VTOL_DUOROTOR:
return 2;
case MAV_TYPE_TRICOPTER:
return 3;
case MAV_TYPE_QUADROTOR:
case MAV_TYPE_VTOL_QUADROTOR:
return 4;
case MAV_TYPE_HEXAROTOR:
return 6;
case MAV_TYPE_OCTOROTOR:
return 8;
default:
return -1;
}
}
bool Vehicle::coaxialMotors(void)
{
return _firmwarePlugin->multiRotorCoaxialMotors(this);
}
bool Vehicle::xConfigMotors(void)
{
return _firmwarePlugin->multiRotorXConfig(this);
}
/* /*
* Internal * Internal
*/ */
...@@ -1738,6 +1769,11 @@ void Vehicle::setSoloFirmware(bool soloFirmware) ...@@ -1738,6 +1769,11 @@ void Vehicle::setSoloFirmware(bool soloFirmware)
} }
} }
void Vehicle::motorTest(int motor, int percent, int timeoutSecs)
{
doCommandLong(defaultComponentId(), MAV_CMD_DO_MOTOR_TEST, motor, MOTOR_TEST_THROTTLE_PERCENT, percent, timeoutSecs);
}
const char* VehicleGPSFactGroup::_hdopFactName = "hdop"; const char* VehicleGPSFactGroup::_hdopFactName = "hdop";
const char* VehicleGPSFactGroup::_vdopFactName = "vdop"; const char* VehicleGPSFactGroup::_vdopFactName = "vdop";
const char* VehicleGPSFactGroup::_courseOverGroundFactName = "courseOverGround"; const char* VehicleGPSFactGroup::_courseOverGroundFactName = "courseOverGround";
......
...@@ -277,6 +277,9 @@ public: ...@@ -277,6 +277,9 @@ public:
Q_PROPERTY(bool rover READ rover CONSTANT) Q_PROPERTY(bool rover READ rover CONSTANT)
Q_PROPERTY(bool autoDisconnect MEMBER _autoDisconnect NOTIFY autoDisconnectChanged) Q_PROPERTY(bool autoDisconnect MEMBER _autoDisconnect NOTIFY autoDisconnectChanged)
Q_PROPERTY(QString prearmError READ prearmError WRITE setPrearmError NOTIFY prearmErrorChanged) Q_PROPERTY(QString prearmError READ prearmError WRITE setPrearmError NOTIFY prearmErrorChanged)
Q_PROPERTY(int motorCount READ motorCount CONSTANT)
Q_PROPERTY(bool coaxialMotors READ coaxialMotors CONSTANT)
Q_PROPERTY(bool xConfigMotors READ xConfigMotors CONSTANT)
/// true: Vehicle is flying, false: Vehicle is on ground /// true: Vehicle is flying, false: Vehicle is on ground
Q_PROPERTY(bool flying READ flying WRITE setFlying NOTIFY flyingChanged) Q_PROPERTY(bool flying READ flying WRITE setFlying NOTIFY flyingChanged)
...@@ -362,6 +365,12 @@ public: ...@@ -362,6 +365,12 @@ public:
/// Clear Messages /// Clear Messages
Q_INVOKABLE void clearMessages(); Q_INVOKABLE void clearMessages();
/// Test motor
/// @param motor Motor number, 1-based
/// @param percent 0-no power, 100-full power
/// @param timeoutSecs Number of seconds for motor to run
Q_INVOKABLE void motorTest(int motor, int percent, int timeoutSecs);
bool guidedModeSupported(void) const; bool guidedModeSupported(void) const;
bool pauseVehicleSupported(void) const; bool pauseVehicleSupported(void) const;
...@@ -438,7 +447,6 @@ public: ...@@ -438,7 +447,6 @@ public:
QString flightMode(void) const; QString flightMode(void) const;
void setFlightMode(const QString& flightMode); void setFlightMode(const QString& flightMode);
bool hilMode(void); bool hilMode(void);
void setHilMode(bool hilMode); void setHilMode(bool hilMode);
...@@ -535,6 +543,15 @@ public: ...@@ -535,6 +543,15 @@ public:
int defaultComponentId(void); int defaultComponentId(void);
/// @return -1 = Unknown, Number of motors on vehicle
int motorCount(void);
/// @return true: Motors are coaxial like an X8 config, false: Quadcopter for example
bool coaxialMotors(void);
/// @return true: X confiuration, false: Plus configuration
bool xConfigMotors(void);
public slots: public slots:
void setLatitude(double latitude); void setLatitude(double latitude);
void setLongitude(double longitude); void setLongitude(double longitude);
......
...@@ -97,6 +97,7 @@ Rectangle { ...@@ -97,6 +97,7 @@ Rectangle {
_messagePanelText = vehicleComponent.prerequisiteSetup + " setup must be completed prior to " + vehicleComponent.name + " setup." _messagePanelText = vehicleComponent.prerequisiteSetup + " setup must be completed prior to " + vehicleComponent.name + " setup."
panelLoader.sourceComponent = messagePanelComponent panelLoader.sourceComponent = messagePanelComponent
} else { } else {
panelLoader.vehicleComponent = vehicleComponent
panelLoader.source = vehicleComponent.setupSource panelLoader.source = vehicleComponent.setupSource
for(var i = 0; i < componentRepeater.count; i++) { for(var i = 0; i < componentRepeater.count; i++) {
var obj = componentRepeater.itemAt(i); var obj = componentRepeater.itemAt(i);
...@@ -324,5 +325,7 @@ Rectangle { ...@@ -324,5 +325,7 @@ Rectangle {
anchors.right: parent.right anchors.right: parent.right
anchors.top: parent.top anchors.top: parent.top
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
property var vehicleComponent
} }
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment