on xenial help sign in
wrap org.gnome.ScreenSaver
7560621Lukáš Tinkl
plugins/Unity/Session/dbusunitysessionservice.cpp+94−21
@@ -1,5 +1,5 @@
1/*
1/*
2− * Copyright (C) 2014 Canonical, Ltd.
2+ * Copyright (C) 2014, 2015 Canonical, Ltd.
3 *
3 *
4 * This program is free software: you can redistribute it and/or modify it under
4 * This program is free software: you can redistribute it and/or modify it under
5 * the terms of the GNU Lesser General Public License version 3, as published by
5 * the terms of the GNU Lesser General Public License version 3, as published by
@@ -12,6 +12,10 @@
12 *
12 *
13 * You should have received a copy of the GNU Lesser General Public License
13 * You should have received a copy of the GNU Lesser General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15+ *
16+ * Authors: Lukáš Tinkl <ltinkl@canonical.com>
17+ * Christopher Townsend <christopher.townsend@canonical.com>
18+ * Paul Liu <paul.liu@canonical.com>
15 */
19 */
16
20
17// local
21// local
@@ -26,18 +30,27 @@
26#include <QDebug>
30#include <QDebug>
27#include <QDBusPendingCall>
31#include <QDBusPendingCall>
28#include <QDBusReply>
32#include <QDBusReply>
33+#include <QElapsedTimer>
29
34
30#define LOGIN1_SERVICE QStringLiteral("org.freedesktop.login1")
35#define LOGIN1_SERVICE QStringLiteral("org.freedesktop.login1")
31#define LOGIN1_PATH QStringLiteral("/org/freedesktop/login1")
36#define LOGIN1_PATH QStringLiteral("/org/freedesktop/login1")
32#define LOGIN1_IFACE QStringLiteral("org.freedesktop.login1.Manager")
37#define LOGIN1_IFACE QStringLiteral("org.freedesktop.login1.Manager")
33#define LOGIN1_SESSION_IFACE QStringLiteral("org.freedesktop.login1.Session")
38#define LOGIN1_SESSION_IFACE QStringLiteral("org.freedesktop.login1.Session")
34
39
40+#define ACTIVE_KEY QStringLiteral("Active")
41+
35class DBusUnitySessionServicePrivate: public QObject
42class DBusUnitySessionServicePrivate: public QObject
36{
43{
44+ Q_OBJECT
37public:
45public:
38 QString logindSessionPath;
46 QString logindSessionPath;
47+ bool isActive = true;
48+ QElapsedTimer screensaverActiveTimer;
39
49
40− DBusUnitySessionServicePrivate(): QObject() { init(); }
50+ DBusUnitySessionServicePrivate(): QObject() {
51+ init();
52+ checkActive();
53+ }
41
54
42 void init()
55 void init()
43 {
56 {
@@ -51,7 +64,11 @@ public:
51 QDBusReply<QDBusObjectPath> reply = QDBusConnection::systemBus().asyncCall(msg);
64 QDBusReply<QDBusObjectPath> reply = QDBusConnection::systemBus().asyncCall(msg);
52 if (reply.isValid()) {
65 if (reply.isValid()) {
53 logindSessionPath = reply.value().path();
66 logindSessionPath = reply.value().path();
54− qDebug() << "session path" << logindSessionPath;
67+ //qDebug() << "session path" << logindSessionPath;
68+
69+ // start watching the Active property
70+ QDBusConnection::systemBus().connect(LOGIN1_SERVICE, logindSessionPath, "org.freedesktop.DBus.Properties", "PropertiesChanged",
71+ this, SLOT(onPropertiesChanged(QString,QVariantMap,QStringList)));
55 } else {
72 } else {
56 qWarning() << "Failed to get logind session path" << reply.error().message();
73 qWarning() << "Failed to get logind session path" << reply.error().message();
57 }
74 }
@@ -74,11 +91,11 @@ public:
74 QDBusConnection::systemBus().asyncCall(msg);
91 QDBusConnection::systemBus().asyncCall(msg);
75 }
92 }
76
93
77− bool isActive() const
94+ void checkActive()
78 {
95 {
79 if (logindSessionPath.isEmpty()) {
96 if (logindSessionPath.isEmpty()) {
80 qWarning() << "Invalid session path";
97 qWarning() << "Invalid session path";
81− return true; //assume active
98+ return;
82 }
99 }
83
100
84 QDBusMessage msg = QDBusMessage::createMethodCall(LOGIN1_SERVICE,
101 QDBusMessage msg = QDBusMessage::createMethodCall(LOGIN1_SERVICE,
@@ -86,17 +103,39 @@ public:
86 "org.freedesktop.DBus.Properties",
103 "org.freedesktop.DBus.Properties",
87 "Get");
104 "Get");
88 msg << LOGIN1_SESSION_IFACE;
105 msg << LOGIN1_SESSION_IFACE;
89− msg << QStringLiteral("Active");
106+ msg << ACTIVE_KEY;
90
107
91− QDBusReply<bool> reply = QDBusConnection::systemBus().asyncCall(msg);
108+ QDBusReply<QVariant> reply = QDBusConnection::systemBus().asyncCall(msg);
92 if (reply.isValid()) {
109 if (reply.isValid()) {
93− return reply;
110+ isActive = reply.value().toBool();
111+ qDebug() << "Session" << logindSessionPath << "is active:" << isActive;
94 } else {
112 } else {
95 qWarning() << "Failed to get Active property" << reply.error().message();
113 qWarning() << "Failed to get Active property" << reply.error().message();
96 }
114 }
115+ }
97
116
98− return true; // assume active
117+private Q_SLOTS:
118+ void onPropertiesChanged(const QString &iface, const QVariantMap &changedProps, const QStringList &invalidatedProps)
119+ {
120+ Q_UNUSED(iface)
121+
122+ if (changedProps.contains(ACTIVE_KEY)) {
123+ isActive = changedProps.value(ACTIVE_KEY).toBool();
124+ } else if (invalidatedProps.contains(ACTIVE_KEY)) {
125+ checkActive();
126+ }
127+
128+ Q_EMIT screensaverActiveChanged(!isActive);
129+
130+ if (isActive) {
131+ screensaverActiveTimer.invalidate();
132+ } else {
133+ screensaverActiveTimer.start();
134+ }
99 }
135 }
136+
137+Q_SIGNALS:
138+ void screensaverActiveChanged(bool active);
100};
139};
101
140
102Q_GLOBAL_STATIC(DBusUnitySessionServicePrivate, d)
141Q_GLOBAL_STATIC(DBusUnitySessionServicePrivate, d)
@@ -219,7 +258,7 @@ void DBusUnitySessionService::Lock()
219
258
220bool DBusUnitySessionService::IsLocked() const
259bool DBusUnitySessionService::IsLocked() const
221{
260{
222− return !d->isActive();
261+ return !d->isActive;
223}
262}
224
263
225void DBusUnitySessionService::RequestLogout()
264void DBusUnitySessionService::RequestLogout()
@@ -270,12 +309,8 @@ enum class Action : unsigned
270 NONE
309 NONE
271};
310};
272
311
273−DBusGnomeSessionManagerWrapper::DBusGnomeSessionManagerWrapper()
274− : UnityDBusObject("/org/gnome/SessionManager/EndSessionDialog", "com.canonical.Unity")
275−{
276−}
277
312
278−void DBusGnomeSessionManagerWrapper::performAsyncCall(const QString &method)
313+void performAsyncUnityCall(const QString &method)
279{
314{
280 const QDBusMessage msg = QDBusMessage::createMethodCall("com.canonical.Unity",
315 const QDBusMessage msg = QDBusMessage::createMethodCall("com.canonical.Unity",
281 "/com/canonical/Unity/Session",
316 "/com/canonical/Unity/Session",
@@ -284,29 +319,67 @@ void DBusGnomeSessionManagerWrapper::performAsyncCall(const QString &method)
284 QDBusConnection::sessionBus().asyncCall(msg);
319 QDBusConnection::sessionBus().asyncCall(msg);
285}
320}
286
321
322+DBusGnomeSessionManagerWrapper::DBusGnomeSessionManagerWrapper()
323+ : UnityDBusObject("/org/gnome/SessionManager/EndSessionDialog", "com.canonical.Unity")
324+{
325+}
326+
287void DBusGnomeSessionManagerWrapper::Open(const unsigned type, const unsigned arg_1, const unsigned max_wait, const QList<QDBusObjectPath> &inhibitors)
327void DBusGnomeSessionManagerWrapper::Open(const unsigned type, const unsigned arg_1, const unsigned max_wait, const QList<QDBusObjectPath> &inhibitors)
288{
328{
289 Q_UNUSED(arg_1);
329 Q_UNUSED(arg_1);
290 Q_UNUSED(max_wait);
330 Q_UNUSED(max_wait);
291 Q_UNUSED(inhibitors);
331 Q_UNUSED(inhibitors);
292
332
293− const Action action = (Action)type;
333+ switch (static_cast<Action>(type))
294−
295− switch (action)
296 {
334 {
297 case Action::LOGOUT:
335 case Action::LOGOUT:
298− performAsyncCall("RequestLogout");
336+ performAsyncUnityCall("RequestLogout");
299 break;
337 break;
300
338
301 case Action::REBOOT:
339 case Action::REBOOT:
302− performAsyncCall("RequestReboot");
340+ performAsyncUnityCall("RequestReboot");
303 break;
341 break;
304
342
305 case Action::SHUTDOWN:
343 case Action::SHUTDOWN:
306− performAsyncCall("RequestShutdown");
344+ performAsyncUnityCall("RequestShutdown");
307 break;
345 break;
308
346
309 default:
347 default:
310 break;
348 break;
311 }
349 }
312}
350}
351+
352+
353+DBusGnomeScreensaverWrapper::DBusGnomeScreensaverWrapper()
354+ : UnityDBusObject("/org/gnome/ScreenSaver", "org.gnome.ScreenSaver")
355+{
356+ connect(d, &DBusUnitySessionServicePrivate::screensaverActiveChanged, this, &DBusGnomeScreensaverWrapper::ActiveChanged);
357+}
358+
359+bool DBusGnomeScreensaverWrapper::GetActive() const
360+{
361+ return !d->isActive; // return whether the session is not active
362+}
363+
364+void DBusGnomeScreensaverWrapper::SetActive(bool lock)
365+{
366+ if (lock) {
367+ Lock();
368+ }
369+}
370+
371+void DBusGnomeScreensaverWrapper::Lock()
372+{
373+ performAsyncUnityCall("Lock");
374+}
375+
376+quint32 DBusGnomeScreensaverWrapper::GetActiveTime() const
377+{
378+ if (GetActive() && d->screensaverActiveTimer.isValid()) {
379+ return d->screensaverActiveTimer.elapsed() / 1000;
380+ }
381+
382+ return 0;
383+}
384+
385+#include "dbusunitysessionservice.moc"
plugins/Unity/Session/dbusunitysessionservice.h+35−3
@@ -1,5 +1,5 @@
1/*
1/*
2− * Copyright (C) 2014 Canonical, Ltd.
2+ * Copyright (C) 2014, 2015 Canonical, Ltd.
3 *
3 *
4 * This program is free software: you can redistribute it and/or modify it under
4 * This program is free software: you can redistribute it and/or modify it under
5 * the terms of the GNU Lesser General Public License version 3, as published by
5 * the terms of the GNU Lesser General Public License version 3, as published by
@@ -264,8 +264,40 @@ public:
264
264
265public Q_SLOTS:
265public Q_SLOTS:
266 Q_SCRIPTABLE void Open(const unsigned int type, const unsigned int arg_1, const unsigned int max_wait, const QList<QDBusObjectPath> &inhibitors);
266 Q_SCRIPTABLE void Open(const unsigned int type, const unsigned int arg_1, const unsigned int max_wait, const QList<QDBusObjectPath> &inhibitors);
267+};
268+
269+class DBusGnomeScreensaverWrapper: public UnityDBusObject
270+{
271+ Q_OBJECT
272+ Q_CLASSINFO("D-Bus Interface", "org.gnome.ScreenSaver")
273+
274+public:
275+ DBusGnomeScreensaverWrapper();
276+ ~DBusGnomeScreensaverWrapper() = default;
267
277
268−private:
278+public Q_SLOTS:
269− void performAsyncCall(const QString &method);
279+ /**
280+ * @return whether the session is currently locked (screensaver is on)
281+ */
282+ Q_SCRIPTABLE bool GetActive() const;
283+
284+ /**
285+ * Locks the session immediately if @p lock is true
286+ */
287+ Q_SCRIPTABLE void SetActive(bool lock);
288+
289+ /**
290+ * Locks the session immediately
291+ */
292+ Q_SCRIPTABLE void Lock();
293+
294+ /**
295+ * @return the number of seconds elapsed since the screensaver had been active
296+ */
297+ Q_SCRIPTABLE quint32 GetActiveTime() const;
298+
299+Q_SIGNALS:
300+ void ActiveChanged(bool active);
270};
301};
302+
271#endif // DBUSUNITYSESSIONSERVICE_H
303#endif // DBUSUNITYSESSIONSERVICE_H