lid behavior watcher to lock session #115
@@ -5,11 +5,12 @@ import QtQuick
|
|||||||
Scope {
|
Scope {
|
||||||
id: root
|
id: root
|
||||||
|
|
||||||
required property var lock
|
signal requestLock
|
||||||
|
|
||||||
Connections {
|
Connections {
|
||||||
function onLidClosing(): void {
|
function onStateChanged(): void {
|
||||||
root.lock.lock.locked = true;
|
if (LidWatcher.state === LidWatcher.Closed)
|
||||||
|
AramJonghu marked this conversation as resolved
Outdated
|
|||||||
|
root.requestLock();
|
||||||
}
|
}
|
||||||
|
|
||||||
target: LidWatcher
|
target: LidWatcher
|
||||||
|
|||||||
@@ -18,6 +18,9 @@ Scope {
|
|||||||
signal requestLock
|
signal requestLock
|
||||||
signal unlock
|
signal unlock
|
||||||
|
|
||||||
|
onRequestLock: lock.locked = true
|
||||||
|
onUnlock: lock.locked = false
|
||||||
|
|
||||||
LockSurface {
|
LockSurface {
|
||||||
id: lockSurface
|
id: lockSurface
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,8 @@
|
|||||||
#include "lidwatcher.hpp"
|
#include "lidwatcher.hpp"
|
||||||
|
|
||||||
#include <QtDBus/QDBusConnection>
|
#include <QtDBus/QDBusConnection>
|
||||||
|
#include <QtDBus/QDBusMessage>
|
||||||
|
#include <QtDBus/QDBusReply>
|
||||||
#include <QLoggingCategory>
|
#include <QLoggingCategory>
|
||||||
|
|
||||||
Q_LOGGING_CATEGORY(lcLidWatcher, "ZShell.lidwatcher", QtInfoMsg)
|
Q_LOGGING_CATEGORY(lcLidWatcher, "ZShell.lidwatcher", QtInfoMsg)
|
||||||
@@ -10,11 +12,12 @@ namespace ZShell {
|
|||||||
static constexpr auto kLogin1Service = "org.freedesktop.login1";
|
static constexpr auto kLogin1Service = "org.freedesktop.login1";
|
||||||
static constexpr auto kLogin1Path = "/org/freedesktop/login1";
|
static constexpr auto kLogin1Path = "/org/freedesktop/login1";
|
||||||
static constexpr auto kLogin1Interface = "org.freedesktop.login1.Manager";
|
static constexpr auto kLogin1Interface = "org.freedesktop.login1.Manager";
|
||||||
static constexpr auto kPrepareForSleep = "PrepareForSleep";
|
static constexpr auto kDBusPropertiesInterface = "org.freedesktop.DBus.Properties";
|
||||||
|
|
||||||
LidWatcher::LidWatcher(QObject* parent)
|
LidWatcher::LidWatcher(QObject* parent)
|
||||||
: QObject(parent)
|
: QObject(parent)
|
||||||
, m_available(false) {
|
, m_available(false)
|
||||||
|
, m_state(Opened) {
|
||||||
QDBusConnection bus = QDBusConnection::systemBus();
|
QDBusConnection bus = QDBusConnection::systemBus();
|
||||||
m_available = bus.isConnected();
|
m_available = bus.isConnected();
|
||||||
|
|
||||||
@@ -24,26 +27,48 @@ LidWatcher::LidWatcher(QObject* parent)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto ok = bus.connect(kLogin1Service, kLogin1Path, kLogin1Interface, kPrepareForSleep, this,
|
const auto ok = bus.connect(kLogin1Service, kLogin1Path, kDBusPropertiesInterface, "PropertiesChanged",
|
||||||
SLOT(onPrepareForSleep(bool)));
|
this, SLOT(onPropertiesChanged(QString,QVariantMap,QStringList)));
|
||||||
|
|
||||||
m_available = ok;
|
m_available = ok;
|
||||||
emit availableChanged();
|
emit availableChanged();
|
||||||
if (!m_available) {
|
if (!m_available) {
|
||||||
qCWarning(lcLidWatcher) << "login1 lid signal unavailable";
|
qCWarning(lcLidWatcher) << "login1 properties signal unavailable";
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
queryInitialState();
|
||||||
}
|
}
|
||||||
|
AramJonghu marked this conversation as resolved
Outdated
zach
commented
Doesn't this trigger only when the system is about to suspend/hibernate? There should be a way to query the lid state directly. Doesn't this trigger only when the system is about to suspend/hibernate? There should be a way to query the lid state directly.
AramJonghu
commented
Correct. And in retrospect, not every distro has defaults where the system suspends when laptop is on AC. The idea was that it should only trigger when the system suspends or hibernates to cover it more broadly for desktops (if wished). Could be a separate plugin or addition to current implementation if that is a wish separate from laptop lid behavior. Correct. And in retrospect, not every distro has defaults where the system suspends when laptop is on AC. The idea was that it should only trigger when the system suspends or hibernates to cover it more broadly for desktops (if wished). Could be a separate plugin or addition to current implementation if that is a wish separate from laptop lid behavior.
|
|||||||
|
|
||||||
bool LidWatcher::available() const {
|
bool LidWatcher::available() const {
|
||||||
return m_available;
|
return m_available;
|
||||||
}
|
}
|
||||||
|
|
||||||
void LidWatcher::onPrepareForSleep(bool goingDown) {
|
LidWatcher::LidState LidWatcher::state() const {
|
||||||
if (goingDown) {
|
return m_state;
|
||||||
emit lidClosing();
|
}
|
||||||
} else {
|
|
||||||
emit lidOpened();
|
void LidWatcher::queryInitialState() {
|
||||||
|
const auto msg = QDBusMessage::createMethodCall(
|
||||||
|
kLogin1Service, kLogin1Path,
|
||||||
|
kDBusPropertiesInterface, "Get");
|
||||||
|
msg << kLogin1Interface << "LidClosed";
|
||||||
|
const QDBusReply<QVariant> reply = QDBusConnection::systemBus().call(msg);
|
||||||
|
if (!reply.isValid()) {
|
||||||
|
qCWarning(lcLidWatcher) << "cannot query LidClosed:" << reply.error().message();
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
m_state = reply.value().toBool() ? Closed : Opened;
|
||||||
|
emit stateChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
void LidWatcher::onPropertiesChanged(const QString& interface, const QVariantMap& changed, const QStringList& /*invalidated*/) {
|
||||||
|
if (interface != kLogin1Interface)
|
||||||
|
return;
|
||||||
|
if (!changed.contains("LidClosed"))
|
||||||
|
return;
|
||||||
|
m_state = changed.value("LidClosed").toBool() ? Closed : Opened;
|
||||||
|
emit stateChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace ZShell
|
} // namespace ZShell
|
||||||
|
|||||||
@@ -1,6 +1,8 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <QObject>
|
#include <QObject>
|
||||||
|
#include <QStringList>
|
||||||
|
#include <QVariantMap>
|
||||||
#include <qqmlintegration.h>
|
#include <qqmlintegration.h>
|
||||||
|
|
||||||
namespace ZShell {
|
namespace ZShell {
|
||||||
@@ -11,22 +13,32 @@ class LidWatcher : public QObject {
|
|||||||
QML_SINGLETON
|
QML_SINGLETON
|
||||||
|
|
||||||
Q_PROPERTY(bool available READ available NOTIFY availableChanged)
|
Q_PROPERTY(bool available READ available NOTIFY availableChanged)
|
||||||
|
Q_PROPERTY(LidState state READ state NOTIFY stateChanged)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
enum LidState {
|
||||||
|
Opened,
|
||||||
|
Closed
|
||||||
|
};
|
||||||
|
Q_ENUM(LidState)
|
||||||
|
|
||||||
explicit LidWatcher(QObject* parent = nullptr);
|
explicit LidWatcher(QObject* parent = nullptr);
|
||||||
|
|
||||||
[[nodiscard]] bool available() const;
|
[[nodiscard]] bool available() const;
|
||||||
|
[[nodiscard]] LidState state() const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
void queryInitialState();
|
||||||
|
|
||||||
|
bool m_available;
|
||||||
|
LidState m_state = Opened;
|
||||||
|
|
||||||
|
AramJonghu marked this conversation as resolved
Outdated
zach
commented
`extracted()` is declared but never implemented in the `.cpp` file.
|
|||||||
private Q_SLOTS:
|
private Q_SLOTS:
|
||||||
void onPrepareForSleep(bool goingDown);
|
void onPropertiesChanged(const QString& interface, const QVariantMap& changed, const QStringList& invalidated);
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
void availableChanged();
|
void availableChanged();
|
||||||
void lidClosing();
|
void stateChanged();
|
||||||
void lidOpened();
|
|
||||||
|
|
||||||
private:
|
|
||||||
bool m_available;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace ZShell
|
} // namespace ZShell
|
||||||
|
|||||||
@@ -331,7 +331,7 @@ export const settingsIndex = [
|
|||||||
category: "lockscreen",
|
category: "lockscreen",
|
||||||
categoryName: "Lockscreen",
|
categoryName: "Lockscreen",
|
||||||
section: "Lockscreen",
|
section: "Lockscreen",
|
||||||
keywords: ["lid", "lcck", "watch", "session", "laptop"],
|
keywords: ["lid", "lock", "watch", "session", "laptop"],
|
||||||
|
AramJonghu marked this conversation as resolved
Outdated
zach
commented
Typo probably. Typo probably. `"lcck"` should be `"lock"`
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Blur amount",
|
name: "Blur amount",
|
||||||
|
|||||||
@@ -47,12 +47,12 @@ ShellRoot {
|
|||||||
Polkit {
|
Polkit {
|
||||||
}
|
}
|
||||||
|
|
||||||
LazyLoader {
|
LazyLoader {
|
||||||
activeAsync: Config.lock.lidWatch && Battery.isLaptop
|
activeAsync: Config.lock.lidWatch && Battery.isLaptop
|
||||||
component: LidService {
|
component: LidService {
|
||||||
lock: lock
|
onRequestLock: lock.requestLock()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
LazyLoader {
|
LazyLoader {
|
||||||
activeAsync: root.laptop
|
activeAsync: root.laptop
|
||||||
|
|||||||
Reference in New Issue
Block a user
You need to create a signal in the root
Scopeand call it here rather than setting the locked value directly.Is what I suggest, ties in nicely with a similar signal related to locking.