diff options
Diffstat (limited to 'src/Authoring/Qt3DStudio/Palettes/Action/ActionView.qml')
-rw-r--r-- | src/Authoring/Qt3DStudio/Palettes/Action/ActionView.qml | 468 |
1 files changed, 468 insertions, 0 deletions
diff --git a/src/Authoring/Qt3DStudio/Palettes/Action/ActionView.qml b/src/Authoring/Qt3DStudio/Palettes/Action/ActionView.qml new file mode 100644 index 00000000..a5b905b3 --- /dev/null +++ b/src/Authoring/Qt3DStudio/Palettes/Action/ActionView.qml @@ -0,0 +1,468 @@ +/**************************************************************************** +** +** Copyright (C) 2017 The Qt Company Ltd. +** Contact: https://www.qt.io/licensing/ +** +** This file is part of Qt 3D Studio. +** +** $QT_BEGIN_LICENSE:GPL-EXCEPT$ +** Commercial License Usage +** Licensees holding valid commercial Qt licenses may use this file in +** accordance with the commercial license agreement provided with the +** Software or, alternatively, in accordance with the terms contained in +** a written agreement between you and The Qt Company. For licensing terms +** and conditions see https://www.qt.io/terms-conditions. For further +** information use the contact form at https://www.qt.io/contact-us. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU +** General Public License version 3 as published by the Free Software +** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT +** included in the packaging of this file. Please review the following +** information to ensure the GNU General Public License requirements will +** be met: https://www.gnu.org/licenses/gpl-3.0.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import QtQuick 2.8 +import QtQuick.Controls 2.2 +import QtQuick.Layouts 1.3 +import Qt3DStudio 1.0 +import "../controls" + +Rectangle { + id: root + + color: _backgroundColor + + Item { + id: focusEater + objectName: "focusEater" + // Used to eat keyboard focus when user clicks outside any property control + } + + Flickable { + id: actionFlickable + ScrollBar.vertical: ScrollBar { + id: scrollBar + visible: size < 1.0 + } + + MouseArea { + anchors.fill: parent + z: -10 + onPressed: { + mouse.accepted = false + focusEater.forceActiveFocus(); + } + } + + anchors.fill: parent + contentHeight: contentColumn.height + + property bool scrollToBottom: false + + onContentHeightChanged: { + if (scrollToBottom) { + scrollToBottom = false; + if (contentHeight > height) + contentY = contentHeight - height; + } + } + + Column { + id: contentColumn + width: parent.width + spacing: 4 + + RowLayout { + height: _controlBaseHeight + 8 + anchors.left: parent.left + anchors.right: parent.right + anchors.margins: 4 + anchors.rightMargin: 12 + + Image { + id: headerImage + source: _parentView.itemIcon !== "" ? _resDir + _parentView.itemIcon : "" + } + + StyledLabel { + Layout.fillWidth: true + text: _parentView.itemText + color: _parentView.itemColor + } + + StyledToolButton { + enabled: actionsList.currentIndex !== -1 + enabledImage: "Action-Trash-Normal.png" + disabledImage: "Action-Trash-Disabled.png" + toolTipText: qsTr("Delete (Del)") + + onClicked: _parentView.deleteAction(actionsList.currentIndex) + } + + StyledToolButton { + enabledImage: "add.png" + disabledImage: "add-disabled.png" + toolTipText: qsTr("New Action (") + _shiftKey + "A)" + enabled: _parentView.hasItem + + onClicked: _parentView.addAction() + } + } + ListView { + id: actionsList + width: parent.width + height: count == 0 ? _controlBaseHeight : count * _controlBaseHeight + clip: true + + Connections { + target: _parentView + // Clear the action selection on item selection change + onItemChanged: actionsList.currentIndex = -1 + } + + MouseArea { + anchors.fill: parent + enabled: parent.count == 0 + + acceptedButtons: Qt.RightButton + + onClicked: { + if (mouse.button == Qt.RightButton) { + var updateMousePosition = mapToItem(actionsList, mouse.x, mouse.y) + _parentView.showContextMenu( + updateMousePosition.x, updateMousePosition.y); + } + } + } + boundsBehavior: Flickable.StopAtBounds + model: _parentView.actionsModel + + delegate: Rectangle { + id: delegateItem + objectName: "actionListDelegate" + + width: actionsList.width + height: _controlBaseHeight + color: model.index === actionsList.currentIndex ? _selectionColor + : "transparent" + + Row { + x: 10 + y: 5 + height: parent.height + width: parent.width - x + spacing: 4 + + Image { + id: visibilityIcon + + source: model.visible ? _resDir + "Toggle-HideShow.png" + : _resDir + "Toggle-HideShow-disabled.png" + + MouseArea { + anchors.fill: parent + onClicked: model.visible = !model.visible + } + } + + StyledLabel { + text: model.description + } + } + + MouseArea { + anchors.fill: parent + + acceptedButtons: Qt.LeftButton | Qt.RightButton + + onPressed: { + actionsList.forceActiveFocus(); + } + + onClicked: { + actionFlickable.scrollToBottom = false; + actionsList.currentIndex = model.index; + _parentView.setCurrentActionIndex(model.index); + if (mouse.button == Qt.LeftButton && mouse.x < visibilityIcon.width + 10) + model.visible = !model.visible; + + if (mouse.button == Qt.RightButton) { + var updateMousePosition = mapToItem(actionsList, mouse.x, mouse.y) + _parentView.showContextMenu(updateMousePosition.x, updateMousePosition.y); + } + } + onDoubleClicked: { + actionFlickable.scrollToBottom = false; + if (mouse.button == Qt.LeftButton && mouse.x > visibilityIcon.width + 10) { + // Scroll down to bottom to show properties on double click + if (actionFlickable.contentHeight > actionFlickable.height) { + actionFlickable.contentY = (actionFlickable.contentHeight + - actionFlickable.height) + } + // Since loading new property fields takes a moment, we want + // to keep the view scrolled to bottom + // when the content height changes the next time. + actionFlickable.scrollToBottom = true; + } + } + } + } + + onCountChanged: { + if (currentIndex >= count) + currentIndex = count - 1; + } + + onCurrentIndexChanged: _parentView.setCurrentActionIndex(currentIndex); + } + + StyledMenuSeparator { + leftPadding: 12 + rightPadding: 12 + } + + Column { + anchors.left: parent.left + anchors.right: parent.right + height: childrenRect.height + visible: actionsList.currentIndex !== -1 + spacing: 4 + + RowLayout { + x: 12 + StyledLabel { + text: qsTr("Trigger Object") + } + BrowserCombo { + value: _parentView.triggerObjectName + onShowBrowser: activeBrowser = _parentView.showTriggerObjectBrowser( + mapToGlobal(width, 0)); + } + } + + RowLayout { + x: 12 + StyledLabel { + text: qsTr("Event") + } + BrowserCombo { + value: _parentView.eventName + onShowBrowser: activeBrowser = _parentView.showEventBrowser( + mapToGlobal(width, 0)) + } + } + } + + StyledMenuSeparator { + visible: actionsList.currentIndex !== -1 + leftPadding: 12 + rightPadding: 12 + } + + Column { + visible: actionsList.currentIndex !== -1 + width: parent.width + height: childrenRect.height + spacing: 4 + + RowLayout { + x: 12 + StyledLabel { + text: qsTr("Target Object") + } + + BrowserCombo { + value: _parentView.targetObjectName + onShowBrowser: activeBrowser = _parentView.showTargetObjectBrowser( + mapToGlobal(width, 0)) + } + } + + RowLayout { + x: 12 + StyledLabel { + text: qsTr("Handler") + } + + BrowserCombo { + value: _parentView.handlerName + onShowBrowser: activeBrowser = _parentView.showHandlerBrowser( + mapToGlobal(width, 0)) + } + } + + Component { + id: genericHandlerComponent + + HandlerGenericText { + label: parent && parent.argument.name ? parent.argument.name : "" + value: parent && parent.argument.value ? parent.argument.value : "" + + onEditingFinished: { + if (parent) + _parentView.setArgumentValue(parent.argument.handle, value) + } + } + } + + Component { + id: floatHandlerComponent + + HandlerGenericText { + label: parent && parent.argument.name ? parent.argument.name : "" + value: parent && parent.argument.value ? parent.argument.value : 0.0 + validator: DoubleValidator { + decimals: 3 + notation: DoubleValidator.StandardNotation + } + + onEditingFinished: { + if (parent) + _parentView.setArgumentValue(parent.argument.handle, value) + } + } + } + + Component { + id: signalHandlerComponent + + HandlerGenericText { + label: parent && parent.argument.name ? parent.argument.name : "" + value: parent && parent.argument.value ? parent.argument.value : "" + + onEditingFinished: { + if (parent) + _parentView.setArgumentValue(parent.argument.handle, value); + } + } + } + + Component { + id: eventHandlerComponent + + HandlerFireEvent { + label: parent && parent.argument.name ? parent.argument.name : "" + value: _parentView.firedEvent === "" ? qsTr("[Unknown Event]") + : _parentView.firedEvent + + onShowBrowser: { + if (parent && parent.argument.handle) { + activeBrowser = _parentView.showEventBrowserForArgument( + parent.argument.handle, mapToGlobal(width, 0)) + } + } + } + } + + Component { + id: slideHandlerComponent + + HandlerGoToSlide { + slideModel: _parentView.slideNames() + defaultSlideIndex: parent && parent.argument.value ? _parentView.slideNameToIndex(parent.argument.value) + : 0 + + onActivated: { + if (parent && parent.argument.handle && currentSlide) + _parentView.setArgumentValue(parent.argument.handle, currentSlide) + } + } + } + + Component { + id: checkboxHandlerComponent + + HandlerGenericCheckbox { + label: parent && parent.argument.name ? parent.argument.name : "" + checked: parent && parent.argument.value ? parent.argument.value : false + + onClicked: { + if (parent && parent.argument.handle) + _parentView.setArgumentValue(parent.argument.handle, !checked) + } + } + } + + Component { + id: propertyHandlerComponent + + HandlerProperty { + propertyModel: _parentView.propertyModel + defaultPropertyIndex: propertyModel ? propertyModel.defaultPropertyIndex : 0 + + onPropertySelected: { + if (parent && parent.argument.handle) + _parentView.setCurrentPropertyIndex(parent.argument.handle, index); + } + } + } + + Repeater { + model: _parentView.handlerArguments.length + + Loader { + x: 12 + + readonly property var argument:_parentView.handlerArguments[model.index] + + onLoaded: { + // HandlerProperty does its own tab order handling + if (argument.type !== HandlerArgumentType.Property) { + // Dynamic actions use group 0. + // We assume there is always just one tabbable argument per action, + // and the rest are dependent types. + _tabOrderHandler.clear(); + if (item.tabItem1 !== undefined) { + _tabOrderHandler.addItem(0, item.tabItem1) + if (item.tabItem2 !== undefined) { + _tabOrderHandler.addItem(0, item.tabItem2) + if (item.tabItem3 !== undefined) + _tabOrderHandler.addItem(0, item.tabItem3) + } + } + } + } + + sourceComponent: { + const handlerType = argument.type; + switch (handlerType) { + case HandlerArgumentType.None: + switch (argument.completeType) { + case CompleteMetaDataType.Boolean: + return checkboxHandlerComponent; + case CompleteMetaDataType.Float: + return floatHandlerComponent; + default: + return genericHandlerComponent; + } + case HandlerArgumentType.Event: + return eventHandlerComponent; + case HandlerArgumentType.Property: + return propertyHandlerComponent; + case HandlerArgumentType.Dependent: + return null; // no UI for Dependent type, they are the value for a property + case HandlerArgumentType.Signal: + return signalHandlerComponent; + case HandlerArgumentType.Slide: + return slideHandlerComponent + default: console.warn("KDAB_TODO implement handler for type: ", handlerType) + } + return null; + } + } + } + } + + StyledMenuSeparator { + visible: actionsList.count > 0 && actionsList.currentIndex !== -1 + leftPadding: 12 + rightPadding: 12 + } + } + } +} |