Warning, /plasma/flatpak-kcm/ui/permissions.qml is written in an unsupported language. File is not indexed.
0001 /**
0002 * SPDX-FileCopyrightText: 2022 Suhaas Joshi <joshiesuhaas0@gmail.com>
0003 * SPDX-FileCopyrightText: 2023 ivan tkachenko <me@ratijas.tk>
0004 * SPDX-License-Identifier: GPL-2.0-or-later
0005 */
0006
0007 pragma ComponentBehavior: Bound
0008
0009 import QtQuick
0010 import QtQuick.Controls as QQC2
0011 import QtQuick.Layouts
0012
0013 import org.kde.kcmutils as KCM
0014 import org.kde.kirigami as Kirigami
0015 import org.kde.plasma.kcm.flatpakpermissions
0016
0017 KCM.ScrollViewKCM {
0018 id: root
0019
0020 required property FlatpakReference ref
0021
0022 title: i18n("Permissions")
0023 implicitWidth: Kirigami.Units.gridUnit * 15
0024 framedView: false
0025
0026 Kirigami.PlaceholderMessage {
0027 text: i18n("Select an application from the list to view its permissions here")
0028 width: parent.width - (Kirigami.Units.largeSpacing * 4)
0029 anchors.centerIn: parent
0030 visible: ref === null
0031 }
0032
0033 Kirigami.Separator {
0034 anchors.left: parent.left
0035 height: parent.height
0036 }
0037
0038 Component {
0039 id: addEnvironmentVariableDialogComponent
0040
0041 AddEnvironmentVariableDialog {
0042 parent: root.Kirigami.ColumnView.view
0043 model: permsModel
0044
0045 onClosed: destroy()
0046 }
0047 }
0048
0049 Component {
0050 id: textPromptDialogComponent
0051
0052 TextPromptDialog {
0053 parent: root.Kirigami.ColumnView.view
0054 model: permsModel
0055
0056 onClosed: destroy()
0057 }
0058 }
0059
0060 // Having it inside a component helps to separate layouts and workarounds for nullable property accesses.
0061 Component {
0062 id: headerComponent
0063
0064 RowLayout {
0065 id: header
0066
0067 readonly property url icon: root.ref.iconSource
0068 readonly property string title: root.ref.displayName
0069 readonly property string subtitle: root.ref.version
0070
0071 spacing: 0
0072
0073 width: ListView.view.width - ListView.view.leftMargin - ListView.view.rightMargin
0074
0075 Kirigami.Icon {
0076 // Fallback doesn't kick in when source is an empty string/url
0077 source: header.icon.toString() !== "" ? header.icon : "application-vnd.flatpak.ref"
0078
0079 Layout.alignment: Qt.AlignCenter
0080 Layout.preferredWidth: Kirigami.Units.iconSizes.large
0081 Layout.preferredHeight: Kirigami.Units.iconSizes.large
0082
0083 // RowLayout is incapable of paddings, so use margins on both child items instead.
0084 Layout.margins: Kirigami.Units.largeSpacing
0085 }
0086 ColumnLayout {
0087 spacing: Kirigami.Units.smallSpacing
0088 Layout.fillWidth: true
0089
0090 Layout.margins: Kirigami.Units.largeSpacing
0091 Layout.leftMargin: 0
0092
0093 Kirigami.Heading {
0094 text: header.title
0095 wrapMode: Text.Wrap
0096 Layout.fillWidth: true
0097 }
0098 Kirigami.Heading {
0099 text: header.subtitle
0100 type: Kirigami.Heading.Secondary
0101 level: 3
0102 wrapMode: Text.Wrap
0103 Layout.fillWidth: true
0104 }
0105 }
0106 }
0107 }
0108
0109 view: ListView {
0110 model: FlatpakPermissionModel {
0111 id: permsModel
0112 reference: root.ref
0113 }
0114
0115 currentIndex: -1
0116 // Mitigate ListView's poor layouting stills.
0117 // Without it, section delegates may shift down and overlap.
0118 reuseItems: false
0119 cacheBuffer: 10000
0120
0121 // Ref is assumed to remain constant for the lifetime of this page. If
0122 // it's not null, then it would remain so, and no further checks are
0123 // needed inside the component.
0124 header: root.ref === null ? null : headerComponent
0125 headerPositioning: ListView.InlineHeader
0126
0127 section.property: "section"
0128 section.criteria: ViewSection.FullString
0129 section.delegate: Kirigami.ListSectionHeader {
0130 id: sectionDelegate
0131
0132 required property string section
0133
0134 /**
0135 * Sorry about this mess. ListView automatically converts data of
0136 * section role to string, so we parse it back into enum.
0137 */
0138 readonly property /*FlatpakPermissionsSectionType::Type*/ int sectionType: parseInt(section)
0139
0140 width: ListView.view.width - ListView.view.leftMargin - ListView.view.rightMargin
0141 label: permsModel.sectionHeaderForSectionType(sectionType)
0142 QQC2.ToolButton {
0143 text: permsModel.showAdvanced ? i18n("Hide advanced permissions") : i18n("Show advanced permissions")
0144 display: QQC2.AbstractButton.IconOnly
0145 icon.name: permsModel.showAdvanced ? "collapse" : "expand"
0146 visible: sectionDelegate.sectionType === FlatpakPermissionsSectionType.Advanced
0147 onClicked: permsModel.showAdvanced = !permsModel.showAdvanced
0148 Layout.alignment: Qt.AlignRight
0149
0150 QQC2.ToolTip.text: text
0151 QQC2.ToolTip.visible: Kirigami.Settings.tabletMode ? pressed : hovered
0152 QQC2.ToolTip.delay: Kirigami.Settings.tabletMode ? Qt.styleHints.mousePressAndHoldInterval : Kirigami.Units.toolTipDelay
0153 }
0154 QQC2.ToolButton {
0155 text: i18n("Add New")
0156 icon.name: "bqm-add"
0157 visible: [
0158 FlatpakPermissionsSectionType.Filesystems,
0159 FlatpakPermissionsSectionType.SessionBus,
0160 FlatpakPermissionsSectionType.SystemBus,
0161 FlatpakPermissionsSectionType.Environment,
0162 ].includes(sectionDelegate.sectionType)
0163 onClicked: {
0164 if (sectionDelegate.sectionType === FlatpakPermissionsSectionType.Environment) {
0165 const dialog = addEnvironmentVariableDialogComponent.createObject(root, {
0166 model: permsModel,
0167 });
0168 dialog.open();
0169 } else {
0170 const dialog = textPromptDialogComponent.createObject(root, {
0171 model: permsModel,
0172 sectionType: sectionDelegate.sectionType,
0173 });
0174 dialog.open();
0175 }
0176 }
0177 Layout.alignment: Qt.AlignRight
0178
0179 QQC2.ToolTip.text: permsModel.sectionAddButtonToolTipTextForSectionType(sectionDelegate.sectionType)
0180 QQC2.ToolTip.visible: Kirigami.Settings.tabletMode ? pressed : hovered
0181 QQC2.ToolTip.delay: Kirigami.Settings.tabletMode ? Qt.styleHints.mousePressAndHoldInterval : Kirigami.Units.toolTipDelay
0182 }
0183 }
0184
0185 // Can't use a CheckDelegate or one of its subclasses since we need the checkbox
0186 // to highlight when it's in a non-default state and none of the pre-made delegates
0187 // can do that
0188 delegate: QQC2.ItemDelegate {
0189 id: permItem
0190
0191 required property var model
0192 required property int index
0193
0194 function toggleAndUncheck() {
0195 if (checkable) {
0196 permsModel.togglePermissionAtRow(index);
0197 }
0198 ListView.view.currentIndex = -1;
0199 }
0200
0201 width: ListView.view.width - ListView.view.leftMargin - ListView.view.rightMargin
0202
0203 // Default-provided custom entries are not meant to be unchecked:
0204 // it is a meaningless undefined operation.
0205 checkable: model.canBeDisabled
0206
0207 visible: model.isNotDummy
0208
0209 onClicked: toggleAndUncheck()
0210
0211 contentItem: RowLayout {
0212 spacing: Kirigami.Units.smallSpacing
0213
0214 QQC2.CheckBox {
0215 id: checkBox
0216 enabled: permItem.checkable
0217 checked: permItem.model.isEffectiveEnabled
0218
0219 onToggled: permItem.toggleAndUncheck()
0220
0221 KCM.SettingHighlighter {
0222 highlight: permItem.model.isEffectiveEnabled !== permItem.model.isDefaultEnabled
0223 }
0224 }
0225
0226 QQC2.Label {
0227 Layout.fillWidth: true
0228 text: model.description
0229 elide: Text.ElideRight
0230 }
0231
0232 QQC2.ComboBox {
0233 visible: [
0234 FlatpakPermissionsSectionType.Filesystems,
0235 FlatpakPermissionsSectionType.SessionBus,
0236 FlatpakPermissionsSectionType.SystemBus,
0237 ].includes(permItem.model.section)
0238
0239 enabled: checkBox.checked
0240
0241 model: permItem.model.valuesModel
0242 textRole: "display"
0243 valueRole: "value"
0244
0245 KCM.SettingHighlighter {
0246 highlight: permItem.model.effectiveValue !== permItem.model.defaultValue
0247 }
0248
0249 onActivated: index => {
0250 // Assuming this is only called for appropriate visible entries.
0251 permsModel.setPermissionValueAtRow(permItem.index, currentValue);
0252 }
0253
0254 Component.onCompleted: {
0255 // Still need to check section type, as this is called for every entry.
0256 if (permItem.model.isNotDummy && [
0257 FlatpakPermissionsSectionType.Filesystems,
0258 FlatpakPermissionsSectionType.SessionBus,
0259 FlatpakPermissionsSectionType.SystemBus,
0260 ].includes(permItem.model.section)) {
0261 currentIndex = Qt.binding(() => indexOfValue(permItem.model.effectiveValue));
0262 }
0263 }
0264 }
0265
0266 QQC2.TextField {
0267 visible: permItem.model.isNotDummy && permItem.model.section === FlatpakPermissionsSectionType.Environment
0268 text: (permItem.model.isNotDummy && permItem.model.section === FlatpakPermissionsSectionType.Environment)
0269 ? permItem.model.effectiveValue : ""
0270 enabled: checkBox.checked
0271
0272 onTextEdited: {
0273 permsModel.setPermissionValueAtRow(permItem.index, text);
0274 }
0275
0276 KCM.SettingHighlighter {
0277 highlight: permItem.model.effectiveValue !== permItem.model.defaultValue
0278 }
0279 }
0280 }
0281 }
0282 }
0283 }