Skip to content
QGCView.qml 11.9 KiB
Newer Older
/****************************************************************************
 *
 *   (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.
 *
 ****************************************************************************/
Don Gagne's avatar
Don Gagne committed


/// @file
///     @author Don Gagne <don@thegagnes.com>

import QtQuick 2.3
import QtQuick.Controls 1.3
import QtQuick.Dialogs 1.2

import QGroundControl.Controls 1.0
import QGroundControl.Palette 1.0
import QGroundControl.ScreenTools 1.0
import QGroundControl.FactSystem 1.0
import QGroundControl.FactControls 1.0

Don Gagne's avatar
Don Gagne committed
FactPanel {
Don Gagne's avatar
Don Gagne committed
    id: __rootItem

    property var qgcView:               __rootItem  ///< Used by Fact controls for validation dialogs
Don Gagne's avatar
Don Gagne committed
    property bool completedSignalled:   false
    property real topDialogMargin:      0           ///< Set a top margin for dialog
    property var viewPanel
Don Gagne's avatar
Don Gagne committed
    /// This is signalled when the top level Item reaches Component.onCompleted. This allows
    /// the view subcomponent to connect to this signal and do work once the full ui is ready
    /// to go.
    signal completed

Don Gagne's avatar
Don Gagne committed
    function __setupDialogButtons(buttons) {
Don Gagne's avatar
Don Gagne committed
        __acceptButton.visible = false
        __rejectButton.visible = false

Don Gagne's avatar
Don Gagne committed
        // Accept role buttons
Don Gagne's avatar
Don Gagne committed
        if (buttons & StandardButton.Ok) {
            __acceptButton.text = qsTr("Ok")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Open) {
            __acceptButton.text = qsTr("Open")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Save) {
            __acceptButton.text = qsTr("Save")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Apply) {
            __acceptButton.text = qsTr("Apply")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Open) {
            __acceptButton.text = qsTr("Open")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.SaveAll) {
            __acceptButton.text = qsTr("Save All")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Yes) {
            __acceptButton.text = qsTr("Yes")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.YesToAll) {
            __acceptButton.text = qsTr("Yes to All")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Retry) {
            __acceptButton.text = qsTr("Retry")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Reset) {
            __acceptButton.text = qsTr("Reset")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.RestoreToDefaults) {
            __acceptButton.text = qsTr("Restore to Defaults")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        } else if (buttons & StandardButton.Ignore) {
            __acceptButton.text = qsTr("Ignore")
Don Gagne's avatar
Don Gagne committed
            __acceptButton.visible = true
        }
Don Gagne's avatar
Don Gagne committed

        // Reject role buttons
        if (buttons & StandardButton.Cancel) {
            __rejectButton.text = qsTr("Cancel")
Don Gagne's avatar
Don Gagne committed
            __rejectButton.visible = true
        } else if (buttons & StandardButton.Close) {
            __rejectButton.text = qsTr("Close")
Don Gagne's avatar
Don Gagne committed
            __rejectButton.visible = true
        } else if (buttons & StandardButton.No) {
            __rejectButton.text = qsTr("No")
Don Gagne's avatar
Don Gagne committed
            __rejectButton.visible = true
        } else if (buttons & StandardButton.NoToAll) {
            __rejectButton.text = qsTr("No to All")
Don Gagne's avatar
Don Gagne committed
            __rejectButton.visible = true
        } else if (buttons & StandardButton.Abort) {
            __rejectButton.text = qsTr("Abort")
Don Gagne's avatar
Don Gagne committed
            __rejectButton.visible = true
        }
Don Gagne's avatar
Don Gagne committed
    }

    function __stopAllAnimations() {
        if (__animateHideDialog.running) {
            __animateHideDialog.stop()
        }
    }

Don Gagne's avatar
Don Gagne committed
    function __checkForEarlyDialog(title) {
        if (!completedSignalled) {
            console.warn(qsTr("showDialog|Message called before QGCView.completed signalled"), title)
    /// Shows a QGCViewDialog component
    ///     @param compoent QGCViewDialog component
    ///     @param title Title for dialog
    ///     @param charWidth Width of dialog in characters
    ///     @param buttons Buttons to show in dialog using StandardButton enum

    readonly property int showDialogFullWidth:      -1  ///< Use for full width dialog
    readonly property int showDialogDefaultWidth:   40  ///< Use for default dialog width

    function showDialog(component, title, charWidth, buttons) {
Don Gagne's avatar
Don Gagne committed
        if (__checkForEarlyDialog(title)) {
        __rejectButton.enabled = true
        __acceptButton.enabled = true

        __stopAllAnimations()

Don Gagne's avatar
Don Gagne committed
        __dialogCharWidth = charWidth
        __dialogTitle = title

        __setupDialogButtons(buttons)
Don Gagne's avatar
Don Gagne committed
        __dialogComponent = component
        viewPanel.enabled = false
Don Gagne's avatar
Don Gagne committed
        __dialogOverlay.visible = true
Don Gagne's avatar
Don Gagne committed

        //__dialogComponentLoader.item.forceActiveFocus()
Don Gagne's avatar
Don Gagne committed
        __animateShowDialog.start()
Don Gagne's avatar
Don Gagne committed
    function showMessage(title, message, buttons) {
Don Gagne's avatar
Don Gagne committed
        if (__checkForEarlyDialog(title)) {
        __rejectButton.enabled = true
        __acceptButton.enabled = true

        __stopAllAnimations()

        __dialogCharWidth = showDialogDefaultWidth
Don Gagne's avatar
Don Gagne committed
        __dialogTitle = title
        __messageDialogText = message

        __setupDialogButtons(buttons)

        __dialogComponent = __messageDialog
        viewPanel.enabled = false
Don Gagne's avatar
Don Gagne committed
        __dialogOverlay.visible = true
Don Gagne's avatar
Don Gagne committed

        __dialogComponentLoader.item.forceActiveFocus()

Don Gagne's avatar
Don Gagne committed
        __animateShowDialog.start()
Don Gagne's avatar
Don Gagne committed
    function hideDialog() {
        //__dialogComponentLoader.item.focus = false
        viewPanel.enabled = true
Don Gagne's avatar
Don Gagne committed
        __animateHideDialog.start()
Don Gagne's avatar
Don Gagne committed
    }

    QGCPalette { id: __qgcPal; colorGroupEnabled: true }
    QGCLabel { id: __textMeasure; text: "X"; visible: false }

Don Gagne's avatar
Don Gagne committed
    property real defaultTextHeight: __textMeasure.contentHeight
    property real defaultTextWidth:  __textMeasure.contentWidth
Don Gagne's avatar
Don Gagne committed

    /// The width of the dialog panel in characters
    property int __dialogCharWidth: 75

    /// The title for the dialog panel
    property string __dialogTitle

Don Gagne's avatar
Don Gagne committed
    property string __messageDialogText

Don Gagne's avatar
Don Gagne committed
    property Component __dialogComponent

Don Gagne's avatar
Don Gagne committed
    function __signalCompleted() {
        // When we use this control inside a QGCQmlWidgetHolder Component.onCompleted is signalled
        // before the width and height are adjusted. So we need to wait for width and heigth to be
        // set before we signal our own completed signal.
        if (!completedSignalled && width != 0 && height != 0) {
            completedSignalled = true
Don Gagne's avatar
Don Gagne committed
            completed()
        }
    }

    Component.onCompleted:  __signalCompleted()
    onWidthChanged:         __signalCompleted()
    onHeightChanged:        __signalCompleted()
Don Gagne's avatar
Don Gagne committed

    Connections {
        target: __dialogComponentLoader.item

Don Gagne's avatar
Don Gagne committed
        onHideDialog: __rootItem.hideDialog()
Don Gagne's avatar
Don Gagne committed
    }

    Item {
        id:             __dialogOverlay
        visible:        false
        anchors.fill:   parent
        z:              5000

Don Gagne's avatar
Don Gagne committed
        readonly property int __animationDuration: 200

        ParallelAnimation {
            id: __animateShowDialog


            NumberAnimation {
                target:     __transparentSection
                properties: "opacity"
                from:       0.0
                to:         0.8
                duration:   __dialogOverlay.__animationDuration
            }

            NumberAnimation {
                target:     __transparentSection
                properties: "width"
                from:       __dialogOverlay.width
                to:         __dialogOverlay.width - __dialogPanel.width
                duration:   __dialogOverlay.__animationDuration
            }
        }

        ParallelAnimation {
            id: __animateHideDialog

            NumberAnimation {
                target:     __transparentSection
                properties: "opacity"
                from:       0.8
                to:         0.0
                duration:   __dialogOverlay.__animationDuration
            }

            NumberAnimation {
                target:     __transparentSection
                properties: "width"
                from:       __dialogOverlay.width - __dialogPanel.width
                to:         __dialogOverlay.width
                duration:   __dialogOverlay.__animationDuration
            }

            onRunningChanged: {
                if (!running) {
                    __dialogComponent = null
                    __dialogOverlay.visible = false
                }
            }
        }

Don Gagne's avatar
Don Gagne committed
        // This covers the parent with an transparent section
        Rectangle {
Don Gagne's avatar
Don Gagne committed
            id:             __transparentSection
            height:         ScreenTools.availableHeight ? ScreenTools.availableHeight : parent.height
Don Gagne's avatar
Don Gagne committed
            anchors.bottom: parent.bottom
            anchors.left:   parent.left
Don Gagne's avatar
Don Gagne committed
            anchors.right:  __dialogPanel.left
Don Gagne's avatar
Don Gagne committed
            opacity:        0.0
Don Gagne's avatar
Don Gagne committed
            color:          __qgcPal.window
        }

        // This is the main dialog panel which is anchored to the right edge
        Rectangle {
            id:                 __dialogPanel
            width:              __dialogCharWidth == showDialogFullWidth ? parent.width : defaultTextWidth * __dialogCharWidth
            anchors.topMargin:  topDialogMargin
            height:             ScreenTools.availableHeight ? ScreenTools.availableHeight : parent.height
            anchors.bottom:     parent.bottom
            anchors.right:      parent.right
            color:              __qgcPal.windowShadeDark
Don Gagne's avatar
Don Gagne committed

            Rectangle {
                id:     __header
                width:  parent.width
Don Gagne's avatar
Don Gagne committed
                height: __acceptButton.visible ? __acceptButton.height : __rejectButton.height
Don Gagne's avatar
Don Gagne committed
                color:  __qgcPal.windowShade

                function __hidePanel() {
                    __fullPanel.visible = false
                }

                QGCLabel {
Don Gagne's avatar
Don Gagne committed
                    x:                  defaultTextWidth
Don Gagne's avatar
Don Gagne committed
                    height:             parent.height
                    verticalAlignment:	Text.AlignVCenter
                    text:               __dialogTitle
                }

                QGCButton {
                    id:             __rejectButton
Don Gagne's avatar
Don Gagne committed
                    anchors.right:  __acceptButton.visible ?  __acceptButton.left : parent.right
Don Gagne's avatar
Don Gagne committed
                    anchors.bottom: parent.bottom

                    onClicked: {
                        enabled = false // prevent multiple clicks
                        __dialogComponentLoader.item.reject()
                    }
Don Gagne's avatar
Don Gagne committed
                }

                QGCButton {
                    id:             __acceptButton
                    anchors.right:  parent.right
                    primary:        true

                        enabled = false // prevent multiple clicks
                       __dialogComponentLoader.item.accept()
                    }
Don Gagne's avatar
Don Gagne committed
                }
            }

            Item {
                id:             __spacer
                width:          10
                height:         10
                anchors.top:    __header.bottom
            }

            Loader {
                id:                 __dialogComponentLoader
                anchors.margins:    5
                anchors.left:       parent.left
                anchors.right:      parent.right
                anchors.top:        __spacer.bottom
                anchors.bottom:     parent.bottom
                sourceComponent:    __dialogComponent

                property bool acceptAllowed: __acceptButton.visible
                property bool rejectAllowed: __rejectButton.visible
Don Gagne's avatar
Don Gagne committed
            }
        } // Rectangle - Dialog panel
    } // Item - Dialog overlay
Don Gagne's avatar
Don Gagne committed

    Component {
        id: __messageDialog

        QGCViewMessage {
            message: __messageDialogText
        }
    }