mobileshell: Manually specify QML files, and private some internal files

The globbing pattern for finding QML files is problematic because it
breaks when we add/delete a file (requiring us to delete
~/kde/build/plasma-mobile). It also placed every file (both public and
internal files) in the same flat namespace, carrying the risk of name
collisions between unrelated folders.

This commit manually specifies every file in the package. It also moves internal files in the actiondrawer folder into its own namespace. Followup MRs will do this process for other folders.
This commit is contained in:
Devin Lin 2025-07-17 01:42:35 -04:00
parent 62a2ddc5e7
commit bc3e80c479
15 changed files with 128 additions and 127 deletions

View file

@ -33,12 +33,111 @@ set_source_files_properties(
QT_QML_SINGLETON_TYPE TRUE
)
# Include qml and js files within ./qml/
file(GLOB_RECURSE _qml_sources
"qml/*.qml"
"qml/*.js"
# QML files meant to be used publicly
# TODO: move files gradually out of main namespace into sub namespaces
ecm_target_qml_sources(mobileshellplugin SOURCES
qml/actiondrawer/ActionDrawer.qml
qml/actiondrawer/ActionDrawerOpenSurface.qml
qml/actiondrawer/ActionDrawerWindow.qml
qml/components/AppLaunch.qml
qml/components/BaseItem.qml
qml/components/Constants.qml
qml/components/Flickable.qml
qml/components/FlickableOpacityGradient.qml
qml/components/GridView.qml
qml/components/HapticsEffect.qml
qml/components/ListView.qml
qml/components/MarqueeLabel.qml
qml/components/PanelBackground.qml
qml/components/ScreenEdgeDragEffect.qml
qml/components/StartupFeedbackPanelFill.qml
qml/components/StartupFeedbackWindows.qml
qml/components/TextDropShadow.qml
qml/components/VelocityCalculator.qml
qml/dataproviders/AudioInfo.qml
qml/dataproviders/BatteryInfo.qml
qml/dataproviders/BluetoothInfo.qml
qml/dataproviders/NetworkInfo.qml
qml/dataproviders/SignalStrengthInfo.qml
qml/homescreen/BlurEffect.qml
qml/homescreen/DeviceLock.qml
qml/homescreen/HomeScreen.qml
qml/homescreen/WallpaperSelector.qml
qml/navigationpanel/NavigationPanel.qml
qml/navigationpanel/NavigationPanelAction.qml
qml/navigationpanel/NavigationPanelButton.qml
qml/popups/actionbuttons/ActionButton.qml
qml/popups/actionbuttons/ActionButtonsProvider.qml
qml/popups/actionbuttons/RotationButton.qml
qml/popups/notifications/NotificationPopup.qml
qml/popups/notifications/NotificationPopupManager.qml
qml/popups/notifications/NotificationPopupProvider.qml
qml/popups/notifications/PulseAudio.qml
qml/popups/volumeosd/AudioApplet.qml
qml/popups/volumeosd/DeviceListItem.qml
qml/popups/volumeosd/icon.js
qml/popups/volumeosd/ListItemBase.qml
qml/popups/volumeosd/PopupCard.qml
qml/popups/volumeosd/StreamListItem.qml
qml/popups/volumeosd/VolumeChangedPopup.qml
qml/popups/volumeosd/VolumeOSD.qml
qml/popups/volumeosd/VolumeOSDProvider.qml
qml/popups/PopupProviderLoader.qml
qml/statusbar/indicators/BatteryIndicator.qml
qml/statusbar/indicators/BluetoothIndicator.qml
qml/statusbar/indicators/InternetIndicator.qml
qml/statusbar/indicators/SignalStrengthIndicator.qml
qml/statusbar/indicators/VolumeIndicator.qml
qml/statusbar/ClockText.qml
qml/statusbar/StatusBar.qml
qml/statusbar/TaskWidget.qml
qml/widgets/krunner/KRunnerScreen.qml
qml/widgets/mediacontrols/BlurredBackground.qml
qml/widgets/mediacontrols/MediaControlsSource.qml
qml/widgets/mediacontrols/MediaControlsWidget.qml
qml/widgets/notifications/BaseNotificationItem.qml
qml/widgets/notifications/NotificationBodyLabel.qml
qml/widgets/notifications/NotificationCard.qml
qml/widgets/notifications/NotificationEditContextMenu.qml
qml/widgets/notifications/NotificationFooterActions.qml
qml/widgets/notifications/NotificationGroupHeader.qml
qml/widgets/notifications/NotificationItem.qml
qml/widgets/notifications/NotificationJobDetails.qml
qml/widgets/notifications/NotificationJobItem.qml
qml/widgets/notifications/NotificationPopupItem.qml
qml/widgets/notifications/NotificationReplyField.qml
qml/widgets/notifications/NotificationsModelType.qml
qml/widgets/notifications/NotificationsUtils.js
qml/widgets/notifications/NotificationsWidget.qml
qml/widgets/notifications/NotificationTimeText.qml
qml/widgets/notifications/ThumbnailStrip.qml
)
# Other supporting QML files
ecm_target_qml_sources(mobileshellplugin SOURCES
qml/actiondrawer/private/BrightnessItem.qml
qml/actiondrawer/private/Handle.qml
qml/actiondrawer/private/QuickSettings.qml
qml/actiondrawer/private/QuickSettingsDelegate.qml
qml/actiondrawer/private/QuickSettingsDrawer.qml
qml/actiondrawer/private/QuickSettingsFullDelegate.qml
qml/actiondrawer/private/QuickSettingsMinimizedDelegate.qml
qml/actiondrawer/private/QuickSettingsPanel.qml
qml/actiondrawer/private/ContentContainer.qml
qml/actiondrawer/private/LandscapeContentContainer.qml
qml/actiondrawer/private/NotificationDrawer.qml
qml/actiondrawer/private/PortraitContentContainer.qml
PATH actiondrawer/private
)
ecm_target_qml_sources(mobileshellplugin SOURCES ${_qml_sources})
target_link_libraries(mobileshellplugin

View file

@ -12,9 +12,11 @@ import QtQuick.Window 2.2
import org.kde.plasma.components 3.0 as PlasmaComponents
import org.kde.plasma.private.nanoshell 2.0 as NanoShell
import org.kde.plasma.private.mobileshell as MobileShell
import org.kde.kirigami 2.20 as Kirigami
import org.kde.plasma.private.mobileshell.quicksettingsplugin as QS
import org.kde.plasma.private.mobileshell as MobileShell
import 'actiondrawer/private'
Item {
id: root
@ -96,7 +98,7 @@ Item {
/**
* The mode of the action drawer (portrait or landscape).
*/
property int mode: (height > width && width <= largePortraitThreshold) ? ActionDrawer.Portrait : ActionDrawer.Landscape
property int mode: (height > width && width <= largePortraitThreshold) ? MobileShell.ActionDrawer.Portrait : MobileShell.ActionDrawer.Landscape
/**
* At some point, even if the screen is technically portrait, if we have a ton of width it'd be best to just show the landscape mode.

View file

@ -83,14 +83,14 @@ Item {
// Proxy in the layout that switches between landscape and portrait mode.
ColumnLayout {
anchors.fill: parent
visible: root.actionDrawer.mode != ActionDrawer.Portrait
visible: root.actionDrawer.mode != MobileShell.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
visible: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait
// dismiss drawer when background is clicked
onClicked: root.actionDrawer.close();
@ -106,8 +106,8 @@ Item {
anchors {
topMargin: notificationDrawer.height + 1
leftMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : 10
rightMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : notificationDrawer.notificationWidget.anchors.rightMargin + Kirigami.Units.gridUnit - notificationDrawer.anchors.leftMargin + 370
leftMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : 10
rightMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : notificationDrawer.notificationWidget.anchors.rightMargin + Kirigami.Units.gridUnit - notificationDrawer.anchors.leftMargin + 370
top: parent.top
left: parent.left
right: parent.right
@ -170,8 +170,8 @@ Item {
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
rightMargin: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : 360
leftMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : notificationDrawer.minWidthHeight * 0.06
}
}
@ -185,8 +185,8 @@ Item {
left: parent.left
right: parent.right
}
height: root.actionDrawer.mode === ActionDrawer.Portrait ? actionDrawer.offsetResistance : root.height
interactive: root.actionDrawer.mode === ActionDrawer.Portrait
height: root.actionDrawer.mode === MobileShell.ActionDrawer.Portrait ? actionDrawer.offsetResistance : root.height
interactive: root.actionDrawer.mode === MobileShell.ActionDrawer.Portrait
onSwipeStarted: root.startSwipe()
onSwipeEnded: root.endSwipe()
@ -199,7 +199,7 @@ Item {
// Proxy in the layout that switches between landscape and portrait mode.
ColumnLayout {
anchors.fill: parent
visible: root.actionDrawer.mode == ActionDrawer.Portrait
visible: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait
LayoutItemProxy { target: contentContainerLoader }
}
}
@ -219,7 +219,7 @@ Item {
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
sourceComponent: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? portraitContentContainer : landscapeContentContainer
}
// The portrait content container.
@ -252,11 +252,11 @@ Item {
// 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 {
property QuickSettings quickSettings: QuickSettings {
id: quickSettings
actionDrawer: root.actionDrawer
quickSettingsModel: root.quickSettingsModel
fullViewProgress: (root.actionDrawer.mode == ActionDrawer.Portrait) ? contentContainerLoader.minimizedToFullProgress : 1.0
fullViewProgress: (root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait) ? contentContainerLoader.minimizedToFullProgress : 1.0
}
property MobileShell.StatusBar statusBar: MobileShell.StatusBar {
@ -265,9 +265,9 @@ Item {
Kirigami.Theme.inherit: false
backgroundColor: "transparent"
showSecondRow: root.actionDrawer.mode == ActionDrawer.Portrait
showSecondRow: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait
showDropShadow: false
showTime: root.actionDrawer.mode == ActionDrawer.Portrait
showTime: root.actionDrawer.mode == MobileShell.ActionDrawer.Portrait
// security reasons, system tray also doesn't work on lockscreen
disableSystemTray: root.actionDrawer.restrictedPermissions

View file

@ -24,8 +24,8 @@ Item {
property alias notificationWidget: notificationWidget
property real contentY: notificationWidget.listView.contentY
property real topPadding: actionDrawer.mode == ActionDrawer.Portrait ? Kirigami.Units.largeSpacing : date.y + date.height + Kirigami.Units.smallSpacing * 6
property real topMargin: actionDrawer.mode == ActionDrawer.Portrait ? actionDrawer.offsetResistance + 1 : 0
property real topPadding: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? Kirigami.Units.largeSpacing : date.y + date.height + Kirigami.Units.smallSpacing * 6
property real topMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? actionDrawer.offsetResistance + 1 : 0
readonly property real minWidthHeight: Math.min(actionDrawer.width, actionDrawer.height)
readonly property bool hasNotifications: notificationWidget.hasNotifications
@ -54,8 +54,8 @@ Item {
id: notificationWidget
anchors.fill: parent
anchors.topMargin: root.topMargin
anchors.rightMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : Math.max(root.width - Kirigami.Units.gridUnit * 25, 0)
anchors.leftMargin: actionDrawer.mode == ActionDrawer.Portrait ? 0 : -Kirigami.Units.gridUnit
anchors.rightMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : Math.max(root.width - Kirigami.Units.gridUnit * 25, 0)
anchors.leftMargin: actionDrawer.mode == MobileShell.ActionDrawer.Portrait ? 0 : -Kirigami.Units.gridUnit
historyModel: actionDrawer.notificationModel
historyModelType: actionDrawer.notificationModelType
@ -63,7 +63,7 @@ Item {
actionsRequireUnlock: actionDrawer.restrictedPermissions
onUnlockRequested: actionDrawer.permissionsRequested()
topPadding: root.topPadding
showHeader: actionDrawer.mode != ActionDrawer.Portrait
showHeader: actionDrawer.mode != MobileShell.ActionDrawer.Portrait
listView.interactive: !actionDrawer.dragging && root.listOverflowing
Connections {
@ -158,7 +158,7 @@ Item {
Item {
id: landscapeModeHeader
anchors.fill: parent
visible: actionDrawer.mode != ActionDrawer.Portrait
visible: actionDrawer.mode != MobileShell.ActionDrawer.Portrait
transform: [
Translate {

View file

@ -1,100 +0,0 @@
/*
* SPDX-FileCopyrightText: 2023 Yari Polla <skilvingr@gmail.com>
*
* SPDX-License-Identifier: GPL-2.0-or-later
*/
import QtQuick
import QtQuick.Layouts
import org.kde.plasma.components 3.0 as PlasmaComponents
import org.kde.plasma.private.nanoshell as NanoShell
import org.kde.kirigami as Kirigami
/*
* A context popup menu closable by tapping outside it.
* Being it a FullScreenOverlay, no event is delivered to underlying components until it's closed.
*
* - property relatedTo: Item to which the popup is related; the popup will spawn either above or below it, depending on its y value.
* If no item is supplied, the popup will spawn at the center of the screen.
* - property title: The title for the menu.
* - property menuActions: The menu will be composed of these actions.
* - function showOverlay(): Spawns the popup.
*/
NanoShell.FullScreenOverlay {
id: overlay
visible: false
color: "transparent"
property point mappedGlobalCoordinates
property Item relatedTo: null
property string title
property list<Kirigami.Action> menuActions
function showOverlay() {
if (!overlay.visible) {
overlay.visible = true;
menu.open();
}
}
Item {
id: containerItem
height: menu.implicitHeight
width: menu.implicitWidth
readonly property point coordinates: {
if (relatedTo) { // Place next to Item
return mapFromGlobal(mappedGlobalCoordinates.x, mappedGlobalCoordinates.y);
} else { // Place at the center of the screen
return Qt.point((overlay.width - width) / 2, (overlay.height - height) / 2);
}
}
x: coordinates.x
y: coordinates.y
transform: Translate {
x: 0
y: (containerItem.coordinates.y <= overlay.height/2 ? relatedTo.height : -containerItem.height) - Constants.topPanelHeight
}
PlasmaComponents.Menu {
id: menu
title: overlay.title
closePolicy: PlasmaComponents.Menu.CloseOnReleaseOutside | PlasmaComponents.Menu.CloseOnEscape
onClosed: overlay.close()
Component.onCompleted: {
for (var i = 0; i < menuActions.length; i++) {
appendItem(menuActions[i]);
}
}
function appendItem(button) {
menu.addItem(menuItem.createObject(
menu,
{
iconName: button.iconName,
text: i18n(button.text),
callback: button.triggered
}));
}
Component {
id: menuItem
PlasmaComponents.MenuItem {
property string iconName: ""
property var callback: () => {}
icon.name: iconName
onClicked: callback()
}
}
}
}
}