/**************************************************************************** * * (c) 2009-2016 QGROUNDCONTROL PROJECT * * 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.Dialogs 1.2 import QtQuick.Layouts 1.2 import QGroundControl.FactSystem 1.0 import QGroundControl.FactControls 1.0 import QGroundControl.Controls 1.0 import QGroundControl.ScreenTools 1.0 import QGroundControl.Controllers 1.0 SetupPage { id: powerPage pageComponent: pageComponent Component { id: pageComponent Item { width: Math.max(availableWidth, innerColumn.width) height: innerColumn.height ColumnLayout { id: innerColumn anchors.horizontalCenter: parent.horizontalCenter spacing: ScreenTools.defaultFontPixelHeight property int textEditWidth: ScreenTools.defaultFontPixelWidth * 8 property Fact battNumCells: controller.getParameterFact(-1, "BAT_N_CELLS") property Fact battHighVolt: controller.getParameterFact(-1, "BAT_V_CHARGED") property Fact battLowVolt: controller.getParameterFact(-1, "BAT_V_EMPTY") property Fact battVoltLoadDrop: controller.getParameterFact(-1, "BAT_V_LOAD_DROP") property Fact battVoltageDivider: controller.getParameterFact(-1, "BAT_V_DIV") property Fact battAmpsPerVolt: controller.getParameterFact(-1, "BAT_A_PER_V") property Fact uavcanEnable: controller.getParameterFact(-1, "UAVCAN_ENABLE", false) readonly property string highlightPrefix: "" readonly property string highlightSuffix: "" function getBatteryImage() { switch(battNumCells.value) { case 1: return "/qmlimages/PowerComponentBattery_01cell.svg"; case 2: return "/qmlimages/PowerComponentBattery_02cell.svg" case 3: return "/qmlimages/PowerComponentBattery_03cell.svg" case 4: return "/qmlimages/PowerComponentBattery_04cell.svg" case 5: return "/qmlimages/PowerComponentBattery_05cell.svg" case 6: return "/qmlimages/PowerComponentBattery_06cell.svg" default: return "/qmlimages/PowerComponentBattery_01cell.svg"; } } function drawArrowhead(ctx, x, y, radians) { ctx.save(); ctx.beginPath(); ctx.translate(x,y); ctx.rotate(radians); ctx.moveTo(0,0); ctx.lineTo(5,10); ctx.lineTo(-5,10); ctx.closePath(); ctx.restore(); ctx.fill(); } function drawLineWithArrow(ctx, x1, y1, x2, y2) { ctx.beginPath(); ctx.moveTo(x1, y1); ctx.lineTo(x2, y2); ctx.stroke(); var rd = Math.atan((y2 - y1) / (x2 - x1)); rd += ((x2 > x1) ? 90 : -90) * Math.PI/180; drawArrowhead(ctx, x2, y2, rd); } PowerComponentController { id: controller factPanel: powerPage.viewPanel onOldFirmware: showMessage(qsTr("ESC Calibration"), qsTr("QGroundControl cannot perform ESC Calibration with this version of firmware. You will need to upgrade to a newer firmware."), StandardButton.Ok) onNewerFirmware: showMessage(qsTr("ESC Calibration"), qsTr("QGroundControl cannot perform ESC Calibration with this version of firmware. You will need to upgrade QGroundControl."), StandardButton.Ok) onBatteryConnected: showMessage(qsTr("ESC Calibration"), qsTr("Performing calibration. This will take a few seconds.."), 0) onCalibrationFailed: showMessage(qsTr("ESC Calibration failed"), errorMessage, StandardButton.Ok) onCalibrationSuccess: showMessage(qsTr("ESC Calibration"), qsTr("Calibration complete. You can disconnect your battery now if you like."), StandardButton.Ok) onConnectBattery: showMessage(qsTr("ESC Calibration"), highlightPrefix + qsTr("WARNING: Props must be removed from vehicle prior to performing ESC calibration.") + highlightSuffix + qsTr(" Connect the battery now and calibration will begin."), 0) onDisconnectBattery: showMessage(qsTr("ESC Calibration failed"), qsTr("You must disconnect the battery prior to performing ESC Calibration. Disconnect your battery and try again."), StandardButton.Ok) } Component { id: calcVoltageDividerDlgComponent QGCViewDialog { id: calcVoltageDividerDlg QGCFlickable { anchors.fill: parent contentHeight: column.height contentWidth: column.width Column { id: column width: calcVoltageDividerDlg.width spacing: ScreenTools.defaultFontPixelHeight QGCLabel { width: parent.width wrapMode: Text.WordWrap text: "Measure battery voltage using an external voltmeter and enter the value below. Click Calculate to set the new voltage multiplier." } Grid { columns: 2 spacing: ScreenTools.defaultFontPixelHeight / 2 verticalItemAlignment: Grid.AlignVCenter QGCLabel { text: "Measured voltage:" } QGCTextField { id: measuredVoltage } QGCLabel { text: "Vehicle voltage:" } QGCLabel { text: controller.vehicle.battery.voltage.valueString } QGCLabel { text: "Voltage divider:" } FactLabel { fact: battVoltageDivider } } QGCButton { text: "Calculate" onClicked: { var measuredVoltageValue = parseFloat(measuredVoltage.text) if (measuredVoltageValue == 0 || isNaN(measuredVoltageValue)) { return } var newVoltageDivider = (measuredVoltageValue * battVoltageDivider.value) / controller.vehicle.battery.voltage.value if (newVoltageDivider > 0) { battVoltageDivider.value = newVoltageDivider } } } } // Column } // QGCFlickable } // QGCViewDialog } // Component - calcVoltageDividerDlgComponent Component { id: calcAmpsPerVoltDlgComponent QGCViewDialog { id: calcAmpsPerVoltDlg QGCFlickable { anchors.fill: parent contentHeight: column.height contentWidth: column.width Column { id: column width: calcAmpsPerVoltDlg.width spacing: ScreenTools.defaultFontPixelHeight QGCLabel { width: parent.width wrapMode: Text.WordWrap text: "Measure current draw using an external current meter and enter the value below. Click Calculate to set the new amps per volt value." } Grid { columns: 2 spacing: ScreenTools.defaultFontPixelHeight / 2 verticalItemAlignment: Grid.AlignVCenter QGCLabel { text: "Measured current:" } QGCTextField { id: measuredCurrent } QGCLabel { text: "Vehicle current:" } QGCLabel { text: controller.vehicle.battery.current.valueString } QGCLabel { text: "Amps per volt:" } FactLabel { fact: battAmpsPerVolt } } QGCButton { text: "Calculate" onClicked: { var measuredCurrentValue = parseFloat(measuredCurrent.text) if (measuredCurrentValue == 0) { return } var newAmpsPerVolt = (measuredCurrentValue * battAmpsPerVolt.value) / controller.vehicle.battery.current.value if (newAmpsPerVolt != 0) { battAmpsPerVolt.value = newAmpsPerVolt } } } } // Column } // QGCFlickable } // QGCViewDialog } // Component - calcAmpsPerVoltDlgComponent QGCGroupBox { id: batteryGroup title: qsTr("Battery") GridLayout { id: batteryGrid columns: 5 columnSpacing: ScreenTools.defaultFontPixelWidth QGCLabel { text: qsTr("Number of Cells (in Series)") } FactTextField { id: cellsField width: textEditWidth fact: battNumCells showUnits: true } QGCColoredImage { id: batteryImage Layout.rowSpan: 3 width: height * 0.75 height: 100 sourceSize.height: height fillMode: Image.PreserveAspectFit smooth: true color: qgcPal.text cache: false source: getBatteryImage(); } Item { width: 1; height: 1; Layout.columnSpan: 2 } QGCLabel { id: battHighLabel text: qsTr("Full Voltage (per cell)") } FactTextField { id: battHighField width: textEditWidth fact: battHighVolt showUnits: true } QGCLabel { text: qsTr("Battery Max:") } QGCLabel { text: (battNumCells.value * battHighVolt.value).toFixed(1) + ' V' } QGCLabel { id: battLowLabel text: qsTr("Empty Voltage (per cell)") } FactTextField { id: battLowField width: textEditWidth fact: battLowVolt showUnits: true } QGCLabel { text: qsTr("Battery Min:") } QGCLabel { text: (battNumCells.value * battLowVolt.value).toFixed(1) + ' V' } QGCLabel { text: qsTr("Voltage divider") } FactTextField { id: voltMultField fact: battVoltageDivider } QGCButton { id: voltMultCalculateButton text: "Calculate" onClicked: showDialog(calcVoltageDividerDlgComponent, qsTr("Calculate Voltage Divider"), powerPage.showDialogDefaultWidth, StandardButton.Close) } Item { width: 1; height: 1; Layout.columnSpan: 2 } QGCLabel { id: voltMultHelp Layout.columnSpan: batteryGrid.columns Layout.fillWidth: true font.pointSize: ScreenTools.smallFontPointSize wrapMode: Text.WordWrap text: "If the battery voltage reported by the vehicle is largely different than the voltage read externally using a voltmeter you can adjust the voltage multiplier value to correct this. " + "Click the Calculate button for help with calculating a new value." } QGCLabel { id: ampPerVoltLabel text: qsTr("Amps per volt") } FactTextField { id: ampPerVoltField fact: battAmpsPerVolt } QGCButton { id: ampPerVoltCalculateButton text: "Calculate" onClicked: showDialog(calcAmpsPerVoltDlgComponent, qsTr("Calculate Amps per Volt"), powerPage.showDialogDefaultWidth, StandardButton.Close) } Item { width: 1; height: 1; Layout.columnSpan: 2 } QGCLabel { id: ampPerVoltHelp Layout.columnSpan: batteryGrid.columns Layout.fillWidth: true font.pointSize: ScreenTools.smallFontPointSize wrapMode: Text.WordWrap text: "If the current draw reported by the vehicle is largely different than the current read externally using a current meter you can adjust the amps per volt value to correct this. " + "Click the Calculate button for help with calculating a new value." } } // Grid } // QGCGroupBox - Battery settings QGCGroupBox { anchors.left: batteryGroup.left anchors.right: batteryGroup.right title: qsTr("ESC PWM Minimum and Maximum Calibration") ColumnLayout { anchors.left: parent.left anchors.right: parent.right spacing: ScreenTools.defaultFontPixelWidth QGCLabel { color: qgcPal.warningText wrapMode: Text.WordWrap text: qsTr("WARNING: Propellers must be removed from vehicle prior to performing ESC calibration.") Layout.fillWidth: true } QGCLabel { text: qsTr("You must use USB connection for this operation.") } QGCButton { text: qsTr("Calibrate") width: ScreenTools.defaultFontPixelWidth * 20 onClicked: controller.calibrateEsc() } } } QGCCheckBox { id: showUAVCAN text: qsTr("Show UAVCAN Settings") checked: uavcanEnable.rawValue != 0 } QGCGroupBox { anchors.left: batteryGroup.left anchors.right: batteryGroup.right title: qsTr("UAVCAN Bus Configuration") visible: showUAVCAN.checked Row { id: uavCanConfigRow spacing: ScreenTools.defaultFontPixelWidth FactComboBox { id: uavcanEnabledCheckBox width: ScreenTools.defaultFontPixelWidth * 20 fact: uavcanEnable indexModel: false } QGCLabel { anchors.verticalCenter: parent.verticalCenter text: qsTr("Change required restart") } } } QGCGroupBox { anchors.left: batteryGroup.left anchors.right: batteryGroup.right title: qsTr("UAVCAN Motor Index and Direction Assignment") visible: showUAVCAN.checked ColumnLayout { anchors.left: parent.left anchors.right: parent.right spacing: ScreenTools.defaultFontPixelWidth QGCLabel { wrapMode: Text.WordWrap color: qgcPal.warningText text: qsTr("WARNING: Propellers must be removed from vehicle prior to performing UAVCAN ESC configuration.") Layout.fillWidth: true } QGCLabel { wrapMode: Text.WordWrap text: qsTr("ESC parameters will only be accessible in the editor after assignment.") Layout.fillWidth: true } QGCLabel { wrapMode: Text.WordWrap text: qsTr("Start the process, then turn each motor into its turn direction, in the order of their motor indices.") Layout.fillWidth: true } QGCButton { text: qsTr("Start Assignment") width: ScreenTools.defaultFontPixelWidth * 20 onClicked: controller.busConfigureActuators() } QGCButton { text: qsTr("Stop Assignment") width: ScreenTools.defaultFontPixelWidth * 20 onClicked: controller.stopBusConfigureActuators() } } } QGCCheckBox { id: showAdvanced text: qsTr("Show Advanced Settings") } QGCGroupBox { anchors.left: batteryGroup.left anchors.right: batteryGroup.right title: qsTr("Advanced Power Settings") visible: showAdvanced.checked ColumnLayout { anchors.left: parent.left anchors.right: parent.right spacing: ScreenTools.defaultFontPixelWidth Row { spacing: ScreenTools.defaultFontPixelWidth QGCLabel { text: qsTr("Voltage Drop on Full Load (per cell)") anchors.baseline: battDropField.baseline } FactTextField { id: battDropField width: textEditWidth fact: battVoltLoadDrop showUnits: true } } QGCLabel { wrapMode: Text.WordWrap text: qsTr("Batteries show less voltage at high throttle. Enter the difference in Volts between idle throttle and full ") + qsTr("throttle, divided by the number of battery cells. Leave at the default if unsure. ") + highlightPrefix + qsTr("If this value is set too high, the battery might be deep discharged and damaged.") + highlightSuffix Layout.fillWidth: true } Row { spacing: ScreenTools.defaultFontPixelWidth QGCLabel { text: qsTr("Compensated Minimum Voltage:") } QGCLabel { text: ((battNumCells.value * battLowVolt.value) - (battNumCells.value * battVoltLoadDrop.value)).toFixed(1) + qsTr(" V") } } } // Column } // QGCGroupBox - Advanced power settings } // Column } // Item } // Component } // SetupPage