diff --git a/src/controls/AbstractApplicationHeader.qml b/src/controls/AbstractApplicationHeader.qml index c3e024b7..2611b82f 100644 --- a/src/controls/AbstractApplicationHeader.qml +++ b/src/controls/AbstractApplicationHeader.qml @@ -1,67 +1,73 @@ /* * Copyright 2016 Marco Martin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU Library General Public License as * published by the Free Software Foundation; either version 2 or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Library General Public License for more details * * You should have received a copy of the GNU Library General Public * License along with this program; if not, write to the * Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ import QtQuick 2.5 import org.kde.kirigami 2.5 import "private" import "templates" as T /** * An item that can be used as a title for the application. * Scrolling the main page will make it taller or shorter (trough the point of going away) * It's a behavior similar to the typical mobile web browser addressbar * the minimum, preferred and maximum heights of the item can be controlled with * * minimumHeight: default is 0, i.e. hidden * * preferredHeight: default is Units.gridUnit * 1.6 * * maximumHeight: default is Units.gridUnit * 3 * * To achieve a titlebar that stays completely fixed just set the 3 sizes as the same */ T.AbstractApplicationHeader { id: root Theme.inherit: false Theme.textColor: root.parent.Theme.highlightedTextColor Theme.backgroundColor: root.parent.Theme.highlightColor Theme.highlightColor: root.parent.Theme.backgroundColor background: Rectangle { color: Theme.backgroundColor EdgeShadow { id: shadow visible: root.separatorVisible anchors { right: parent.right left: parent.left top: parent.bottom } edge: Qt.TopEdge opacity: (!root.page.header || root.page.header.toString().indexOf("ToolBar") === -1) Behavior on opacity { OpacityAnimator { duration: Units.longDuration easing.type: Easing.InOutQuad } } } + Behavior on opacity { + OpacityAnimator { + duration: Units.longDuration + easing.type: Easing.InOutQuad + } + } } } diff --git a/src/controls/Page.qml b/src/controls/Page.qml index 243f3c5f..e2782792 100644 --- a/src/controls/Page.qml +++ b/src/controls/Page.qml @@ -1,347 +1,347 @@ /* * Copyright 2015 Marco Martin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU Library General Public License as * published by the Free Software Foundation; either version 2, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Library General Public License for more details * * You should have received a copy of the GNU Library General Public * License along with this program; if not, write to the * Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ import QtQuick 2.1 import QtQuick.Layouts 1.2 import org.kde.kirigami 2.4 as Kirigami import "private" import QtQuick.Templates 2.0 as T2 /** * Page is a container for all the app pages: everything pushed to the * ApplicationWindow stackView should be a Page instabnce (or a subclass, * such as ScrollablePage) * @see ScrollablePage * @inherit QtQuick.Templates.Page */ T2.Page { id: root /** * leftPadding: int * default contents padding at left */ leftPadding: Kirigami.Units.gridUnit /** * topPadding: int * default contents padding at top */ topPadding: Kirigami.Units.gridUnit /** * rightPadding: int * default contents padding at right */ rightPadding: Kirigami.Units.gridUnit /** * bottomPadding: int * default contents padding at bottom */ bottomPadding: actionButtons.item ? actionButtons.height : Kirigami.Units.gridUnit /** * flickable: Flickable * if the central element of the page is a Flickable * (ListView and Gridview as well) you can set it there. * normally, you wouldn't need to do that, but just use the * ScrollablePage element instead * @see ScrollablePage * Use this if your flickable has some non standard properties, such as not covering the whole Page */ property Flickable flickable /** * actions.contextualActions: list * Defines the contextual actions for the page: * an easy way to assign actions in the right sliding panel * * Example usage: * @code * import org.kde.kirigami 2.4 as Kirigami * * Kirigami.ApplicationWindow { * [...] * contextDrawer: Kirigami.ContextDrawer { * id: contextDrawer * } * [...] * } * @endcode * * @code * import org.kde.kirigami 2.4 as Kirigami * * Kirigami.Page { * [...] * actions.contextualActions: [ * Kirigami.Action { * iconName: "edit" * text: "Action text" * onTriggered: { * // do stuff * } * }, * Kirigami.Action { * iconName: "edit" * text: "Action text" * onTriggered: { * // do stuff * } * } * ] * [...] * } * @endcode */ //TODO: remove property alias contextualActions: actionsGroup.contextualActions /** * actions.main: Action * An optional single action for the action button. * it can be a Kirigami.Action or a QAction * * Example usage: * * @code * import org.kde.kirigami 2.4 as Kirigami * Kirigami.Page { * actions.main: Kirigami.Action { * iconName: "edit" * onTriggered: { * // do stuff * } * } * } * @endcode */ //TODO: remove property alias mainAction: actionsGroup.main /** * actions.left: Action * An optional extra action at the left of the main action button. * it can be a Kirigami.Action or a QAction * * Example usage: * * @code * import org.kde.kirigami 2.4 as Kirigami * Kirigami.Page { * actions.left: Kirigami.Action { * iconName: "edit" * onTriggered: { * // do stuff * } * } * } * @endcode */ //TODO: remove property alias leftAction: actionsGroup.left /** * actions.right: Action * An optional extra action at the right of the main action button. * it can be a Kirigami.Action or a QAction * * Example usage: * * @code * import org.kde.kirigami 2.4 as Kirigami * Kirigami.Page { * actions.right: Kirigami.Action { * iconName: "edit" * onTriggered: { * // do stuff * } * } * } * @endcode */ //TODO: remove property alias rightAction: actionsGroup.right /** * Actions properties are grouped. * * @code * import org.kde.kirigami 2.4 as Kirigami * Kirigami.Page { * actions { * main: Kirigami.Action {...} * left: Kirigami.Action {...} * right: Kirigami.Action {...} * contextualActions: [ * Kirigami.Action {...}, * Kirigami.Action {...} * ] * } * } * @endcode */ readonly property alias actions: actionsGroup /** * isCurrentPage: bool * * Specifies if it's the currently selected page in the window's pages row. * * @since 2.1 */ readonly property bool isCurrentPage: typeof applicationWindow === "undefined" || !globalToolBar.row ? true : (globalToolBar.row.layers.depth > 1 ? globalToolBar.row.layers.currentItem == root : globalToolBar.row.currentItem == root) PageActionPropertyGroup { id: actionsGroup } /** * overlay: Item * an item which stays on top of every other item in the page, * if you want to make sure some elements are completely in a * layer on top of the whole content, parent items to this one. * It's a "local" version of ApplicationWindow's overlay * @since 2.5 */ readonly property alias overlay: overlayItem /** * emitted When the application requests a Back action * For instance a global "back" shortcut or the Android * Back button has been pressed. * The page can manage the back event by itself, * and if it set event.accepted = true, it will stop the main * application to manage the back event. */ signal backRequested(var event); // Look for sheets and cose them //FIXME: port Sheets to Popup? onBackRequested: { for(var i in root.resources) { var item = root.resources[i]; if (item.hasOwnProperty("close") && item.hasOwnProperty("sheetOpen") && item.sheetOpen) { item.close() event.accepted = true; return; } } } //NOTE: This exists just because control instances require it contentItem: Item { } //FIXME: on material the shadow would bleed over clip: root.header != null; Component.onCompleted: { parentChanged(root.parent); } onParentChanged: { if (!parent) { return; } globalToolBar.stack = null; globalToolBar.row = null; if (root.parent.hasOwnProperty("__pageRow")) { globalToolBar.row = root.parent.__pageRow; } if (root.T2.StackView.view) { globalToolBar.stack = root.T2.StackView.view; globalToolBar.row = root.T2.StackView.view.parent; } if (globalToolBar.row) { globalToolBar.row.globalToolBar.actualStyleChanged.connect(globalToolBar.syncSource); globalToolBar.syncSource(); } } Item { id: overlayItem parent: root z: 9997 anchors.fill: parent } //global top toolbar if we are in a PageRow (in the row or as a layer) Loader { id: globalToolBar z: 9999 parent: root.clip ? root.parent : root height: item ? item.implicitHeight : 0 anchors { left: parent ? root.left : undefined right: parent ? root.right : undefined bottom: parent ? root.top : undefined } property Kirigami.PageRow row property T2.StackView stack - active: row && (row.globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.ToolBar || globalToolBar.row.globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.Titles) + active: row && (row.layers.depth > 1 || row.globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.ToolBar || globalToolBar.row.globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.Titles) function syncSource() { if (row && active) { setSource(Qt.resolvedUrl(row.globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.ToolBar ? "private/globaltoolbar/ToolBarPageHeader.qml" : "private/globaltoolbar/TitlesPageHeader.qml"), //TODO: find container reliably, remove assumption {"pageRow": Qt.binding(function() {return row}), "page": root, "current": Qt.binding(function() {return stack || !root.parent ? true : row.currentIndex == root.parent.level})}); } } Separator { z: 999 anchors.verticalCenter: globalToolBar.verticalCenter height: globalToolBar.height * 0.6 visible: globalToolBar.row && root.parent && globalToolBar.row.contentItem.contentX < root.parent.x - globalToolBar.row.globalToolBar.leftReservedSpace Kirigami.Theme.textColor: globalToolBar.item ? globalToolBar.item.Kirigami.Theme.textColor : undefined } } //bottom action buttons Loader { id: actionButtons z: 9999 parent: root anchors { left: parent.left right: parent.right bottom: parent.bottom } //It should be T2.Page, Qt 5.7 doesn't like it property Item page: root height: item ? item.height : 0 active: typeof applicationWindow !== "undefined" && (!globalToolBar.row || globalToolBar.row.globalToolBar.actualStyle != Kirigami.ApplicationHeaderStyle.ToolBar) && //Legacy (typeof applicationWindow === "undefined" || (!applicationWindow().header || applicationWindow().header.toString().indexOf("ToolBarApplicationHeader") === -1) && (!applicationWindow().footer || applicationWindow().footer.toString().indexOf("ToolBarApplicationHeader") === -1)) source: Qt.resolvedUrl("./private/ActionButton.qml") } Layout.fillWidth: true } diff --git a/src/controls/private/globaltoolbar/PageRowGlobalToolBarUI.qml b/src/controls/private/globaltoolbar/PageRowGlobalToolBarUI.qml index 32d890c5..7f85e2eb 100644 --- a/src/controls/private/globaltoolbar/PageRowGlobalToolBarUI.qml +++ b/src/controls/private/globaltoolbar/PageRowGlobalToolBarUI.qml @@ -1,94 +1,102 @@ /* * Copyright 2018 Marco Martin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU Library General Public License as * published by the Free Software Foundation; either version 2 or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Library General Public License for more details * * You should have received a copy of the GNU Library General Public * License along with this program; if not, write to the * Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ -import QtQuick 2.1 +import QtQuick 2.6 import QtQuick.Layouts 1.2 import org.kde.kirigami 2.4 as Kirigami import "../../templates/private" as TemplatesPrivate Kirigami.AbstractApplicationHeader { id: header readonly property int leftReservedSpace: buttonsLayout.visible && buttonsLayout.visibleChildren.length > 1 ? buttonsLayout.width : 0 readonly property int rightReservedSpace: rightHandleAnchor.visible ? backButton.background.implicitHeight : 0 readonly property alias leftHandleAnchor: leftHandleAnchor readonly property alias rightHandleAnchor: rightHandleAnchor height: visible ? implicitHeight : 0 minimumHeight: globalToolBar.minimumHeight preferredHeight: globalToolBar.preferredHeight maximumHeight: globalToolBar.maximumHeight separatorVisible: globalToolBar.separatorVisible RowLayout { anchors.fill: parent spacing: 0 RowLayout { id: buttonsLayout Layout.fillHeight: true visible: globalToolBar.showNavigationButtons && globalToolBar.actualStyle != Kirigami.ApplicationHeaderStyle.None Item { id: leftHandleAnchor visible: typeof applicationWindow() !== "undefined" && applicationWindow().globalDrawer && applicationWindow().globalDrawer.handleVisible && (applicationWindow().globalDrawer.handle.handleAnchor == (Qt.application.layoutDirection == Qt.LeftToRight ? leftHandleAnchor : rightHandleAnchor)) Layout.fillHeight: true Layout.preferredWidth: height } TemplatesPrivate.BackButton { id: backButton Layout.leftMargin: leftHandleAnchor.visible ? 0 : Kirigami.Units.smallSpacing Layout.fillHeight: true Layout.preferredWidth: height } TemplatesPrivate.ForwardButton { Layout.fillHeight: true Layout.preferredWidth: height } Kirigami.Separator { Layout.preferredHeight: parent.parent.height * 0.6 //FIXME: hacky opacity: buttonsLayout.visibleChildren.length > 1 } } Loader { id: breadcrumbLoader Layout.fillWidth: true Layout.fillHeight: true Layout.minimumHeight: -1 Layout.preferredHeight: -1 property Kirigami.PageRow pageRow: root + opacity: pageRow.layers.depth < 2 active: globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.TabBar || globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.Breadcrumb //TODO: different implementation? source: globalToolBar.actualStyle == Kirigami.ApplicationHeaderStyle.TabBar ? Qt.resolvedUrl("TabBarControl.qml") : Qt.resolvedUrl("BreadcrumbControl.qml") + + Behavior on opacity { + OpacityAnimator { + duration: Kirigami.Units.longDuration + easing.type: Easing.InOutQuad + } + } } Item { id: rightHandleAnchor visible: typeof applicationWindow() !== "undefined" && applicationWindow().contextDrawer && applicationWindow().contextDrawer.handleVisible && applicationWindow().contextDrawer.handle.handleAnchor == Qt.application.layoutDirection == (Qt.LeftToRight ? rightHandleAnchor : leftHandleAnchor) Layout.fillHeight: true Layout.preferredWidth: height } } - background.visible: breadcrumbLoader.active + background.opacity: pageRow.layers.depth < 2 && breadcrumbLoader.active } - +