Unverified Commit 4dec1b4c authored by Don Gagne's avatar Don Gagne Committed by GitHub

Merge pull request #8993 from DonLakeFlyer/ForceArm

Force arm support
parents 9b9d8130 50acd9a9
......@@ -4,6 +4,7 @@ Note: This file only contains high level features or important fixes.
## 4.1 - Daily build
* Fly: Press and hold on arm button will change it to Force Arm. Click again to force arm.
* VTOL: General setting for transition distance which affects Plan takeoff, landing pattern creation
* VTOL: Much better VTOL support throughout QGC
* Maps: Support zoom up to level 23 even if map provider doesn't provide tiles that high
......
......@@ -61,8 +61,6 @@ SetupPage {
property real _margins: ScreenTools.defaultFontPixelHeight
property bool _showIcon: !ScreenTools.isTinyScreen
ExclusiveGroup { id: fenceActionRadioGroup }
Column {
spacing: _margins / 2
......
......@@ -59,10 +59,6 @@ SetupPage {
property bool _loadComplete: false
ExclusiveGroup { id: fenceActionRadioGroup }
ExclusiveGroup { id: landLoiterRadioGroup }
ExclusiveGroup { id: returnAltRadioGroup }
Component.onCompleted: {
// We use QtCharts only on Desktop platforms
showAdvanced = !ScreenTools.isMobile
......
......@@ -34,14 +34,12 @@ SetupPage {
property real _margins: ScreenTools.defaultFontPixelHeight
ExclusiveGroup { id: buttonGroup }
Row {
spacing: _margins
QGCButton {
id: atcButton
text: qsTr("Attitude Controller Parameters")
exclusiveGroup: buttonGroup
autoExclusive: true
checked: true
onClicked: checked = true
}
......@@ -49,14 +47,14 @@ SetupPage {
QGCButton {
id: posButton
text: qsTr("Position Controller Parameters")
exclusiveGroup: buttonGroup
autoExclusive: true
onClicked: checked = true
}
QGCButton {
id: navButton
text: qsTr("Waypoint navigation parameters")
exclusiveGroup: buttonGroup
autoExclusive: true
onClicked: checked = true
}
}
......
......@@ -35,6 +35,7 @@ Item {
readonly property string emergencyStopTitle: qsTr("EMERGENCY STOP")
readonly property string armTitle: qsTr("Arm")
readonly property string forceArmTitle: qsTr("Force Arm")
readonly property string disarmTitle: qsTr("Disarm")
readonly property string rtlTitle: qsTr("Return")
readonly property string takeoffTitle: qsTr("Takeoff")
......@@ -55,6 +56,7 @@ Item {
readonly property string actionListTitle: qsTr("Action")
readonly property string armMessage: qsTr("Arm the vehicle.")
readonly property string forceArmMessage: qsTr("WARNING: This will force arming of the vehicle bypassing any safety checks.")
readonly property string disarmMessage: qsTr("Disarm the vehicle")
readonly property string emergencyStopMessage: qsTr("WARNING: THIS WILL STOP ALL MOTORS. IF VEHICLE IS CURRENTLY IN THE AIR IT WILL CRASH.")
readonly property string takeoffMessage: qsTr("Takeoff from ground and hold position.")
......@@ -97,6 +99,7 @@ Item {
readonly property int actionVtolTransitionToMRFlight: 21
readonly property int actionROI: 22
readonly property int actionActionList: 23
readonly property int actionForceArm: 24
property bool _useChecklist: QGroundControl.settingsManager.appSettings.useChecklist.rawValue && QGroundControl.corePlugin.options.preFlightChecklistUrl.toString().length
property bool _enforceChecklist: _useChecklist && QGroundControl.settingsManager.appSettings.enforceChecklist.rawValue
......@@ -104,6 +107,7 @@ Item {
property bool showEmergenyStop: _guidedActionsEnabled && !_hideEmergenyStop && _vehicleArmed && _vehicleFlying
property bool showArm: _guidedActionsEnabled && !_vehicleArmed && _canArm
property bool showForceArm: _guidedActionsEnabled && !_vehicleArmed
property bool showDisarm: _guidedActionsEnabled && _vehicleArmed && !_vehicleFlying
property bool showRTL: _guidedActionsEnabled && _vehicleArmed && activeVehicle.guidedModeSupported && _vehicleFlying && !_vehicleInRTLMode
property bool showTakeoff: _guidedActionsEnabled && activeVehicle.takeoffVehicleSupported && !_vehicleFlying && _canArm
......@@ -274,6 +278,7 @@ Item {
Connections {
target: mainWindow
onArmVehicleRequest: armVehicleRequest()
onForceArmVehicleRequest: forceArmVehicleRequest()
onDisarmVehicleRequest: disarmVehicleRequest()
onVtolTransitionToFwdFlightRequest: vtolTransitionToFwdFlightRequest()
onVtolTransitionToMRFlightRequest: vtolTransitionToMRFlightRequest()
......@@ -283,6 +288,10 @@ Item {
confirmAction(actionArm)
}
function forceArmVehicleRequest() {
confirmAction(actionForceArm)
}
function disarmVehicleRequest() {
if (showEmergenyStop) {
confirmAction(actionEmergencyStop)
......@@ -325,6 +334,11 @@ Item {
confirmDialog.message = armMessage
confirmDialog.hideTrigger = Qt.binding(function() { return !showArm })
break;
case actionForceArm:
confirmDialog.title = forceArmTitle
confirmDialog.message = forceArmMessage
confirmDialog.hideTrigger = Qt.binding(function() { return !showForceArm })
break;
case actionDisarm:
if (_vehicleFlying) {
return
......@@ -480,6 +494,9 @@ Item {
case actionArm:
activeVehicle.armed = true
break
case actionForceArm:
activeVehicle.forceArm()
break
case actionDisarm:
activeVehicle.armed = false
break
......
......@@ -28,10 +28,6 @@ Column {
QGCPalette { id: qgcPal; colorGroupEnabled: true }
ExclusiveGroup {
id: cameraOrientationGroup
}
Column {
anchors.left: parent.left
anchors.right: parent.right
......
......@@ -188,8 +188,6 @@ Item {
}
}
ExclusiveGroup { id: buttonGroup }
Repeater {
model: categoryHeader.checked ? controller.getGroupsForCategory(category) : 0
......@@ -198,7 +196,7 @@ Item {
text: groupName
height: _rowHeight
checked: controller.currentGroup === text
exclusiveGroup: buttonGroup
autoExclusive: true
readonly property string groupName: modelData
......
import QtQuick 2.3
import QtQuick.Controls 1.2
import QtQuick.Controls.Styles 1.4
import QtQuick 2.3
import QtQuick.Controls 2.12
import QtQuick.Controls.Styles 1.4
import QGroundControl.Palette 1.0
import QGroundControl.ScreenTools 1.0
Button {
activeFocusOnPress: true
id: control
hoverEnabled: true
topPadding: _verticalPadding
bottomPadding: _verticalPadding
leftPadding: _horizontalPadding
rightPadding: _horizontalPadding
focusPolicy: Qt.ClickFocus
property bool primary: false ///< primary button for a group of buttons
property real pointSize: ScreenTools.defaultFontPointSize ///< Point size for button text
property bool showBorder: _qgcPal.globalTheme === QGCPalette.Light
property bool showBorder: qgcPal.globalTheme === QGCPalette.Light
property bool iconLeft: false
property real backRadius: 0
property real heightFactor: 0.5
property string iconSource
property var _qgcPal: QGCPalette { colorGroupEnabled: enabled }
property bool _showHighlight: (pressed | hovered | checked) && !__forceHoverOff
property bool _showHighlight: pressed | hovered | checked
// This fixes the issue with button hover where if a Button is near the edge oa QQuickWidget you can
// move the mouse fast enough such that the MouseArea does not trigger an onExited. This is turn
// cause the hover property to not be cleared correctly.
property bool __forceHoverOff: false
property int __lastGlobalMouseX: 0
property int __lastGlobalMouseY: 0
property int _horizontalPadding: ScreenTools.defaultFontPixelWidth
property int _verticalPadding: Math.round(ScreenTools.defaultFontPixelHeight * heightFactor)
Connections {
target: __behavior
onMouseXChanged: {
__lastGlobalMouseX = ScreenTools.mouseX()
__lastGlobalMouseY = ScreenTools.mouseY()
}
onMouseYChanged: {
__lastGlobalMouseX = ScreenTools.mouseX()
__lastGlobalMouseY = ScreenTools.mouseY()
}
onEntered: { __forceHoverOff = false; hoverTimer.start() }
onExited: { __forceHoverOff = false; hoverTimer.stop() }
}
QGCPalette { id: qgcPal; colorGroupEnabled: enabled }
Timer {
id: hoverTimer
interval: 250
repeat: true
onTriggered: {
__forceHoverOff = (__lastGlobalMouseX !== ScreenTools.mouseX() || __lastGlobalMouseY !== ScreenTools.mouseY());
}
background: Rectangle {
id: backRect
implicitWidth: ScreenTools.implicitButtonWidth
implicitHeight: ScreenTools.implicitButtonHeight
radius: backRadius
border.width: showBorder ? 1 : 0
border.color: qgcPal.buttonText
color: _showHighlight ?
qgcPal.buttonHighlight :
(primary ? qgcPal.primaryButton : qgcPal.button)
}
style: ButtonStyle {
/*! The padding between the background and the label components. */
padding {
top: _verticalPadding
bottom: _verticalPadding
left: _horizontalPadding
right: _horizontalPadding
}
/*! This defines the background of the button. */
background: Rectangle {
id: backRect
implicitWidth: ScreenTools.implicitButtonWidth
implicitHeight: ScreenTools.implicitButtonHeight
radius: backRadius
border.width: showBorder ? 1 : 0
border.color: _qgcPal.buttonText
color: _showHighlight ?
control._qgcPal.buttonHighlight :
(primary ? control._qgcPal.primaryButton : control._qgcPal.button)
}
/*! This defines the label of the button. */
label: Item {
implicitWidth: text.implicitWidth + icon.width
implicitHeight: text.implicitHeight
baselineOffset: text.y + text.baselineOffset
contentItem: Item {
implicitWidth: text.implicitWidth + icon.width
implicitHeight: text.implicitHeight
baselineOffset: text.y + text.baselineOffset
QGCColoredImage {
id: icon
source: control.iconSource
height: source === "" ? 0 : text.height
width: height
color: text.color
fillMode: Image.PreserveAspectFit
sourceSize.height: height
anchors.left: control.iconLeft ? parent.left : undefined
anchors.leftMargin: control.iconLeft ? ScreenTools.defaultFontPixelWidth : undefined
anchors.right: !control.iconLeft ? parent.right : undefined
anchors.rightMargin: !control.iconLeft ? ScreenTools.defaultFontPixelWidth : undefined
anchors.verticalCenter: parent.verticalCenter
}
QGCColoredImage {
id: icon
source: control.iconSource
height: source === "" ? 0 : text.height
width: height
color: text.color
fillMode: Image.PreserveAspectFit
sourceSize.height: height
anchors.left: control.iconLeft ? parent.left : undefined
anchors.leftMargin: control.iconLeft ? ScreenTools.defaultFontPixelWidth : undefined
anchors.right: !control.iconLeft ? parent.right : undefined
anchors.rightMargin: !control.iconLeft ? ScreenTools.defaultFontPixelWidth : undefined
anchors.verticalCenter: parent.verticalCenter
}
Text {
id: text
anchors.centerIn: parent
antialiasing: true
text: control.text
font.pointSize: pointSize
font.family: ScreenTools.normalFontFamily
color: _showHighlight ?
control._qgcPal.buttonHighlightText :
(primary ? control._qgcPal.primaryButtonText : control._qgcPal.buttonText)
}
}
Text {
id: text
anchors.centerIn: parent
antialiasing: true
text: control.text
font.pointSize: pointSize
font.family: ScreenTools.normalFontFamily
color: _showHighlight ?
qgcPal.buttonHighlightText :
(primary ? qgcPal.primaryButtonText : qgcPal.buttonText)
}
}
}
......@@ -2397,6 +2397,15 @@ void Vehicle::setArmed(bool armed)
armed ? 1.0f : 0.0f);
}
void Vehicle::forceArm(void)
{
sendMavCommand(_defaultComponentId,
MAV_CMD_COMPONENT_ARM_DISARM,
true, // show error if fails
1.0f, // arm
2989); // force arm
}
bool Vehicle::flightModeSetAvailable()
{
return _firmwarePlugin->isCapable(this, FirmwarePlugin::SetFlightModeCapability);
......
......@@ -791,6 +791,7 @@ public:
Q_INVOKABLE void gimbalPitchStep (int direction);
Q_INVOKABLE void gimbalYawStep (int direction);
Q_INVOKABLE void centerGimbal ();
Q_INVOKABLE void forceArm ();
/// Sends PARAM_MAP_RC message to vehicle
Q_INVOKABLE void sendParamMapRC(const QString& paramName, double scale, double centerValue, int tuningID, double minValue, double maxValue);
......
......@@ -49,8 +49,6 @@ Rectangle {
flickableDirection: Flickable.VerticalFlick
clip: true
ExclusiveGroup { id: panelActionGroup }
ColumnLayout {
id: buttonColumn
spacing: _verticalMargin
......@@ -62,7 +60,7 @@ Rectangle {
QGCButton {
height: _buttonHeight
text: modelData.title
exclusiveGroup: panelActionGroup
autoExclusive: true
Layout.fillWidth: true
onClicked: {
......
......@@ -96,6 +96,7 @@ ApplicationWindow {
//-- Actions
signal armVehicleRequest
signal forceArmVehicleRequest
signal disarmVehicleRequest
signal vtolTransitionToFwdFlightRequest
signal vtolTransitionToMRFlightRequest
......
......@@ -25,7 +25,6 @@ Column {
function saveSettings() {
// No need
}
ExclusiveGroup { id: linkGroup }
Row {
spacing: ScreenTools.defaultFontPixelWidth
QGCLabel {
......@@ -79,10 +78,10 @@ Column {
model: subEditConfig && subEditConfig.linkType === LinkConfiguration.TypeBluetooth ? subEditConfig.nameList : ""
delegate:
QGCButton {
text: modelData
width: _secondColumn
text: modelData
width: _secondColumn
anchors.leftMargin: ScreenTools.defaultFontPixelWidth * 2
exclusiveGroup: linkGroup
autoExclusive: true
onClicked: {
checked = true
if(subEditConfig && modelData !== "")
......
......@@ -27,8 +27,6 @@ Rectangle {
property int _firstColumn: ScreenTools.defaultFontPixelWidth * 12
property int _secondColumn: ScreenTools.defaultFontPixelWidth * 30
ExclusiveGroup { id: linkGroup }
QGCPalette {
id: qgcPal
colorGroupEnabled: enabled
......@@ -65,7 +63,7 @@ Rectangle {
anchors.horizontalCenter: settingsColumn.horizontalCenter
width: _linkRoot.width * 0.5
text: object.name
exclusiveGroup: linkGroup
autoExclusive: true
visible: !object.dynamic
onClicked: {
checked = true
......
......@@ -28,8 +28,6 @@ Column {
property string _currentHost: ""
ExclusiveGroup { id: linkGroup }
Row {
spacing: ScreenTools.defaultFontPixelWidth
QGCLabel {
......@@ -81,10 +79,10 @@ Column {
model: subEditConfig && subEditConfig.linkType === LinkConfiguration.TypeUdp ? subEditConfig.hostList : ""
delegate:
QGCButton {
text: modelData
width: _secondColumn
text: modelData
width: _secondColumn
anchors.leftMargin: ScreenTools.defaultFontPixelWidth * 2
exclusiveGroup: linkGroup
autoExclusive: true
onClicked: {
checked = true
_udpSetting._currentHost = modelData
......
......@@ -190,13 +190,23 @@ RowLayout {
QGCButton {
Layout.alignment: Qt.AlignHCenter
text: _armed ? qsTr("Disarm") : qsTr("Arm")
text: _armed ? qsTr("Disarm") : (forceArm ? qsTr("Force Arm") : qsTr("Arm"))
property bool forceArm: false
onPressAndHold: forceArm = true
onClicked: {
if (_armed) {
mainWindow.disarmVehicleRequest()
} else {
mainWindow.armVehicleRequest()
if (forceArm) {
mainWindow.forceArmVehicleRequest()
} else {
mainWindow.armVehicleRequest()
}
}
forceArm = false
mainWindow.hideIndicatorPopup()
}
}
......
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