Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: register a D-Bus service per widget to apply presets #138

Open
wants to merge 3 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 30 additions & 8 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,9 +42,13 @@ Fully-featured widget to bring Latte-Dock and WM status bar customization featur
* [Built-in presets](https://github.com/luisbocanegra/plasma-panel-colorizer/tree/main/package/contents/ui/presets)
* Create your own presets
* Preset auto-loading
* Floating panel
* Maximized window shown
* Window touching panel
* Fullscreen window
* Maximized window
* Window touching the panel
* At least one window is shown on screen
* Panel is floating
* Normal (fall-back when none of the above are meet)
* [Switch presets from the command-line using D-Bus](#switching-presets-using-the-commandline-with-d-bus)

### Panel/Widget/System Tray elements

Expand Down Expand Up @@ -96,8 +100,14 @@ Overrides let you give a completely different configuration to one or more widge

### KDE Store

1. **Right click on the Panel** > **Add or manage widgets** > **Add new...** > **Download new...**
2. **Search** for "**Panel Colorizer**", install and add it to a Panel.
1. Install these runtime dependencies or the equivalents for your distribution

```txt
python python-dbus python-gobject
```

2. **Right click on the Panel** > **Add or manage widgets** > **Add new...** > **Download new...**
3. **Search** for "**Panel Colorizer**", install and add it to a Panel.

* ~~[Plasma 5](https://store.kde.org/p/2131149) version v0.2.0~~ **[No longer maintained](https://github.com/luisbocanegra/plasma-panel-colorizer/issues/10)**

Expand All @@ -110,13 +120,13 @@ Overrides let you give a completely different configuration to one or more widge
* Arch

```txt
git gcc cmake extra-cmake-modules libplasma spectacle
git gcc cmake extra-cmake-modules libplasma spectacle python python-dbus python-gobject
```

* Fedora

```txt
git gcc-c++ cmake extra-cmake-modules libplasma-devel spectacle
git gcc-c++ cmake extra-cmake-modules libplasma-devel spectacle python3 python3-dbus python3-gobject
```

Spectacle is optional, will be used to create preset previews
Expand Down Expand Up @@ -187,6 +197,18 @@ To install the widget use one of these methods:
2. Go to the widget settings to change the current panel appearance (right click > Configure...)
3. Widget can set to only show in panel **Edit Mode** (right click > Hide widget or from the widget settings)

### Switching presets using the commandline with D-Bus

1. Go to the widget settings
2. In General tab enable the D-Bus service
3. To apply a preset can use qdbus6 and pass the absolute path of a preset:

```sh
qdbus6 luisbocanegra.panel.colorizer.c337.w2346 /preset preset /path/to/preset/dir/
```

Each widget instance has its own D-bus name, you can get it from the same widget settings General tab.

## Adding or improving the built-in presets

Instructions to add new presets or improve the existing ones are [here](https://github.com/luisbocanegra/plasma-panel-colorizer/blob/main/package/contents/ui/presets/README.md)
Expand Down Expand Up @@ -243,7 +265,7 @@ Backgrounds are drawn by creating rectangle areas bellow widgets/panel, text and

**Performance**

I tried to optimize it so CPU usage only increases around 0.5-1% on my computer, but usage could vary depending on your System or how many widgets are in your panels.
I tried to optimize it so CPU usage only increases around 0.5-1% on my computer, usage may vary depending on your System or how many widgets are in your panels.

### Can this widget change the appearance of other parts of Plasma (e.g Desktop view, widget popups/tooltips, overview)

Expand Down
13 changes: 13 additions & 0 deletions package/contents/config/main.xml
Original file line number Diff line number Diff line change
Expand Up @@ -69,5 +69,18 @@
type="Int">
<default>0</default>
</entry>
<entry name="pythonExecutable" type="String">
<default>python3</default>
</entry>
<entry
name="enableDBusService"
type="Bool">
<default>false</default>
</entry>
<entry
name="dBusPollingRate"
type="Int">
<default>250</default>
</entry>
</group>
</kcfg>
73 changes: 73 additions & 0 deletions package/contents/ui/DBusServiceModel.qml
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import QtQuick
import org.kde.plasma.plasmoid


Item {

id: root
property bool enabled: false
property string preset: ""
property bool switchIsPending: false
property int poolingRate: 250

property string toolsDir: Qt.resolvedUrl("./tools").toString().substring(7) + "/"
property string serviceUtil: toolsDir+"service.py"
property string pythonExecutable: plasmoid.configuration.pythonExecutable
property string serviceCmd: pythonExecutable + " '" + serviceUtil + "' " + Plasmoid.containment.id + " " + Plasmoid.id
property string dbusName: Plasmoid.metaData.pluginId + ".c" + Plasmoid.containment.id + ".w" + Plasmoid.id
property string gdbusPartial: "gdbus call --session --dest "+dbusName+" --object-path /preset --method "+dbusName
property string pendingSwitchCmd: gdbusPartial +".pending_switch"
property string switchDoneCmd: gdbusPartial +".switch_done"
property string getPresetCmd: gdbusPartial +".preset"
property string quitServiceCmd: gdbusPartial +".quit"

RunCommand {
id: runCommand
onExited: (cmd, exitCode, exitStatus, stdout, stderr) => {
// console.error(cmd, exitCode, exitStatus, stdout, stderr)
if (exitCode!==0) return
stdout = stdout.trim().replace(/[()',]/g, "")
// console.log("stdout parsed:", stdout)
if(cmd === pendingSwitchCmd) {
switchIsPending = stdout === "true"
}
if (cmd === getPresetCmd) {
preset = stdout
switchIsPending = false
}
}
}

Component.onCompleted: {
toggleService()
}

function toggleService() {
if (enabled) {
runCommand.run(serviceCmd)
} else (
runCommand.run(quitServiceCmd)
)
}

onEnabledChanged: toggleService()

onSwitchIsPendingChanged: {
if (switchIsPending) {
runCommand.run(switchDoneCmd)
runCommand.run(getPresetCmd)
}
}

Timer {
id: updateTimer
interval: poolingRate
running: enabled
repeat: true
onTriggered: {
if (switchIsPending) return
runCommand.run(pendingSwitchCmd)
}
}
}

5 changes: 4 additions & 1 deletion package/contents/ui/code/globals.js
Original file line number Diff line number Diff line change
Expand Up @@ -260,5 +260,8 @@ const ignoredConfigs = [
"configurationOverrides",
"widgetClickMode",
"switchPresets",
"switchPresetsIndex"
"switchPresetsIndex",
"enableDBusService",
"dBusPollingRate",
"pythonExecutable"
]
84 changes: 84 additions & 0 deletions package/contents/ui/configGeneral.qml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,15 @@ KCM.SimpleKCM {
property bool cfg_hideWidget: hideWidget.checked
property alias cfg_isEnabled: headerComponent.isEnabled
property alias cfg_enableDebug: enableDebug.checked
property alias cfg_enableDBusService: enableDBusService.checked
property alias cfg_pythonExecutable: pythonExecutable.text
property alias cfg_dBusPollingRate: dBusPollingRate.value

property string presetsDir: StandardPaths.writableLocation(
StandardPaths.HomeLocation).toString().substring(7) + "/.config/panel-colorizer/presets"
property string presetsBuiltinDir: Qt.resolvedUrl("./presets").toString().substring(7) + "/"

property string dbusName: Plasmoid.metaData.pluginId + ".c" + Plasmoid.containment.id + ".w" + Plasmoid.id

header: ColumnLayout {
Components.Header {
Expand All @@ -27,6 +36,7 @@ KCM.SimpleKCM {

ColumnLayout {
Kirigami.FormLayout {
id: form
CheckBox {
Kirigami.FormData.label: i18n("Hide widget:")
id: hideWidget
Expand All @@ -41,6 +51,80 @@ KCM.SimpleKCM {
onCheckedChanged: cfg_enableDebug = checked
text: i18n("Show debugging information")
}

Kirigami.Separator {
Kirigami.FormData.isSection: true
Kirigami.FormData.label: i18n("D-Bus Service")
Layout.fillWidth: true
}

CheckBox {
Kirigami.FormData.label: i18n("Enabled:")
id: enableDBusService
checked: cfg_enableDBusService
onCheckedChanged: cfg_enableDBusService = checked
text: i18n("D-Bus name:") + " " + dbusName
}

Label {
text: i18n("Each Panel Colorizer instance has its D-Bus name.")
wrapMode: Text.WordWrap
Layout.preferredWidth: 400
opacity: 0.6
}

TextField {
Kirigami.FormData.label: i18n("Python 3 executable:")
id: pythonExecutable
placeholderText: qsTr("Python executable e.g. python, python3")
enabled: enableDBusService.checked
}

Label {
text: i18n("Required to run the D-Bus service in the background")
wrapMode: Text.WordWrap
Layout.preferredWidth: 400
opacity: 0.6
}

SpinBox {
Kirigami.FormData.label: i18n("Polling rate:")
from: 10
to: 9999
stepSize: 100
id: dBusPollingRate
}

Label {
text: i18n("How fast the widget reacts to D-Bus changes")
wrapMode: Text.WordWrap
Layout.preferredWidth: 400
opacity: 0.6
}


Label {
Kirigami.FormData.label: i18n("Usage:")
text: i18n("Apply a preset:")
}

TextArea {
text: "qdbus6 " + dbusName + " /preset preset /path/to/preset/dir/"
readOnly: true
wrapMode: Text.WordWrap
Layout.preferredWidth: 400
}

Label {
text: i18n("Preview and switch presets using fzf + qdbus6 + jq:")
}

TextArea {
text: "find " + presetsBuiltinDir + " "+ presetsDir +" -mindepth 1 -prune -type d | fzf --preview 'qdbus6 " + dbusName + " /preset preset {} && jq --color-output . {}/settings.json'"
readOnly: true
wrapMode: Text.WordWrap
Layout.preferredWidth: 400
}
}
}
}
32 changes: 20 additions & 12 deletions package/contents/ui/main.qml
Original file line number Diff line number Diff line change
Expand Up @@ -150,7 +150,7 @@ PlasmoidItem {

onStockPanelSettingsChanged: {
Qt.callLater(function() {
console.error(JSON.stringify(stockPanelSettings))
// console.error(JSON.stringify(stockPanelSettings))
let script = Utils.setPanelModeScript(panelPosition, stockPanelSettings)
Utils.evaluateScript(script)
})
Expand Down Expand Up @@ -1333,7 +1333,7 @@ PlasmoidItem {
if (!child.applet?.plasmoid?.pluginName) continue
// if (Utils.getBgManaged(child)) continue
// console.error(child.applet?.plasmoid?.pluginName)
if (child.applet.plasmoid.pluginName !== "luisbocanegra.panel.colorizer") {
if (child.applet.plasmoid.pluginName !== Plasmoid.metaData.pluginId) {
child.applet.plasmoid.contextualActions.push(configureAction)
}
const isTray = child.applet.plasmoid.pluginName === "org.kde.plasma.systemtray"
Expand Down Expand Up @@ -1433,20 +1433,20 @@ PlasmoidItem {
}
}

// toolTipMainText: onDesktop ? "" :
toolTipSubText: {
let text = ""
if (onDesktop) {
return "<font color='"+Kirigami.Theme.neutralTextColor+"'>Panel not found, this widget must be child of a panel</font>"
}
if (!plasmoid.configuration.isEnabled) {
return ""
}
const name = plasmoid.configuration.lastPreset.split("/")
if (name.length) {
return i18n("Last preset loaded:") + " " + name[name.length-1]
text = "<font color='"+Kirigami.Theme.neutralTextColor+"'>Panel not found, this widget must be child of a panel</font>"
} else if (plasmoid.configuration.isEnabled) {
const name = plasmoid.configuration.lastPreset.split("/")
if (name.length) {
text = i18n("Last preset loaded:") + " " + name[name.length-1]
}
}
return ""
return text
}
toolTipTextFormat: Text.RichText
toolTipTextFormat: Text.PlainText

Plasmoid.status: (editMode || !hideWidget) ?
PlasmaCore.Types.ActiveStatus :
Expand Down Expand Up @@ -1588,4 +1588,12 @@ PlasmoidItem {
}

fullRepresentation: onDesktop ? desktopView : popupView

DBusServiceModel {
enabled: plasmoid.configuration.enableDBusService
poolingRate: plasmoid.configuration.dBusPollingRate
onPresetChanged: {
applyPreset(preset)
}
}
}
Loading