envmanager: Handle SSD toggling with kwin rules

Replace the convergentwindows KWin script SSD toggling with KWin rules to ensure
windows are maximized and have no window border (and toggle off for
docked mode). KWin rules work immediately at window creation, which is
more efficient than listening to window creation events and manually
changing properties on them.

Currently, window rules setting maximization don't seem to address all cases where a window gets unmaximized, so for the time being we will still need the logic in convergentwindows to handle any sidecases.
This commit is contained in:
Devin Lin 2024-11-15 13:12:22 -08:00
parent 4167045642
commit c45f9ed446
4 changed files with 101 additions and 25 deletions

View file

@ -72,5 +72,47 @@ QMap<QString, QMap<QString, QVariant>> getKwinrcSettings(KSharedConfig::Ptr m_mo
const QList<QString> KWIN_EFFECTS = {"blur", "mobiletaskswitcher", "screenedge"}; const QList<QString> KWIN_EFFECTS = {"blur", "mobiletaskswitcher", "screenedge"};
const QList<QString> KWIN_SCRIPTS = {"convergentwindows"}; const QList<QString> KWIN_SCRIPTS = {"convergentwindows"};
//ksmserver // ksmserver
const QMap<QString, QMap<QString, QVariant>> KSMSERVER_SETTINGS = {{"General", {{"loginMode", "emptySession"}}}}; const QMap<QString, QMap<QString, QVariant>> KSMSERVER_SETTINGS = {{"General", {{"loginMode", "emptySession"}}}};
// kwinrulesrc
const QList<QString> KWIN_RULES = {"plasma-mobile-desktop", "plasma-mobile-maximized-no-border"};
QMap<QString, QMap<QString, QVariant>> getKwinrulesrcSettings(KSharedConfig::Ptr m_mobileConfig, bool isMobileSession)
{
auto group = KConfigGroup{m_mobileConfig, QStringLiteral("General")};
bool convergenceModeEnabled = group.readEntry("convergenceModeEnabled", false);
if (convergenceModeEnabled || !isMobileSession) {
return {{"plasma-mobile-desktop",
{
{"Description", "Desktop windows (controlled by Plasma Mobile)"},
{"maximizehoriz", true},
{"maximizehorizrule", 1},
{"maximizevert", true},
{"maximizevertrule", 1},
{"noborderrule", 2},
}},
{"General",
{
{"count", 1},
{"rules", "plasma-mobile-desktop"},
}}};
} else {
return {{"plasma-mobile-maximized-no-border",
{
{"Description", "Mobile windows (controlled by Plasma Mobile)"},
{"maximizehoriz", true},
{"maximizehorizrule", 2},
{"maximizevert", true},
{"maximizevertrule", 2},
{"noborder", true},
{"noborderrule", 2},
}},
{"General",
{
{"count", 1},
{"rules", "plasma-mobile-maximized-no-border"},
}}};
}
}

View file

@ -26,6 +26,7 @@ Settings::Settings(QObject *parent)
, m_appBlacklistConfig{KSharedConfig::openConfig(u"applications-blacklistrc"_s, KConfig::SimpleConfig)} , m_appBlacklistConfig{KSharedConfig::openConfig(u"applications-blacklistrc"_s, KConfig::SimpleConfig)}
, m_kdeglobalsConfig{KSharedConfig::openConfig(u"kdeglobals"_s, KConfig::SimpleConfig)} , m_kdeglobalsConfig{KSharedConfig::openConfig(u"kdeglobals"_s, KConfig::SimpleConfig)}
, m_ksmServerConfig{KSharedConfig::openConfig(u"ksmserverrc"_s, KConfig::SimpleConfig)} , m_ksmServerConfig{KSharedConfig::openConfig(u"ksmserverrc"_s, KConfig::SimpleConfig)}
, m_kwinrulesrcConfig{KSharedConfig::openConfig(u"kwinrulesrc"_s, KConfig::SimpleConfig)}
, m_configWatcher{KConfigWatcher::create(m_mobileConfig)} , m_configWatcher{KConfigWatcher::create(m_mobileConfig)}
{ {
} }
@ -54,6 +55,14 @@ void Settings::loadSavedConfiguration()
// kwinrc // kwinrc
loadKeys(u"kwinrc"_s, m_kwinrcConfig, getKwinrcSettings(m_mobileConfig)); loadKeys(u"kwinrc"_s, m_kwinrcConfig, getKwinrcSettings(m_mobileConfig));
m_kwinrcConfig->sync(); m_kwinrcConfig->sync();
// kwinrules
for (const auto &groupName : KWIN_RULES) {
m_kwinrulesrcConfig->deleteGroup(groupName);
}
writeKeys(u"kwinrulesrc"_s, m_kwinrulesrcConfig, getKwinrulesrcSettings(m_mobileConfig, false), false, false);
m_kwinrulesrcConfig->sync();
reloadKWinConfig(); reloadKWinConfig();
// applications-blacklistrc // applications-blacklistrc
@ -74,6 +83,14 @@ void Settings::applyMobileConfiguration()
// kwinrc // kwinrc
writeKeys(u"kwinrc"_s, m_kwinrcConfig, getKwinrcSettings(m_mobileConfig), false); writeKeys(u"kwinrc"_s, m_kwinrcConfig, getKwinrcSettings(m_mobileConfig), false);
m_kwinrcConfig->sync(); m_kwinrcConfig->sync();
// kwinrules
for (const auto &groupName : KWIN_RULES) {
m_kwinrulesrcConfig->deleteGroup(groupName);
}
writeKeys(u"kwinrulesrc"_s, m_kwinrulesrcConfig, getKwinrulesrcSettings(m_mobileConfig, true), false, false);
m_kwinrulesrcConfig->sync();
reloadKWinConfig(); reloadKWinConfig();
// applications-blacklistrc // applications-blacklistrc
@ -97,7 +114,11 @@ void Settings::applyMobileConfiguration()
m_mobileConfig->sync(); m_mobileConfig->sync();
} }
void Settings::writeKeys(const QString &fileName, KSharedConfig::Ptr &config, const QMap<QString, QMap<QString, QVariant>> &settings, bool overwriteOnlyIfEmpty) void Settings::writeKeys(const QString &fileName,
KSharedConfig::Ptr &config,
const QMap<QString, QMap<QString, QVariant>> &settings,
bool overwriteOnlyIfEmpty,
bool saveSettings)
{ {
const auto groupNames = settings.keys(); const auto groupNames = settings.keys();
for (const auto &groupName : groupNames) { for (const auto &groupName : groupNames) {
@ -107,7 +128,9 @@ void Settings::writeKeys(const QString &fileName, KSharedConfig::Ptr &config, co
for (const auto &key : keys) { for (const auto &key : keys) {
if (!group.hasKey(key) || !overwriteOnlyIfEmpty) { if (!group.hasKey(key) || !overwriteOnlyIfEmpty) {
// save key // save key
if (saveSettings) {
saveConfigSetting(fileName, groupName, key, group.readEntry(key)); saveConfigSetting(fileName, groupName, key, group.readEntry(key));
}
// overwrite with mobile setting // overwrite with mobile setting
group.writeEntry(key, settings[groupName][key], KConfigGroup::Notify); group.writeEntry(key, settings[groupName][key], KConfigGroup::Notify);
@ -207,6 +230,10 @@ void Settings::reloadKWinConfig()
} }
// Call "start" to load enabled KWin scripts. // Call "start" to load enabled KWin scripts.
QDBusMessage message = QDBusMessage::createMethodCall(u"org.kde.KWin"_s, u"/Scripting"_s, u"org.kde.kwin.Scripting"_s, u"start"_s); QDBusMessage startScriptsMessage = QDBusMessage::createMethodCall(u"org.kde.KWin"_s, u"/Scripting"_s, u"org.kde.kwin.Scripting"_s, u"start"_s);
QDBusConnection::sessionBus().send(message); QDBusConnection::sessionBus().send(startScriptsMessage);
// Call reconfigure
QDBusMessage reconfigureMessage = QDBusMessage::createSignal("/KWin", "org.kde.KWin", "reconfigure");
QDBusConnection::sessionBus().send(reconfigureMessage);
} }

View file

@ -28,7 +28,11 @@ private:
// applies our mobile configuration // applies our mobile configuration
void applyMobileConfiguration(); void applyMobileConfiguration();
void writeKeys(const QString &fileName, KSharedConfig::Ptr &config, const QMap<QString, QMap<QString, QVariant>> &settings, bool overwriteOnlyIfEmpty); void writeKeys(const QString &fileName,
KSharedConfig::Ptr &config,
const QMap<QString, QMap<QString, QVariant>> &settings,
bool overwriteOnlyIfEmpty,
bool saveSettings = true);
void loadKeys(const QString &fileName, KSharedConfig::Ptr &config, const QMap<QString, QMap<QString, QVariant>> &settings); void loadKeys(const QString &fileName, KSharedConfig::Ptr &config, const QMap<QString, QMap<QString, QVariant>> &settings);
void saveConfigSetting(const QString &fileName, const QString &group, const QString &key, const QVariant value); void saveConfigSetting(const QString &fileName, const QString &group, const QString &key, const QVariant value);
const QString loadSavedConfigSetting(KSharedConfig::Ptr &config, const QString &fileName, const QString &group, const QString &key, bool write = true); const QString loadSavedConfigSetting(KSharedConfig::Ptr &config, const QString &fileName, const QString &group, const QString &key, bool write = true);
@ -43,6 +47,7 @@ private:
KSharedConfig::Ptr m_appBlacklistConfig; KSharedConfig::Ptr m_appBlacklistConfig;
KSharedConfig::Ptr m_kdeglobalsConfig; KSharedConfig::Ptr m_kdeglobalsConfig;
KSharedConfig::Ptr m_ksmServerConfig; KSharedConfig::Ptr m_ksmServerConfig;
KSharedConfig::Ptr m_kwinrulesrcConfig;
KConfigWatcher::Ptr m_configWatcher; KConfigWatcher::Ptr m_configWatcher;
}; };

View file

@ -6,6 +6,11 @@ import QtQuick
import org.kde.kwin as KWinComponents import org.kde.kwin as KWinComponents
import org.kde.plasma.private.mobileshell.shellsettingsplugin as ShellSettings import org.kde.plasma.private.mobileshell.shellsettingsplugin as ShellSettings
// This script ensures that windows stay maximized in the shell.
//
// We eventually want to replace this with the window rules implementation,
// but it seems that window maximize rules still don't work for all cases just yet
// (ex. unmaximizing fullscreen window)
Loader { Loader {
id: root id: root
@ -23,8 +28,9 @@ Loader {
} }
if (ShellSettings.Settings.convergenceModeEnabled) { if (ShellSettings.Settings.convergenceModeEnabled) {
window.noBorder = false; return;
} else { }
if (!window.fullScreen) { if (!window.fullScreen) {
const output = window.output; const output = window.output;
const desktop = window.desktops[0]; // assume it's the first desktop that the window is on const desktop = window.desktops[0]; // assume it's the first desktop that the window is on
@ -39,15 +45,11 @@ Loader {
window.frameGeometry = maximizeRect; window.frameGeometry = maximizeRect;
} }
// turn off window decorations
window.noBorder = true;
if (!window.fullScreen) { if (!window.fullScreen) {
// run maximize after to ensure the state is maximized // run maximize after to ensure the state is maximized
window.setMaximize(true, true); window.setMaximize(true, true);
} }
} }
}
Connections { Connections {
target: currentWindow target: currentWindow