Warning, /frameworks/kirigami/src/controls/Page.qml is written in an unsupported language. File is not indexed.
0001 /*
0002 * SPDX-FileCopyrightText: 2015 Marco Martin <mart@kde.org>
0003 *
0004 * SPDX-License-Identifier: LGPL-2.0-or-later
0005 */
0006
0007 import QtQuick
0008 import QtQuick.Layouts
0009 import QtQuick.Templates as T
0010 import QtQuick.Controls as QQC2
0011 import org.kde.kirigami as Kirigami
0012 import "private" as P
0013
0014 /**
0015 * Page is a container for all the app pages: everything pushed to the
0016 * ApplicationWindow's pageStack should be a Page.
0017 *
0018 * @see ScrollablePage
0019 * For content that should be scrollable, such as ListViews, use ScrollablePage instead.
0020 * @inherit QtQuick.Controls.Page
0021 */
0022 QQC2.Page {
0023 id: root
0024
0025 //BEGIN properties
0026 padding: Kirigami.Units.gridUnit
0027
0028 /**
0029 * @brief If the central element of the page is a Flickable
0030 * (ListView and Gridview as well) you can set it there.
0031 *
0032 * Normally, you wouldn't need to do that, but just use the
0033 * ScrollablePage element instead.
0034 *
0035 * Use this if your flickable has some non standard properties, such as not covering the whole Page.
0036 *
0037 * @see ScrollablePage
0038 */
0039 property Flickable flickable
0040
0041 /**
0042 * @brief This property holds the actions for the page.
0043 *
0044 * These actions will be displayed in the toolbar on the desktop and inside
0045 * the ContextDrawer on mobile.
0046 *
0047 * @code
0048 * import org.kde.kirigami 2 as Kirigami
0049 *
0050 * Kirigami.Page {
0051 * actions: [
0052 * Kirigami.Action {...},
0053 * Kirigami.Action {...}
0054 * }
0055 * }
0056 * @endcode
0057 */
0058 property list<T.Action> actions
0059
0060 /**
0061 * @brief This property tells us if it is the currently active page.
0062 *
0063 * Specifies if it's the currently selected page in the window's pages row, or if layers
0064 * are used whether this is the topmost item on the layers stack. If the page is
0065 * not attached to either a column view or a stack view, expect this to be true.
0066 *
0067 * @since 2.1
0068 */
0069 //TODO KF6: remove this or at least all the assumptions about the internal tree structure of items
0070 // Kirigami.ColumnView.view.parent.parent is the StackView in which the ColumnView is, the condition means "is the ColumnView the current layer of the pagerow"
0071 readonly property bool isCurrentPage: Kirigami.ColumnView.view
0072 ? (Kirigami.ColumnView.index === Kirigami.ColumnView.view.currentIndex && Kirigami.ColumnView.view.parent.parent.currentItem === Kirigami.ColumnView.view.parent)
0073 : (parent && parent instanceof QQC2.StackView
0074 ? parent.currentItem === root
0075 : true)
0076
0077 /**
0078 * An item which stays on top of every other item in the page,
0079 * if you want to make sure some elements are completely in a
0080 * layer on top of the whole content, parent items to this one.
0081 * It's a "local" version of ApplicationWindow's overlay
0082 *
0083 * @property Item overlay
0084 * @since 2.5
0085 */
0086 readonly property alias overlay: overlayItem
0087
0088 /**
0089 * @brief This holds the icon that represents this page.
0090 * @property var icon
0091 */
0092 property P.ActionIconGroup icon: P.ActionIconGroup {}
0093
0094 /**
0095 * @brief Progress of a task this page is doing.
0096 *
0097 * Set to undefined to indicate that there are no ongoing tasks.
0098 *
0099 * default: ``undefined``
0100 *
0101 * @property real progress
0102 */
0103 property var progress: undefined
0104
0105 /**
0106 * @brief The delegate which will be used to draw the page title.
0107 *
0108 * It can be customized to put any kind of Item in there.
0109 *
0110 * @since 2.7
0111 */
0112 property Component titleDelegate: Component {
0113 id: defaultTitleDelegate
0114 P.DefaultPageTitleDelegate {
0115 text: root.title
0116 }
0117 }
0118
0119 /**
0120 * The item used as global toolbar for the page
0121 * present only if we are in a PageRow as a page or as a layer,
0122 * and the style is either Titles or ToolBar.
0123 *
0124 * @since 2.5
0125 */
0126 readonly property Item globalToolBarItem: globalToolBar.item
0127
0128 /**
0129 * The style for the automatically generated global toolbar: by default the Page toolbar is the one set globally in the PageRow in its globalToolBar.style property.
0130 * A single page can override the application toolbar style for itself.
0131 * It is discouraged to use this, except very specific exceptions, like a chat
0132 * application which can't have controls on the bottom except the text field.
0133 * If the Page is not in a PageRow, by default the toolbar will be invisible,
0134 * so has to be explicitly set to Kirigami.ApplicationHeaderStyle.ToolBar if
0135 * desired to be used in that case.
0136 */
0137 property int globalToolBarStyle: {
0138 if (globalToolBar.row && !globalToolBar.stack) {
0139 return globalToolBar.row.globalToolBar.actualStyle;
0140 } else if (globalToolBar.stack) {
0141 return Kirigami.Settings.isMobile ? Kirigami.ApplicationHeaderStyle.Titles : Kirigami.ApplicationHeaderStyle.ToolBar;
0142 } else {
0143 return Kirigami.ApplicationHeaderStyle.None;
0144 }
0145 }
0146 //END properties
0147
0148 //BEGIN signal and signal handlers
0149 /**
0150 * @brief Emitted when the application requests a Back action.
0151 *
0152 * For instance a global "back" shortcut or the Android
0153 * Back button has been pressed.
0154 * The page can manage the back event by itself,
0155 * and if it set event.accepted = true, it will stop the main
0156 * application to manage the back event.
0157 */
0158 signal backRequested(var event);
0159
0160 background: Rectangle {
0161 color: Kirigami.Theme.backgroundColor
0162 }
0163
0164 // FIXME: on material the shadow would bleed over
0165 clip: root.header !== null;
0166
0167 Component.onCompleted: {
0168 headerChanged();
0169 parentChanged(root.parent);
0170 globalToolBar.syncSource();
0171 bottomToolBar.pageComplete = true
0172 }
0173
0174 onParentChanged: {
0175 if (!parent) {
0176 return;
0177 }
0178 globalToolBar.stack = null;
0179 globalToolBar.row = null;
0180
0181 if (root.Kirigami.ColumnView.view) {
0182 globalToolBar.row = root.Kirigami.ColumnView.view.__pageRow;
0183 }
0184 if (root.T.StackView.view) {
0185 globalToolBar.stack = root.T.StackView.view;
0186 globalToolBar.row = root.T.StackView.view.parent instanceof Kirigami.PageRow ? root.T.StackView.view.parent : null;
0187 }
0188 if (globalToolBar.row) {
0189 root.globalToolBarStyleChanged.connect(globalToolBar.syncSource);
0190 globalToolBar.syncSource();
0191 }
0192 }
0193 //END signals and signal handlers
0194
0195 // in data in order for them to not be considered for contentItem, contentChildren, contentData
0196 data: [
0197 Item {
0198 id: overlayItem
0199 parent: root
0200 z: 9997
0201 anchors {
0202 fill: parent
0203 topMargin: globalToolBar.height
0204 }
0205 }
0206 ]
0207 // global top toolbar if we are in a PageRow (in the row or as a layer)
0208 Kirigami.ColumnView.globalHeader: Loader {
0209 id: globalToolBar
0210 z: 9999
0211 height: item ? item.implicitHeight : 0
0212
0213 width: root.width
0214 property Kirigami.PageRow row
0215 property T.StackView stack
0216
0217 // don't load async so that on slower devices we don't have the page content height changing while loading in
0218 // otherwise, it looks unpolished and jumpy
0219 asynchronous: false
0220
0221 visible: active
0222 active: (root.titleDelegate !== defaultTitleDelegate || root.globalToolBarStyle === Kirigami.ApplicationHeaderStyle.ToolBar || root.globalToolBarStyle === Kirigami.ApplicationHeaderStyle.Titles)
0223 onActiveChanged: {
0224 if (active) {
0225 syncSource();
0226 }
0227 }
0228
0229 function syncSource() {
0230 if (root.globalToolBarStyle !== Kirigami.ApplicationHeaderStyle.ToolBar &&
0231 root.globalToolBarStyle !== Kirigami.ApplicationHeaderStyle.Titles &&
0232 root.titleDelegate !== defaultTitleDelegate) {
0233 sourceComponent = root.titleDelegate;
0234 } else if (active) {
0235 const url = root.globalToolBarStyle === Kirigami.ApplicationHeaderStyle.ToolBar
0236 ? "private/globaltoolbar/ToolBarPageHeader.qml"
0237 : "private/globaltoolbar/TitlesPageHeader.qml";
0238 // TODO: find container reliably, remove assumption
0239 setSource(Qt.resolvedUrl(url), {
0240 pageRow: Qt.binding(() => row),
0241 page: root,
0242 current: Qt.binding(() => {
0243 if (!row && !stack) {
0244 return true;
0245 } else if (stack) {
0246 return stack;
0247 } else {
0248 return row.currentIndex === root.Kirigami.ColumnView.level;
0249 }
0250 }),
0251 });
0252 }
0253 }
0254 }
0255 // bottom action buttons
0256 Kirigami.ColumnView.globalFooter: Loader {
0257 id: bottomToolBar
0258
0259 property T.Page page: root
0260 property bool pageComplete: false
0261
0262 visible: active
0263
0264 active: {
0265 // Important! Do not do anything until the page has been
0266 // completed, so we are sure what the globalToolBarStyle is,
0267 // otherwise we risk creating the content and then discarding it.
0268 if (!pageComplete) {
0269 return false;
0270 }
0271
0272 if ((globalToolBar.row && globalToolBar.row.globalToolBar.actualStyle === Kirigami.ApplicationHeaderStyle.ToolBar)
0273 || root.globalToolBarStyle === Kirigami.ApplicationHeaderStyle.ToolBar
0274 || root.globalToolBarStyle === Kirigami.ApplicationHeaderStyle.None) {
0275 return false;
0276 }
0277
0278 if (root.actions.length === 0) {
0279 return false;
0280 }
0281
0282 // Legacy
0283 if (typeof applicationWindow === "undefined") {
0284 return true;
0285 }
0286
0287 const drawer = applicationWindow() ? applicationWindow()['contextDrawer'] : undefined;
0288 if (drawer !== undefined && drawer.enabled && drawer.handleVisible) {
0289 return false;
0290 }
0291
0292 return true;
0293 }
0294
0295 source: Qt.resolvedUrl("./private/globaltoolbar/ToolBarPageFooter.qml")
0296 }
0297
0298 Layout.fillWidth: true
0299 }