File: ContentContainer.qml

package info (click to toggle)
plasma-mobile 6.3.6-3
  • links: PTS, VCS
  • area: main
  • in suites: trixie
  • size: 18,612 kB
  • sloc: xml: 38,470; cpp: 18,437; javascript: 139; sh: 82; makefile: 5
file content (282 lines) | stat: -rw-r--r-- 10,944 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
// SPDX-FileCopyrightText: 2021-2024 Devin Lin <devin@kde.org>
// SPDX-License-Identifier: LGPL-2.0-or-later

import QtQuick 2.15
import QtQuick.Controls 2.15
import QtQuick.Window 2.2
import QtQuick.Layouts

import org.kde.plasma.components 3.0 as PlasmaComponents
import org.kde.plasma.private.mobileshell as MobileShell
import org.kde.plasma.components 3.0 as PC3
import org.kde.kirigami as Kirigami
import org.kde.plasma.private.mobileshell.quicksettingsplugin as QS

/**
 * Root element that contains all the ActionDrawer's contents, and is anchored to the screen.
 */
Item {
    id: root

    required property var actionDrawer
    required property QS.QuickSettingsModel quickSettingsModel

    readonly property real minimizedQuickSettingsOffset: contentContainerLoader.minimizedQuickSettingsOffset
    readonly property real maximizedQuickSettingsOffset: contentContainerLoader.maximizedQuickSettingsOffset

    Kirigami.Theme.colorSet: Kirigami.Theme.View
    Kirigami.Theme.inherit: false

    readonly property alias brightnessPressedValue: quickSettings.brightnessPressedValue

    function applyMinMax(val) {
        return Math.max(0, Math.min(1, val));
    }

    function startSwipe() {
        actionDrawer.cancelAnimations();
        actionDrawer.dragging = true;
        // Immediately open action drawer if we interact with it and it's already open
        // This allows us to have 2 quick flicks from minimized -> expanded
        if (actionDrawer.visible && !actionDrawer.opened) {
            actionDrawer.opened = true;
        }
    }

    function endSwipe() {
        actionDrawer.dragging = false;
        actionDrawer.updateState();
    }

    function moveSwipe(totalDeltaX, totalDeltaY, deltaX, deltaY) {
        actionDrawer.offset += deltaY;
    }

    // Background color
    Rectangle {
        anchors.fill: parent
        color: Qt.rgba(Kirigami.Theme.backgroundColor.r,
                       Kirigami.Theme.backgroundColor.g,
                       Kirigami.Theme.backgroundColor.b,
                       0.95)
        Behavior on color { ColorAnimation { duration: Kirigami.Units.longDuration; easing.type: Easing.OutQuad } }
        opacity: Math.max(0, Math.min(brightnessPressedValue, actionDrawer.offset / root.minimizedQuickSettingsOffset))
    }

    // The base swipe area.
    // Used to cover the full surface of the drawer to allow dismissing or expanding it.
    MobileShell.SwipeArea {
        id: swipeAreaBase
        mode: MobileShell.SwipeArea.VerticalOnly
        anchors.fill: parent

        onSwipeStarted: root.startSwipe()
        onSwipeEnded: root.endSwipe()
        onSwipeMove: (totalDeltaX, totalDeltaY, deltaX, deltaY) => root.moveSwipe(totalDeltaX, totalDeltaY, deltaX, deltaY)

        onTouchpadScrollStarted: root.startSwipe()
        onTouchpadScrollEnded: root.endSwipe()
        onTouchpadScrollMove: (totalDeltaX, totalDeltaY, deltaX, deltaY) => root.moveSwipe(totalDeltaX, totalDeltaY, deltaX, deltaY)

        // Proxy in the layout that switches between landscape and portrait mode.
        ColumnLayout {
            anchors.fill: parent
            visible: root.actionDrawer.mode != ActionDrawer.Portrait
            LayoutItemProxy { target: contentContainerLoader }
        }

        // Mouse area for dismissing action drawer in portrait mode when background is clicked.
        MouseArea {
            anchors.fill: parent
            visible: root.actionDrawer.mode == ActionDrawer.Portrait

            // dismiss drawer when background is clicked
            onClicked: root.actionDrawer.close();
        }

        // The clear all notification history button.
        Item {
            id: toolButtons
            height: visible ? spacer.height + toolLayout.height + toolLayout.anchors.topMargin + toolLayout.anchors.bottomMargin : 0

            visible: actionDrawer.intendedToBeVisible
            opacity: Math.max(0, Math.min(root.brightnessPressedValue, actionDrawer.offsetResistance / root.minimizedQuickSettingsOffset))

            anchors {
                topMargin: notificationDrawer.height
                leftMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : 10
                rightMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : notificationDrawer.notificationWidget.anchors.rightMargin + Kirigami.Units.gridUnit - notificationDrawer.anchors.leftMargin + 370
                top: parent.top
                left: parent.left
                right: parent.right
            }

            Rectangle {
                id: spacer
                anchors.left: parent.left
                anchors.right: parent.right

                visible: notificationDrawer.listOverflowing
                height: 1
                opacity: 0.25
                color: Kirigami.Theme.textColor
            }

            RowLayout {
                id: toolLayout

                anchors {
                    top: spacer.bottom
                    right: parent.right
                    left: parent.left
                    leftMargin: Kirigami.Units.largeSpacing
                    rightMargin: Kirigami.Units.largeSpacing
                    topMargin: Kirigami.Units.largeSpacing
                    bottomMargin: Kirigami.Units.largeSpacing
                }

                PlasmaComponents.ToolButton {
                    id: clearButton

                    Layout.alignment: Qt.AlignCenter

                    visible: notificationDrawer.hasNotifications

                    font.bold: true
                    font.pointSize: Kirigami.Theme.smallFont.pointSize

                    icon.name: "edit-clear-history"
                    text: i18n("Clear All Notifications")
                    onClicked: notificationDrawer.notificationWidget.clearHistory()
                }
            }
        }
    }

    // notification drawer ui
    // separated from the main drawer ui swipe area to prevent scrolling conflicts
    NotificationDrawer {
        id: notificationDrawer

        swipeArea: swipeAreaPortrait
        actionDrawer: root.actionDrawer
        mediaControlsWidget: root.mediaControlsWidget
        contentContainer: root
        opacity: Math.max(0, Math.min(root.brightnessPressedValue, actionDrawer.offsetResistance / root.minimizedQuickSettingsOffset))

        anchors {
            top: parent.top
            left: parent.left
            right: parent.right
            rightMargin: root.actionDrawer.mode == ActionDrawer.Portrait ? 0 : 360
            leftMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : notificationDrawer.minWidthHeight * 0.06
        }
    }

    // Secondary swipe area for uses in portrait.
    // Covers the surface area of the quick settings panel to allow dismissing or expanding the drawer while also having it over top of the notification list.
    MobileShell.SwipeArea {
        id: swipeAreaPortrait
        mode: MobileShell.SwipeArea.VerticalOnly
        anchors {
            top: parent.top
            left: parent.left
            right: parent.right
        }
        height: root.actionDrawer.mode === ActionDrawer.Portrait ? actionDrawer.offsetResistance : root.height
        interactive: root.actionDrawer.mode === ActionDrawer.Portrait

        onSwipeStarted: root.startSwipe()
        onSwipeEnded: root.endSwipe()
        onSwipeMove: (totalDeltaX, totalDeltaY, deltaX, deltaY) => root.moveSwipe(totalDeltaX, totalDeltaY, deltaX, deltaY)

        onTouchpadScrollStarted: root.startSwipe()
        onTouchpadScrollEnded: root.endSwipe()
        onTouchpadScrollMove: (totalDeltaX, totalDeltaY, deltaX, deltaY) => root.moveSwipe(totalDeltaX, totalDeltaY, deltaX, deltaY)

        // Proxy in the layout that switches between landscape and portrait mode.
        ColumnLayout {
            anchors.fill: parent
            visible: root.actionDrawer.mode == ActionDrawer.Portrait
            LayoutItemProxy { target: contentContainerLoader }
        }
    }

    // Layout that switches between landscape and portrait mode
    Loader {
        id: contentContainerLoader

        Layout.fillWidth: true
        Layout.fillHeight: true

        readonly property real minimizedQuickSettingsOffset: item ? item.minimizedQuickSettingsOffset : 0
        readonly property real maximizedQuickSettingsOffset: item ? item.maximizedQuickSettingsOffset : 0

        readonly property real offsetDist: root.actionDrawer.offset - minimizedQuickSettingsOffset
        readonly property real totalOffsetDist: maximizedQuickSettingsOffset - minimizedQuickSettingsOffset
        readonly property real minimizedToFullProgress: root.actionDrawer.openToPinnedMode ? (root.actionDrawer.opened ? applyMinMax(offsetDist / totalOffsetDist) : 0) : 1

        asynchronous: true
        sourceComponent: root.actionDrawer.mode == ActionDrawer.Portrait ? portraitContentContainer : landscapeContentContainer
    }

    // The portrait content container.
    Component {
        id: portraitContentContainer
        PortraitContentContainer {
            actionDrawer: root.actionDrawer
            width: root.width
            height: root.height

            quickSettings: root.quickSettings
            statusBar: root.statusBar
            mediaControlsWidget: root.mediaControlsWidget
        }
    }

    // The landscape content container.
    Component {
        id: landscapeContentContainer
        LandscapeContentContainer {
            actionDrawer: root.actionDrawer
            width: root.width
            height: root.height

            quickSettings: root.quickSettings
            statusBar: root.statusBar
        }
    }

    // Components shared between the two layouts.
    // This allows us to avoid having to reload the components every time the screen size changes.

    property MobileShell.QuickSettings quickSettings: MobileShell.QuickSettings {
        id: quickSettings
        actionDrawer: root.actionDrawer
        quickSettingsModel: root.quickSettingsModel
        fullViewProgress: (root.actionDrawer.mode == ActionDrawer.Portrait) ? contentContainerLoader.minimizedToFullProgress : 1.0
    }

    property MobileShell.StatusBar statusBar: MobileShell.StatusBar {
        id: statusBar
        Kirigami.Theme.colorSet: Kirigami.Theme.Window
        Kirigami.Theme.inherit: false

        backgroundColor: "transparent"
        showSecondRow: root.actionDrawer.mode == ActionDrawer.Portrait
        showDropShadow: false
        showTime: root.actionDrawer.mode == ActionDrawer.Portrait

        // security reasons, system tray also doesn't work on lockscreen
        disableSystemTray: root.actionDrawer.restrictedPermissions

        opacity: brightnessPressedValue
    }

    property MobileShell.MediaControlsWidget mediaControlsWidget: MobileShell.MediaControlsWidget {
        id: mediaWidget
        inActionDrawer: root.actionDrawer.mode == ActionDrawer.Portrait

        opacity: brightnessPressedValue
    }
}