Merge lp:~nick-dedekind/unity8/lp1385331.led into lp:unity8

Proposed by Nick Dedekind on 2014-11-11
Status: Merged
Approved by: Albert Astals Cid on 2014-12-17
Approved revision: 1378
Merged at revision: 1534
Proposed branch: lp:~nick-dedekind/unity8/lp1385331.led
Merge into: lp:unity8
Diff against target: 2016 lines (+1124/-312)
35 files modified
debian/control (+3/-3)
plugins/Lights/Lights.cpp (+9/-24)
plugins/Unity/Indicators/CMakeLists.txt (+3/-1)
plugins/Unity/Indicators/Indicators.qmltypes (+18/-7)
plugins/Unity/Indicators/actionrootstate.cpp (+97/-0)
plugins/Unity/Indicators/actionrootstate.h (+55/-0)
plugins/Unity/Indicators/modelactionrootstate.cpp (+127/-0)
plugins/Unity/Indicators/modelactionrootstate.h (+61/-0)
plugins/Unity/Indicators/plugin.cpp (+4/-2)
plugins/Unity/Indicators/rootstateparser.cpp (+75/-142)
plugins/Unity/Indicators/rootstateparser.h (+20/-36)
qml/Greeter/Clock.qml (+1/-1)
qml/Panel/IndicatorItem.qml (+0/-8)
qml/Panel/Indicators/IndicatorBase.qml (+1/-1)
qml/Panel/Indicators/IndicatorsLight.qml (+19/-1)
qml/Panel/IndicatorsMenu.qml (+5/-0)
tests/mocks/CMakeLists.txt (+1/-0)
tests/mocks/Lights/CMakeLists.txt (+8/-0)
tests/mocks/Lights/Lights.cpp (+84/-0)
tests/mocks/Lights/Lights.h (+66/-0)
tests/mocks/Lights/Lights.qmltypes (+45/-0)
tests/mocks/Lights/plugin.cpp (+33/-0)
tests/mocks/Lights/plugin.h (+32/-0)
tests/mocks/Lights/qmldir (+3/-0)
tests/mocks/QMenuModel/CMakeLists.txt (+1/-0)
tests/mocks/QMenuModel/QDBusActionGroup.qml (+21/-68)
tests/mocks/QMenuModel/actiondata.h (+52/-0)
tests/mocks/QMenuModel/plugin.cpp (+10/-0)
tests/mocks/Unity/Indicators/ActionRootState.qml (+46/-0)
tests/mocks/Unity/Indicators/qmldir (+2/-1)
tests/plugins/Unity/Indicators/rootactionstatetest.cpp (+4/-4)
tests/qmltests/CMakeLists.txt (+1/-0)
tests/qmltests/Panel/Indicators/tst_IndicatorsLight.qml (+129/-0)
tests/qmltests/Panel/Indicators/tst_MenuItemFactory.qml (+52/-1)
tests/qmltests/Wizard/tst_Wizard.qml (+36/-12)
To merge this branch: bzr merge lp:~nick-dedekind/unity8/lp1385331.led
Reviewer Review Type Date Requested Status
PS Jenkins bot continuous-integration Needs Fixing on 2014-12-17
Albert Astals Cid (community) 2014-11-11 Approve on 2014-12-17
Review via email: mp+241417@code.launchpad.net

Commit Message

Unhook Lights interface from indicator widgets

Description of the Change

Unhook Lights interface from indicator widgets

 * Are there any related MPs required for this MP to build/function as expected? Please list.
https://code.launchpad.net/~nick-dedekind/qmenumodel/lp1385331.led/+merge/241422

 * Did you perform an exploratory manual test run of your code change and any related functionality?
Yes

 * Did you make sure that your branch does not contain spurious tags?
Yes

 * If you changed the packaging (debian), did you subscribe the ubuntu-unity team to this MP?
N/A

 * If you changed the UI, has there been a design review?
N/A

To post a comment you must log in.
1374. By Nick Dedekind on 2014-11-24

removed author

Albert Astals Cid (aacid) wrote :

Text conflict in debian/control
1 conflicts encountered.

1375. By Nick Dedekind on 2014-11-28

merged with trunk

Nick Dedekind (nick-dedekind) wrote :

> Text conflict in debian/control
> 1 conflicts encountered.

Fixed.

Albert Astals Cid (aacid) wrote :

Text conflict in debian/control
Text conflict in tests/mocks/CMakeLists.txt
Text conflict in tests/mocks/QMenuModel/QDBusActionGroup.qml
3 conflicts encountered.

review: Needs Fixing
1376. By Nick Dedekind on 2014-12-11

merged with trunk

1377. By Nick Dedekind on 2014-12-12

better lights init

Albert Astals Cid (aacid) wrote :

Is there an easy way to reproduce the problem this is fixing?

review: Needs Information
Nick Dedekind (nick-dedekind) wrote :

1) kill unity8 when the light is blinking (new message + screen off)
2) clear messages (I use a messaging test script to add the new messages)
3) when unity8 restarts light will remain be blinking

Albert Astals Cid (aacid) wrote :

/home/phablet/unity8-lp1385331.led/plugins/Unity/Indicators/modelactionrootstate.cpp: multiple new lines at end of file

review: Needs Fixing
Albert Astals Cid (aacid) wrote :

 * Start messages.py
 * Led blinks forever
 * Kill unity8 (restarts itself)
 * Led blinks just one time more

I guess it should be still blinking forever?

review: Needs Information
Nick Dedekind (nick-dedekind) wrote :

> * Start messages.py
> * Led blinks forever
> * Kill unity8 (restarts itself)
> * Led blinks just one time more
>
> I guess it should be still blinking forever?

hm. if the screen is off and there are messages, it should keep blinking. I'll have to check what's happening.

Nick Dedekind (nick-dedekind) wrote :

> > * Start messages.py
> > * Led blinks forever
> > * Kill unity8 (restarts itself)
> > * Led blinks just one time more
> >
> > I guess it should be still blinking forever?
>
> hm. if the screen is off and there are messages, it should keep blinking. I'll
> have to check what's happening.

Tested this and in my instance, this is because Powerd.status is coming up as "On" when unity8 is restarted from a kill (when the screen is off). :/
Needs some sorting out, but it's not related to this branch.

1378. By Nick Dedekind on 2014-12-17

removed whitespace

Nick Dedekind (nick-dedekind) wrote :

> /home/phablet/unity8-lp1385331.led/plugins/Unity/Indicators/modelactionrootsta
> te.cpp: multiple new lines at end of file

Fixed.

Albert Astals Cid (aacid) wrote :

 * Did you perform an exploratory manual test run of the code change and any related functionality?
Yes

 * Did CI run pass?
It needs a dependency

 * Did you make sure that the branch does not contain spurious tags?
Yes

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'debian/control'
2--- debian/control 2014-12-08 18:15:11 +0000
3+++ debian/control 2014-12-17 11:19:14 +0000
4@@ -22,7 +22,7 @@
5 libpam0g-dev,
6 libpay2-dev,
7 libpulse-dev,
8- libqmenumodel-dev (>= 0.2.8),
9+ libqmenumodel-dev (>= 0.2.9),
10 libqt5xmlpatterns5-dev,
11 libsystemsettings-dev,
12 libunity-api-dev (>= 7.94),
13@@ -61,7 +61,7 @@
14
15 Package: indicators-client
16 Architecture: amd64 armhf i386
17-Depends: qmenumodel-qml (>= 0.2.8),
18+Depends: qmenumodel-qml (>= 0.2.9),
19 qtdeclarative5-ubuntu-ui-toolkit-plugin (>= 1.1.1239) | qtdeclarative5-ubuntu-ui-toolkit-plugin-gles (>= 1.1.1239),
20 unity8 (= ${binary:Version}),
21 ${misc:Depends},
22@@ -85,7 +85,7 @@
23 Depends: gsettings-desktop-schemas,
24 libcap2-bin,
25 libglib2.0-bin,
26- qmenumodel-qml (>= 0.2.8),
27+ qmenumodel-qml (>= 0.2.9),
28 qml-module-qt-labs-folderlistmodel,
29 qml-module-qtquick-xmllistmodel,
30 qtdeclarative5-gsettings1.0,
31
32=== modified file 'plugins/Lights/Lights.cpp'
33--- plugins/Lights/Lights.cpp 2014-09-08 15:07:24 +0000
34+++ plugins/Lights/Lights.cpp 2014-12-17 11:19:14 +0000
35@@ -44,12 +44,20 @@
36
37 void Lights::setState(Lights::State newState)
38 {
39+ if (!init()) {
40+ qWarning() << "No lights device";
41+ return;
42+ }
43+
44 if (m_state != newState) {
45 if (newState == Lights::On) {
46 turnOn();
47 } else {
48 turnOff();
49 }
50+
51+ m_state = newState;
52+ Q_EMIT stateChanged(m_state);
53 }
54 }
55
56@@ -115,6 +123,7 @@
57 err = module->methods->open(module, LIGHT_ID_NOTIFICATIONS, &device);
58 if (err == 0) {
59 m_lightDevice = (light_device_t*)device;
60+ turnOff();
61 return true;
62 } else {
63 qWarning() << "Failed to access notification lights";
64@@ -127,15 +136,6 @@
65
66 void Lights::turnOn()
67 {
68- if (!init()) {
69- qWarning() << "No lights device";
70- return;
71- }
72-
73- if (m_state == Lights::On) {
74- return;
75- }
76-
77 // pulse
78 light_state_t state;
79 memset(&state, 0, sizeof(light_state_t));
80@@ -147,23 +147,11 @@
81
82 if (m_lightDevice->set_light(m_lightDevice, &state) != 0) {
83 qWarning() << "Failed to turn the light off";
84- } else {
85- m_state = Lights::On;
86- Q_EMIT stateChanged(m_state);
87 }
88 }
89
90 void Lights::turnOff()
91 {
92- if (!init()) {
93- qWarning() << "No lights device";
94- return;
95- }
96-
97- if (m_state == Lights::Off) {
98- return;
99- }
100-
101 light_state_t state;
102 memset(&state, 0, sizeof(light_state_t));
103 state.color = 0x00000000;
104@@ -174,8 +162,5 @@
105
106 if (m_lightDevice->set_light(m_lightDevice, &state) != 0) {
107 qWarning() << "Failed to turn the light off";
108- } else {
109- m_state = Lights::Off;
110- Q_EMIT stateChanged(m_state);
111 }
112 }
113
114=== modified file 'plugins/Unity/Indicators/CMakeLists.txt'
115--- plugins/Unity/Indicators/CMakeLists.txt 2014-10-03 10:53:02 +0000
116+++ plugins/Unity/Indicators/CMakeLists.txt 2014-12-17 11:19:14 +0000
117@@ -16,14 +16,16 @@
118 )
119
120 set(IndicatorsQML_SOURCES
121+ actionrootstate.cpp
122 indicator.cpp
123 indicators.h
124 indicatorsmanager.cpp
125 indicatorsmodel.cpp
126 menucontentactivator.cpp
127+ modelactionrootstate.cpp
128 modelprinter.cpp
129 plugin.cpp
130- rootactionstate.cpp
131+ rootstateparser.cpp
132 sharedunitymenumodel.cpp
133 unitymenumodelcache.cpp
134 unitymenumodelstack.cpp
135
136=== modified file 'plugins/Unity/Indicators/Indicators.qmltypes'
137--- plugins/Unity/Indicators/Indicators.qmltypes 2014-10-07 10:58:39 +0000
138+++ plugins/Unity/Indicators/Indicators.qmltypes 2014-12-17 11:19:14 +0000
139@@ -8,6 +8,14 @@
140
141 Module {
142 Component {
143+ name: "ActionRootState"
144+ prototype: "RootStateObject"
145+ exports: ["Unity.Indicators/ActionRootState 0.1"]
146+ exportMetaObjectRevisions: [0]
147+ Property { name: "actionGroup"; type: "QDBusActionGroup"; isPointer: true }
148+ Property { name: "actionName"; type: "string" }
149+ }
150+ Component {
151 name: "ActionState"
152 prototype: "QObject"
153 exports: ["Unity.Indicators/ActionState 0.1"]
154@@ -23,7 +31,6 @@
155 }
156 }
157 }
158- Component { name: "ActionStateParser"; prototype: "QObject" }
159 Component {
160 name: "FlatMenuProxyModelRole"
161 prototype: "QObject"
162@@ -147,6 +154,14 @@
163 Property { name: "active"; type: "bool"; isReadonly: true }
164 }
165 Component {
166+ name: "ModelActionRootState"
167+ prototype: "RootStateObject"
168+ exports: ["Unity.Indicators/ModelActionRootState 0.1"]
169+ exportMetaObjectRevisions: [0]
170+ Property { name: "menu"; type: "UnityMenuModel"; isPointer: true }
171+ Signal { name: "indexChanged" }
172+ }
173+ Component {
174 name: "ModelPrinter"
175 prototype: "QObject"
176 exports: ["Unity.Indicators/ModelPrinter 0.1"]
177@@ -192,11 +207,8 @@
178 }
179 Component { name: "QIdentityProxyModel"; prototype: "QAbstractProxyModel" }
180 Component {
181- name: "RootActionState"
182- prototype: "ActionStateParser"
183- exports: ["Unity.Indicators/RootActionState 0.1"]
184- exportMetaObjectRevisions: [0]
185- Property { name: "menu"; type: "UnityMenuModel"; isPointer: true }
186+ name: "RootStateObject"
187+ prototype: "QObject"
188 Property { name: "valid"; type: "bool"; isReadonly: true }
189 Property { name: "title"; type: "string"; isReadonly: true }
190 Property { name: "leftLabel"; type: "string"; isReadonly: true }
191@@ -205,7 +217,6 @@
192 Property { name: "accessibleName"; type: "string"; isReadonly: true }
193 Property { name: "visible"; type: "bool"; isReadonly: true }
194 Signal { name: "updated" }
195- Signal { name: "indexChanged" }
196 }
197 Component {
198 name: "SharedUnityMenuModel"
199
200=== added file 'plugins/Unity/Indicators/actionrootstate.cpp'
201--- plugins/Unity/Indicators/actionrootstate.cpp 1970-01-01 00:00:00 +0000
202+++ plugins/Unity/Indicators/actionrootstate.cpp 2014-12-17 11:19:14 +0000
203@@ -0,0 +1,97 @@
204+/*
205+ * Copyright 2014 Canonical Ltd.
206+ *
207+ * This program is free software; you can redistribute it and/or modify
208+ * it under the terms of the GNU Lesser General Public License as published by
209+ * the Free Software Foundation; version 3.
210+ *
211+ * This program is distributed in the hope that it will be useful,
212+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
213+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
214+ * GNU Lesser General Public License for more details.
215+ *
216+ * You should have received a copy of the GNU Lesser General Public License
217+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
218+ */
219+
220+#include "actionrootstate.h"
221+
222+#include <qdbusactiongroup.h>
223+#include <QDebug>
224+
225+ActionRootState::ActionRootState(QObject *parent)
226+ : RootStateObject(parent)
227+ , m_actionGroup(nullptr)
228+{
229+}
230+
231+QDBusActionGroup *ActionRootState::actionGroup() const
232+{
233+ return m_actionGroup;
234+}
235+
236+void ActionRootState::setActionGroup(QDBusActionGroup *actionGroup)
237+{
238+ if (m_actionGroup != actionGroup) {
239+ bool wasValid = valid();
240+
241+ if (m_actionGroup) {
242+ disconnect(m_actionGroup, 0, this, 0);
243+ }
244+ m_actionGroup = actionGroup;
245+
246+ if (m_actionGroup) {
247+ connect(m_actionGroup, &QDBusActionGroup::statusChanged, this, [&](bool) { updateActionState(); });
248+ connect(m_actionGroup, &QDBusActionGroup::actionAppear, this, [&](const QString&) { updateActionState(); });
249+ connect(m_actionGroup, &QDBusActionGroup::actionVanish, this, [&](const QString&) { updateActionState(); });
250+ connect(m_actionGroup, &QDBusActionGroup::actionStateChanged, this, [&](QVariant) { updateActionState(); });
251+
252+ connect(m_actionGroup, &QObject::destroyed, this, [&](QObject*) { updateActionState(); });
253+ }
254+ updateActionState();
255+ Q_EMIT actionGroupChanged();
256+
257+ if (wasValid != valid()) Q_EMIT validChanged();
258+ }
259+}
260+
261+QString ActionRootState::actionName() const
262+{
263+ return m_actionName;
264+}
265+
266+void ActionRootState::setActionName(const QString &actionName)
267+{
268+ if (m_actionName != actionName) {
269+ bool wasValid = valid();
270+
271+ m_actionName = actionName;
272+ updateActionState();
273+
274+ Q_EMIT actionNameChanged();
275+
276+ if (wasValid != valid()) Q_EMIT validChanged();
277+ }
278+}
279+
280+bool ActionRootState::valid() const
281+{
282+ return m_actionGroup && m_actionGroup->status() == DBusEnums::Connected &&
283+ !m_actionName.isEmpty() && m_actionGroup->hasAction(m_actionName);
284+}
285+
286+void ActionRootState::updateActionState()
287+{
288+ if (valid()) {
289+ ActionStateParser* oldParser = m_actionGroup->actionStateParser();
290+ m_actionGroup->setActionStateParser(&m_parser);
291+
292+ QVariantMap state = m_actionGroup->actionState(m_actionName).toMap();
293+
294+ m_actionGroup->setActionStateParser(oldParser);
295+
296+ setCurrentState(state);
297+ } else {
298+ setCurrentState(QVariantMap());
299+ }
300+}
301
302=== added file 'plugins/Unity/Indicators/actionrootstate.h'
303--- plugins/Unity/Indicators/actionrootstate.h 1970-01-01 00:00:00 +0000
304+++ plugins/Unity/Indicators/actionrootstate.h 2014-12-17 11:19:14 +0000
305@@ -0,0 +1,55 @@
306+/*
307+ * Copyright 2014 Canonical Ltd.
308+ *
309+ * This program is free software; you can redistribute it and/or modify
310+ * it under the terms of the GNU Lesser General Public License as published by
311+ * the Free Software Foundation; version 3.
312+ *
313+ * This program is distributed in the hope that it will be useful,
314+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
315+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
316+ * GNU Lesser General Public License for more details.
317+ *
318+ * You should have received a copy of the GNU Lesser General Public License
319+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
320+ */
321+
322+#ifndef ACTIONROOTSTATE_H
323+#define ACTIONROOTSTATE_H
324+
325+#include "unityindicatorsglobal.h"
326+
327+#include "rootstateparser.h"
328+
329+class QDBusActionGroup;
330+
331+class UNITYINDICATORS_EXPORT ActionRootState : public RootStateObject
332+{
333+ Q_OBJECT
334+ Q_PROPERTY(QDBusActionGroup* actionGroup READ actionGroup WRITE setActionGroup NOTIFY actionGroupChanged)
335+ Q_PROPERTY(QString actionName READ actionName WRITE setActionName NOTIFY actionNameChanged)
336+
337+public:
338+ ActionRootState(QObject *parent = 0);
339+
340+ QDBusActionGroup *actionGroup() const;
341+ void setActionGroup(QDBusActionGroup *actionGroup);
342+
343+ QString actionName() const;
344+ void setActionName(const QString& actionName);
345+
346+ bool valid() const override;
347+
348+Q_SIGNALS:
349+ void actionGroupChanged();
350+ void actionNameChanged();
351+
352+private Q_SLOTS:
353+ void updateActionState();
354+
355+private:
356+ QDBusActionGroup* m_actionGroup;
357+ QString m_actionName;
358+};
359+
360+#endif // ACTIONROOTSTATE_H
361
362=== added file 'plugins/Unity/Indicators/modelactionrootstate.cpp'
363--- plugins/Unity/Indicators/modelactionrootstate.cpp 1970-01-01 00:00:00 +0000
364+++ plugins/Unity/Indicators/modelactionrootstate.cpp 2014-12-17 11:19:14 +0000
365@@ -0,0 +1,127 @@
366+/*
367+ * Copyright 2013 Canonical Ltd.
368+ *
369+ * This program is free software; you can redistribute it and/or modify
370+ * it under the terms of the GNU Lesser General Public License as published by
371+ * the Free Software Foundation; version 3.
372+ *
373+ * This program is distributed in the hope that it will be useful,
374+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
375+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
376+ * GNU Lesser General Public License for more details.
377+ *
378+ * You should have received a copy of the GNU Lesser General Public License
379+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
380+ *
381+ * Authors:
382+ * Nick Dedekind <nick.dedekind@canonical.com>
383+ */
384+
385+#include "modelactionrootstate.h"
386+#include "indicators.h"
387+
388+#include <unitymenumodel.h>
389+#include <QVariant>
390+#include <QIcon>
391+
392+extern "C" {
393+#include <glib.h>
394+#include <gio/gio.h>
395+}
396+
397+ModelActionRootState::ModelActionRootState(QObject *parent)
398+ : RootStateObject(parent),
399+ m_menu(nullptr)
400+{
401+}
402+
403+ModelActionRootState::~ModelActionRootState()
404+{
405+}
406+
407+UnityMenuModel* ModelActionRootState::menu() const
408+{
409+ return m_menu;
410+}
411+
412+void ModelActionRootState::setMenu(UnityMenuModel* menu)
413+{
414+ if (m_menu != menu) {
415+ bool wasValid = valid();
416+
417+ if (m_menu) {
418+ m_menu->disconnect(this);
419+ }
420+ m_menu = menu;
421+
422+ if (m_menu) {
423+ connect(m_menu, SIGNAL(rowsInserted(const QModelIndex&, int, int)), SLOT(onModelRowsAdded(const QModelIndex&, int, int)));
424+ connect(m_menu, SIGNAL(rowsRemoved(const QModelIndex&, int, int)), SLOT(onModelRowsRemoved(const QModelIndex&, int, int)));
425+ connect(m_menu, SIGNAL(dataChanged(const QModelIndex&, const QModelIndex&, const QVector<int>&)), SLOT(onModelDataChanged(const QModelIndex&, const QModelIndex&, const QVector<int>&)));
426+
427+ connect(m_menu, SIGNAL(destroyed()), SLOT(reset()));
428+ }
429+ updateActionState();
430+ Q_EMIT menuChanged();
431+
432+ if (wasValid != valid())
433+ Q_EMIT validChanged();
434+ }
435+}
436+
437+bool ModelActionRootState::valid() const
438+{
439+ return m_menu && m_menu->rowCount() > 0;
440+}
441+
442+void ModelActionRootState::onModelRowsAdded(const QModelIndex& parent, int start, int end)
443+{
444+ Q_UNUSED(parent);
445+ if (start == 0 && end >= 0) {
446+ updateActionState();
447+ }
448+}
449+
450+void ModelActionRootState::onModelRowsRemoved(const QModelIndex& parent, int start, int end)
451+{
452+ Q_UNUSED(parent);
453+ if (start == 0 && end >= 0) {
454+ updateActionState();
455+ }
456+}
457+
458+void ModelActionRootState::onModelDataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>& roles)
459+{
460+ Q_UNUSED(roles);
461+ if (!topLeft.isValid() || !bottomRight.isValid()) {
462+ return;
463+ }
464+
465+ if (topLeft.row() <= 0 && bottomRight.row() >= 0) {
466+ updateActionState();
467+ }
468+}
469+
470+void ModelActionRootState::reset()
471+{
472+ m_menu = nullptr;
473+
474+ Q_EMIT menuChanged();
475+ setCurrentState(QVariantMap());
476+}
477+
478+void ModelActionRootState::updateActionState()
479+{
480+ if (m_menu && m_menu->rowCount() > 0) {
481+ ActionStateParser* oldParser = m_menu->actionStateParser();
482+ m_menu->setActionStateParser(&m_parser);
483+
484+ QVariantMap state = m_menu->get(0, "actionState").toMap();
485+
486+ m_menu->setActionStateParser(oldParser);
487+
488+ setCurrentState(state);
489+ } else {
490+ setCurrentState(QVariantMap());
491+ }
492+}
493
494=== added file 'plugins/Unity/Indicators/modelactionrootstate.h'
495--- plugins/Unity/Indicators/modelactionrootstate.h 1970-01-01 00:00:00 +0000
496+++ plugins/Unity/Indicators/modelactionrootstate.h 2014-12-17 11:19:14 +0000
497@@ -0,0 +1,61 @@
498+/*
499+ * Copyright 2013 Canonical Ltd.
500+ *
501+ * This program is free software; you can redistribute it and/or modify
502+ * it under the terms of the GNU Lesser General Public License as published by
503+ * the Free Software Foundation; version 3.
504+ *
505+ * This program is distributed in the hope that it will be useful,
506+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
507+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
508+ * GNU Lesser General Public License for more details.
509+ *
510+ * You should have received a copy of the GNU Lesser General Public License
511+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
512+ *
513+ * Authors:
514+ * Nick Dedekind <nick.dedekind@canonical.com>
515+ */
516+
517+#ifndef MODELACTIONROOTSTATE_H
518+#define MODELACTIONROOTSTATE_H
519+
520+#include "unityindicatorsglobal.h"
521+
522+#include "rootstateparser.h"
523+
524+class UnityMenuModel;
525+
526+class UNITYINDICATORS_EXPORT ModelActionRootState : public RootStateObject
527+{
528+ Q_OBJECT
529+ Q_PROPERTY(UnityMenuModel* menu READ menu WRITE setMenu NOTIFY menuChanged)
530+public:
531+ ModelActionRootState(QObject *parent = 0);
532+ virtual ~ModelActionRootState();
533+
534+ UnityMenuModel* menu() const;
535+ void setMenu(UnityMenuModel* menu);
536+
537+ int index() const;
538+ void setIndex(int index);
539+
540+ bool valid() const override;
541+
542+Q_SIGNALS:
543+ void menuChanged();
544+ void indexChanged();
545+
546+private Q_SLOTS:
547+ void onModelRowsAdded(const QModelIndex& parent, int start, int end);
548+ void onModelRowsRemoved(const QModelIndex& parent, int start, int end);
549+ void onModelDataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>&);
550+ void reset();
551+
552+private:
553+ void updateActionState();
554+
555+ UnityMenuModel* m_menu;
556+};
557+
558+#endif // MODELACTIONROOTSTATE_H
559
560=== modified file 'plugins/Unity/Indicators/plugin.cpp'
561--- plugins/Unity/Indicators/plugin.cpp 2014-10-07 10:28:59 +0000
562+++ plugins/Unity/Indicators/plugin.cpp 2014-12-17 11:19:14 +0000
563@@ -24,12 +24,13 @@
564 #include "plugin.h"
565
566 // local
567+#include "actionrootstate.h"
568 #include "indicators.h"
569 #include "indicatorsmanager.h"
570 #include "indicatorsmodel.h"
571 #include "menucontentactivator.h"
572+#include "modelactionrootstate.h"
573 #include "modelprinter.h"
574-#include "rootactionstate.h"
575 #include "sharedunitymenumodel.h"
576 #include "unitymenumodelcache.h"
577 #include "unitymenumodelstack.h"
578@@ -51,7 +52,8 @@
579 qmlRegisterType<IndicatorsModel>(uri, 0, 1, "IndicatorsModel");
580 qmlRegisterType<MenuContentActivator>(uri, 0, 1, "MenuContentActivator");
581 qmlRegisterType<UnityMenuModelStack>(uri, 0, 1, "UnityMenuModelStack");
582- qmlRegisterType<RootActionState>(uri, 0, 1, "RootActionState");
583+ qmlRegisterType<ModelActionRootState>(uri, 0, 1, "ModelActionRootState");
584+ qmlRegisterType<ActionRootState>(uri, 0, 1, "ActionRootState");
585 qmlRegisterType<ModelPrinter>(uri, 0, 1, "ModelPrinter");
586 qmlRegisterType<VisibleIndicatorsModel>(uri, 0, 1, "VisibleIndicatorsModel");
587 qmlRegisterType<SharedUnityMenuModel>(uri, 0, 1, "SharedUnityMenuModel");
588
589=== renamed file 'plugins/Unity/Indicators/rootactionstate.cpp' => 'plugins/Unity/Indicators/rootstateparser.cpp'
590--- plugins/Unity/Indicators/rootactionstate.cpp 2014-10-20 12:38:16 +0000
591+++ plugins/Unity/Indicators/rootstateparser.cpp 2014-12-17 11:19:14 +0000
592@@ -12,155 +12,18 @@
593 *
594 * You should have received a copy of the GNU Lesser General Public License
595 * along with this program. If not, see <http://www.gnu.org/licenses/>.
596- *
597- * Authors:
598- * Nick Dedekind <nick.dedekind@canonical.com>
599 */
600
601-#include "rootactionstate.h"
602-#include "indicators.h"
603-
604-#include <unitymenumodel.h>
605-#include <QVariant>
606-#include <QIcon>
607+#include "rootstateparser.h"
608
609 extern "C" {
610 #include <glib.h>
611 #include <gio/gio.h>
612 }
613
614-RootActionState::RootActionState(QObject *parent)
615- : ActionStateParser(parent),
616- m_menu(nullptr)
617-{
618-}
619-
620-RootActionState::~RootActionState()
621-{
622-}
623-
624-UnityMenuModel* RootActionState::menu() const
625-{
626- return m_menu;
627-}
628-
629-void RootActionState::setMenu(UnityMenuModel* menu)
630-{
631- if (m_menu != menu) {
632- if (m_menu) {
633- m_menu->disconnect(this);
634- }
635- m_menu = menu;
636-
637- if (m_menu) {
638- connect(m_menu, SIGNAL(rowsInserted(const QModelIndex&, int, int)), SLOT(onModelRowsAdded(const QModelIndex&, int, int)));
639- connect(m_menu, SIGNAL(rowsRemoved(const QModelIndex&, int, int)), SLOT(onModelRowsRemoved(const QModelIndex&, int, int)));
640- connect(m_menu, SIGNAL(dataChanged(const QModelIndex&, const QModelIndex&, const QVector<int>&)), SLOT(onModelDataChanged(const QModelIndex&, const QModelIndex&, const QVector<int>&)));
641-
642- connect(m_menu, SIGNAL(destroyed()), SLOT(reset()));
643- }
644- updateActionState();
645- Q_EMIT menuChanged();
646- }
647-}
648-
649-void RootActionState::onModelRowsAdded(const QModelIndex& parent, int start, int end)
650-{
651- Q_UNUSED(parent);
652- if (start == 0 && end >= 0) {
653- updateActionState();
654- }
655-}
656-
657-void RootActionState::onModelRowsRemoved(const QModelIndex& parent, int start, int end)
658-{
659- Q_UNUSED(parent);
660- if (start == 0 && end >= 0) {
661- updateActionState();
662- }
663-}
664-
665-void RootActionState::onModelDataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>& roles)
666-{
667- Q_UNUSED(roles);
668- if (!topLeft.isValid() || !bottomRight.isValid()) {
669- return;
670- }
671-
672- if (topLeft.row() <= 0 && bottomRight.row() >= 0) {
673- updateActionState();
674- }
675-}
676-
677-void RootActionState::reset()
678-{
679- m_cachedState.clear();
680- m_menu = nullptr;
681-
682- Q_EMIT menuChanged();
683- Q_EMIT updated();
684-}
685-
686-void RootActionState::updateActionState()
687-{
688- if (m_menu && m_menu->rowCount() > 0) {
689- ActionStateParser* oldParser = m_menu->actionStateParser();
690- m_menu->setActionStateParser(this);
691-
692- m_cachedState = m_menu->get(0, "actionState").toMap();
693-
694- m_menu->setActionStateParser(oldParser);
695- } else {
696- m_cachedState.clear();
697- }
698- Q_EMIT updated();
699-}
700-
701-bool RootActionState::isValid() const
702-{
703- return m_menu && m_menu->rowCount() > 0;
704-}
705-
706-QString RootActionState::title() const
707-{
708- if (!isValid()) return QString();
709-
710- return m_cachedState.value("title", QVariant::fromValue(QString())).toString();
711-}
712-
713-QString RootActionState::leftLabel() const
714-{
715- if (!isValid()) return QString();
716-
717- return m_cachedState.value("pre-label", QVariant::fromValue(QString())).toString();
718-}
719-
720-QString RootActionState::rightLabel() const
721-{
722- if (!isValid()) return QString();
723-
724- return m_cachedState.value("label", QVariant::fromValue(QString())).toString();
725-}
726-
727-QStringList RootActionState::icons() const
728-{
729- if (!isValid()) return QStringList();
730-
731- return m_cachedState.value("icons", QVariant::fromValue(QStringList())).toStringList();
732-}
733-
734-QString RootActionState::accessibleName() const
735-{
736- if (!isValid()) return QString();
737-
738- return m_cachedState.value("accessible-desc", QVariant::fromValue(QString())).toString();
739-}
740-
741-bool RootActionState::indicatorVisible() const
742-{
743- if (!isValid()) return false;
744-
745- return m_cachedState.value("visible", QVariant::fromValue(true)).toBool();
746+RootStateParser::RootStateParser(QObject* parent)
747+ : ActionStateParser(parent)
748+{
749 }
750
751 static QString iconUri(GIcon *icon)
752@@ -209,7 +72,7 @@
753 return uri;
754 }
755
756-QVariant RootActionState::toQVariant(GVariant* state) const
757+QVariant RootStateParser::toQVariant(GVariant* state) const
758 {
759 if (!state) {
760 return QVariant();
761@@ -296,3 +159,73 @@
762 }
763 return ActionStateParser::toQVariant(state);
764 }
765+
766+
767+RootStateObject::RootStateObject(QObject* parent)
768+ : QObject(parent)
769+{
770+}
771+
772+QString RootStateObject::title() const
773+{
774+ if (!valid()) return QString();
775+
776+ return m_currentState.value("title", QVariant::fromValue(QString())).toString();
777+}
778+
779+QString RootStateObject::leftLabel() const
780+{
781+ if (!valid()) return QString();
782+
783+ return m_currentState.value("pre-label", QVariant::fromValue(QString())).toString();
784+}
785+
786+QString RootStateObject::rightLabel() const
787+{
788+ if (!valid()) return QString();
789+
790+ return m_currentState.value("label", QVariant::fromValue(QString())).toString();
791+}
792+
793+QStringList RootStateObject::icons() const
794+{
795+ if (!valid()) return QStringList();
796+
797+ return m_currentState.value("icons", QVariant::fromValue(QStringList())).toStringList();
798+}
799+
800+QString RootStateObject::accessibleName() const
801+{
802+ if (!valid()) return QString();
803+
804+ return m_currentState.value("accessible-desc", QVariant::fromValue(QString())).toString();
805+}
806+
807+bool RootStateObject::indicatorVisible() const
808+{
809+ if (!valid()) return false;
810+
811+ return m_currentState.value("visible", QVariant::fromValue(true)).toBool();
812+}
813+
814+void RootStateObject::setCurrentState(const QVariantMap& newState)
815+{
816+ QString oldTitle = title();
817+ QString oldLeftLabel = leftLabel();
818+ QString oldRightLabel = rightLabel();
819+ QStringList oldIcons = icons();
820+ QString oldAccessibleName = accessibleName();
821+ bool oldIndicatorVisible = indicatorVisible();
822+
823+ if (m_currentState != newState) {
824+ m_currentState = newState;
825+ Q_EMIT updated();
826+
827+ if (oldTitle != title()) Q_EMIT titleChanged();
828+ if (oldLeftLabel != leftLabel()) Q_EMIT leftLabelChanged();
829+ if (oldRightLabel != rightLabel()) Q_EMIT rightLabelChanged();
830+ if (oldIcons != icons()) Q_EMIT iconsChanged();
831+ if (oldAccessibleName != accessibleName()) Q_EMIT accessibleNameChanged();
832+ if (oldIndicatorVisible != indicatorVisible()) Q_EMIT indicatorVisibleChanged();
833+ }
834+}
835
836=== renamed file 'plugins/Unity/Indicators/rootactionstate.h' => 'plugins/Unity/Indicators/rootstateparser.h'
837--- plugins/Unity/Indicators/rootactionstate.h 2014-10-20 12:38:16 +0000
838+++ plugins/Unity/Indicators/rootstateparser.h 2014-12-17 11:19:14 +0000
839@@ -12,26 +12,27 @@
840 *
841 * You should have received a copy of the GNU Lesser General Public License
842 * along with this program. If not, see <http://www.gnu.org/licenses/>.
843- *
844- * Authors:
845- * Nick Dedekind <nick.dedekind@canonical.com>
846 */
847
848-#ifndef ROOTACTIONSTATE_H
849-#define ROOTACTIONSTATE_H
850+#ifndef ROOTSTATEPARSER_H
851+#define ROOTSTATEPARSER_H
852
853 #include "unityindicatorsglobal.h"
854
855 #include <actionstateparser.h>
856
857-class UnityMenuModel;
858+class UNITYINDICATORS_EXPORT RootStateParser : public ActionStateParser
859+{
860+public:
861+ RootStateParser(QObject* parent = nullptr);
862+ virtual QVariant toQVariant(GVariant* state) const override;
863+};
864
865-class UNITYINDICATORS_EXPORT RootActionState : public ActionStateParser
866+class UNITYINDICATORS_EXPORT RootStateObject : public QObject
867 {
868 Q_OBJECT
869- Q_PROPERTY(UnityMenuModel* menu READ menu WRITE setMenu NOTIFY menuChanged)
870
871- Q_PROPERTY(bool valid READ isValid NOTIFY validChanged)
872+ Q_PROPERTY(bool valid READ valid NOTIFY validChanged)
873 Q_PROPERTY(QString title READ title NOTIFY titleChanged)
874 Q_PROPERTY(QString leftLabel READ leftLabel NOTIFY leftLabelChanged)
875 Q_PROPERTY(QString rightLabel READ rightLabel NOTIFY rightLabelChanged)
876@@ -39,16 +40,10 @@
877 Q_PROPERTY(QString accessibleName READ accessibleName NOTIFY accessibleNameChanged)
878 Q_PROPERTY(bool indicatorVisible READ indicatorVisible NOTIFY indicatorVisibleChanged)
879 public:
880- RootActionState(QObject *parent = 0);
881- virtual ~RootActionState();
882-
883- UnityMenuModel* menu() const;
884- void setMenu(UnityMenuModel* menu);
885-
886- int index() const;
887- void setIndex(int index);
888-
889- bool isValid() const;
890+ RootStateObject(QObject* parent = 0);
891+
892+ virtual bool valid() const = 0;
893+
894 QString title() const;
895 QString leftLabel() const;
896 QString rightLabel() const;
897@@ -56,15 +51,12 @@
898 QString accessibleName() const;
899 bool indicatorVisible() const;
900
901- // from ActionStateParser
902- virtual QVariant toQVariant(GVariant* state) const override;
903+ QVariantMap currentState() const { return m_currentState; }
904+ void setCurrentState(const QVariantMap& currentState);
905
906 Q_SIGNALS:
907 void updated();
908
909- void menuChanged();
910- void indexChanged();
911-
912 void validChanged();
913 void titleChanged();
914 void leftLabelChanged();
915@@ -73,17 +65,9 @@
916 void accessibleNameChanged();
917 void indicatorVisibleChanged();
918
919-private Q_SLOTS:
920- void onModelRowsAdded(const QModelIndex& parent, int start, int end);
921- void onModelRowsRemoved(const QModelIndex& parent, int start, int end);
922- void onModelDataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>&);
923- void reset();
924-
925-private:
926- void updateActionState();
927-
928- UnityMenuModel* m_menu;
929- QVariantMap m_cachedState;
930+protected:
931+ RootStateParser m_parser;
932+ QVariantMap m_currentState;
933 };
934
935-#endif // ROOTACTIONSTATE_H
936+#endif // ROOTSTATEPARSER_H
937
938=== modified file 'qml/Greeter/Clock.qml'
939--- qml/Greeter/Clock.qml 2014-11-21 19:23:57 +0000
940+++ qml/Greeter/Clock.qml 2014-12-17 11:19:14 +0000
941@@ -53,7 +53,7 @@
942 menuObjectPath: clock.visible ? "/com/canonical/indicator/datetime/phone" : ""
943 }
944
945- Indicators.RootActionState {
946+ Indicators.ModelActionRootState {
947 menu: timeModel.model
948 onUpdated: {
949 if (timeLabel.text != rightLabel) {
950
951=== modified file 'qml/Panel/IndicatorItem.qml'
952--- qml/Panel/IndicatorItem.qml 2014-11-21 15:01:59 +0000
953+++ qml/Panel/IndicatorItem.qml 2014-12-17 11:19:14 +0000
954@@ -45,14 +45,6 @@
955 onClicked: parent.clicked()
956 }
957
958- // FIXME: For now we will enable led indicator support only for messaging indicator
959- // in the future we should export a led API insted of doing that,
960- Loader {
961- id: indicatorLed
962- // only load source Component if the icons contains the new message icon
963- source: (root.icons && (String(root.icons).indexOf("indicator-messages-new") != -1)) ? Qt.resolvedUrl("Indicators/IndicatorsLight.qml") : ""
964- }
965-
966 Item {
967 id: mainItems
968 anchors.centerIn: parent
969
970=== modified file 'qml/Panel/Indicators/IndicatorBase.qml'
971--- qml/Panel/Indicators/IndicatorBase.qml 2014-10-17 14:55:35 +0000
972+++ qml/Panel/Indicators/IndicatorBase.qml 2014-12-17 11:19:14 +0000
973@@ -40,7 +40,7 @@
974 menuObjectPath: indicatorItem.menuObjectPath
975 }
976
977- RootActionState {
978+ ModelActionRootState {
979 id: rootAction
980 menu: menuModel ? menuModel : null
981 onUpdated: indicatorItem.rootActionStateChanged()
982
983=== modified file 'qml/Panel/Indicators/IndicatorsLight.qml'
984--- qml/Panel/Indicators/IndicatorsLight.qml 2014-08-05 14:31:12 +0000
985+++ qml/Panel/Indicators/IndicatorsLight.qml 2014-12-17 11:19:14 +0000
986@@ -20,16 +20,34 @@
987 import QtQuick 2.0
988 import Powerd 0.1
989 import Lights 0.1
990+import QMenuModel 0.1 as QMenuModel
991+import Unity.Indicators 0.1 as Indicators
992
993 QtObject {
994 id: root
995
996+ property var _actionGroup: QMenuModel.QDBusActionGroup {
997+ busType: 1
998+ busName: "com.canonical.indicator.messages"
999+ objectPath: "/com/canonical/indicator/messages"
1000+ }
1001+
1002+ property var _rootState: Indicators.ActionRootState {
1003+ actionGroup: _actionGroup
1004+ actionName: "messages"
1005+ Component.onCompleted: actionGroup.start()
1006+
1007+ property bool hasMessages: valid && (String(icons).indexOf("indicator-messages-new") != -1)
1008+ }
1009+
1010 Component.onDestruction: Lights.state = Lights.Off
1011
1012 // QtObject does not have children
1013 property var _binding: Binding {
1014 target: Lights
1015 property: "state"
1016- value: (Powerd.status === Powerd.Off) ? Lights.On : Lights.Off
1017+ value: {
1018+ return (Powerd.status === Powerd.Off && _rootState.hasMessages) ? Lights.On : Lights.Off
1019+ }
1020 }
1021 }
1022
1023=== modified file 'qml/Panel/IndicatorsMenu.qml'
1024--- qml/Panel/IndicatorsMenu.qml 2014-10-21 19:32:03 +0000
1025+++ qml/Panel/IndicatorsMenu.qml 2014-12-17 11:19:14 +0000
1026@@ -18,6 +18,7 @@
1027 import Ubuntu.Components 1.1
1028 import Ubuntu.Gestures 0.1
1029 import "../Components"
1030+import "Indicators"
1031
1032 Showable {
1033 id: root
1034@@ -60,6 +61,10 @@
1035 onUnitProgressChanged: d.updateState()
1036 clip: root.partiallyOpened
1037
1038+ IndicatorsLight {
1039+ id: indicatorLights
1040+ }
1041+
1042 // eater
1043 MouseArea {
1044 anchors.fill: parent
1045
1046=== modified file 'tests/mocks/CMakeLists.txt'
1047--- tests/mocks/CMakeLists.txt 2014-11-21 19:28:16 +0000
1048+++ tests/mocks/CMakeLists.txt 2014-12-17 11:19:14 +0000
1049@@ -32,6 +32,7 @@
1050 add_subdirectory(GSettings.1.0)
1051 add_subdirectory(libusermetrics)
1052 add_subdirectory(LightDM)
1053+add_subdirectory(Lights)
1054 add_subdirectory(MeeGo)
1055 add_subdirectory(Powerd)
1056 add_subdirectory(QMenuModel)
1057
1058=== added directory 'tests/mocks/Lights'
1059=== added file 'tests/mocks/Lights/CMakeLists.txt'
1060--- tests/mocks/Lights/CMakeLists.txt 1970-01-01 00:00:00 +0000
1061+++ tests/mocks/Lights/CMakeLists.txt 2014-12-17 11:19:14 +0000
1062@@ -0,0 +1,8 @@
1063+add_library(MockLights-qml MODULE
1064+ plugin.cpp
1065+ Lights.cpp
1066+ )
1067+
1068+qt5_use_modules(MockLights-qml Qml Gui)
1069+
1070+add_unity8_mock(Lights 0.1 Lights TARGETS MockLights-qml)
1071
1072=== added file 'tests/mocks/Lights/Lights.cpp'
1073--- tests/mocks/Lights/Lights.cpp 1970-01-01 00:00:00 +0000
1074+++ tests/mocks/Lights/Lights.cpp 2014-12-17 11:19:14 +0000
1075@@ -0,0 +1,84 @@
1076+/*
1077+ * Copyright (C) 2014 Canonical, Ltd.
1078+ *
1079+ * This program is free software; you can redistribute it and/or modify
1080+ * it under the terms of the GNU General Public License as published by
1081+ * the Free Software Foundation; version 3.
1082+ *
1083+ * This program is distributed in the hope that it will be useful,
1084+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1085+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1086+ * GNU General Public License for more details.
1087+ *
1088+ * You should have received a copy of the GNU General Public License
1089+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1090+ */
1091+
1092+#include "Lights.h"
1093+
1094+#include <QDebug>
1095+
1096+Lights::Lights(QObject* parent)
1097+ : QObject(parent),
1098+ m_color("blue"),
1099+ m_state(Lights::Off),
1100+ m_onMs(1000),
1101+ m_offMs(3000)
1102+{
1103+}
1104+
1105+Lights::~Lights()
1106+{
1107+}
1108+
1109+void Lights::setState(Lights::State newState)
1110+{
1111+ if (m_state != newState) {
1112+ m_state = newState;
1113+ Q_EMIT stateChanged(m_state);
1114+ }
1115+}
1116+
1117+Lights::State Lights::state() const
1118+{
1119+ return m_state;
1120+}
1121+
1122+void Lights::setColor(const QColor &color)
1123+{
1124+ if (m_color != color) {
1125+ m_color = color;
1126+ Q_EMIT colorChanged(m_color);
1127+ }
1128+}
1129+
1130+QColor Lights::color() const
1131+{
1132+ return m_color;
1133+}
1134+
1135+int Lights::onMillisec() const
1136+{
1137+ return m_onMs;
1138+}
1139+
1140+void Lights::setOnMillisec(int onMs)
1141+{
1142+ if (m_onMs != onMs) {
1143+ m_onMs = onMs;
1144+ Q_EMIT onMillisecChanged(m_onMs);
1145+ }
1146+}
1147+
1148+int Lights::offMillisec() const
1149+{
1150+ return m_offMs;
1151+}
1152+
1153+void Lights::setOffMillisec(int offMs)
1154+{
1155+ if (m_offMs != offMs) {
1156+ m_offMs = offMs;
1157+ Q_EMIT offMillisecChanged(m_offMs);
1158+ }
1159+}
1160
1161=== added file 'tests/mocks/Lights/Lights.h'
1162--- tests/mocks/Lights/Lights.h 1970-01-01 00:00:00 +0000
1163+++ tests/mocks/Lights/Lights.h 2014-12-17 11:19:14 +0000
1164@@ -0,0 +1,66 @@
1165+/*
1166+ * Copyright (C) 2014 Canonical, Ltd.
1167+ *
1168+ * This program is free software; you can redistribute it and/or modify
1169+ * it under the terms of the GNU General Public License as published by
1170+ * the Free Software Foundation; version 3.
1171+ *
1172+ * This program is distributed in the hope that it will be useful,
1173+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1174+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1175+ * GNU General Public License for more details.
1176+ *
1177+ * You should have received a copy of the GNU General Public License
1178+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1179+ */
1180+
1181+#ifndef UNITY_MOCK_LIGHTS_H
1182+#define UNITY_MOCK_LIGHTS_H
1183+
1184+#include <QtCore/QObject>
1185+#include <QtGui/QColor>
1186+
1187+class Lights: public QObject
1188+{
1189+ Q_OBJECT
1190+ Q_ENUMS(State)
1191+ Q_PROPERTY(State state READ state WRITE setState NOTIFY stateChanged)
1192+ Q_PROPERTY(QColor color READ color WRITE setColor NOTIFY colorChanged)
1193+ Q_PROPERTY(int onMillisec READ onMillisec WRITE setOnMillisec NOTIFY onMillisecChanged)
1194+ Q_PROPERTY(int offMillisec READ offMillisec WRITE setOffMillisec NOTIFY offMillisecChanged)
1195+
1196+public:
1197+ enum State {
1198+ Off,
1199+ On,
1200+ };
1201+
1202+ explicit Lights(QObject *parent = 0);
1203+ ~Lights();
1204+
1205+ void setState(State newState);
1206+ State state() const;
1207+
1208+ void setColor(const QColor &color);
1209+ QColor color() const;
1210+
1211+ int onMillisec() const;
1212+ void setOnMillisec(int onMs);
1213+
1214+ int offMillisec() const;
1215+ void setOffMillisec(int offMs);
1216+
1217+Q_SIGNALS:
1218+ void stateChanged(State newState);
1219+ void colorChanged(const QColor &color);
1220+ void onMillisecChanged(int onMs);
1221+ void offMillisecChanged(int offMs);
1222+
1223+private:
1224+ QColor m_color;
1225+ State m_state;
1226+ int m_onMs;
1227+ int m_offMs;
1228+};
1229+
1230+#endif
1231
1232=== added file 'tests/mocks/Lights/Lights.qmltypes'
1233--- tests/mocks/Lights/Lights.qmltypes 1970-01-01 00:00:00 +0000
1234+++ tests/mocks/Lights/Lights.qmltypes 2014-12-17 11:19:14 +0000
1235@@ -0,0 +1,45 @@
1236+import QtQuick.tooling 1.1
1237+
1238+// This file describes the plugin-supplied types contained in the library.
1239+// It is used for QML tooling purposes only.
1240+//
1241+// This file was auto-generated by:
1242+// 'qmlplugindump -notrelocatable Lights 0.1 tests/mocks'
1243+
1244+Module {
1245+ Component {
1246+ name: "Lights"
1247+ prototype: "QObject"
1248+ exports: ["Lights/Lights 0.1"]
1249+ isCreatable: false
1250+ isSingleton: true
1251+ exportMetaObjectRevisions: [0]
1252+ Enum {
1253+ name: "State"
1254+ values: {
1255+ "Off": 0,
1256+ "On": 1
1257+ }
1258+ }
1259+ Property { name: "state"; type: "State" }
1260+ Property { name: "color"; type: "QColor" }
1261+ Property { name: "onMillisec"; type: "int" }
1262+ Property { name: "offMillisec"; type: "int" }
1263+ Signal {
1264+ name: "stateChanged"
1265+ Parameter { name: "newState"; type: "State" }
1266+ }
1267+ Signal {
1268+ name: "colorChanged"
1269+ Parameter { name: "color"; type: "QColor" }
1270+ }
1271+ Signal {
1272+ name: "onMillisecChanged"
1273+ Parameter { name: "onMs"; type: "int" }
1274+ }
1275+ Signal {
1276+ name: "offMillisecChanged"
1277+ Parameter { name: "offMs"; type: "int" }
1278+ }
1279+ }
1280+}
1281
1282=== added file 'tests/mocks/Lights/plugin.cpp'
1283--- tests/mocks/Lights/plugin.cpp 1970-01-01 00:00:00 +0000
1284+++ tests/mocks/Lights/plugin.cpp 2014-12-17 11:19:14 +0000
1285@@ -0,0 +1,33 @@
1286+/*
1287+ * Copyright (C) 2012,2013 Canonical, Ltd.
1288+ *
1289+ * This program is free software; you can redistribute it and/or modify
1290+ * it under the terms of the GNU General Public License as published by
1291+ * the Free Software Foundation; version 3.
1292+ *
1293+ * This program is distributed in the hope that it will be useful,
1294+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1295+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1296+ * GNU General Public License for more details.
1297+ *
1298+ * You should have received a copy of the GNU General Public License
1299+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1300+ */
1301+
1302+#include "plugin.h"
1303+#include "Lights.h"
1304+
1305+#include <QtQml/qqml.h>
1306+
1307+static QObject *lights_provider(QQmlEngine *engine, QJSEngine *scriptEngine)
1308+{
1309+ Q_UNUSED(engine)
1310+ Q_UNUSED(scriptEngine)
1311+ return new Lights();
1312+}
1313+
1314+void PowerdPlugin::registerTypes(const char *uri)
1315+{
1316+ Q_ASSERT(uri == QLatin1String("Lights"));
1317+ qmlRegisterSingletonType<Lights>(uri, 0, 1, "Lights", lights_provider);
1318+}
1319
1320=== added file 'tests/mocks/Lights/plugin.h'
1321--- tests/mocks/Lights/plugin.h 1970-01-01 00:00:00 +0000
1322+++ tests/mocks/Lights/plugin.h 2014-12-17 11:19:14 +0000
1323@@ -0,0 +1,32 @@
1324+/*
1325+ * Copyright (C) 2012,2013 Canonical, Ltd.
1326+ *
1327+ * This program is free software; you can redistribute it and/or modify
1328+ * it under the terms of the GNU General Public License as published by
1329+ * the Free Software Foundation; version 3.
1330+ *
1331+ * This program is distributed in the hope that it will be useful,
1332+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1333+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1334+ * GNU General Public License for more details.
1335+ *
1336+ * You should have received a copy of the GNU General Public License
1337+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1338+ */
1339+
1340+#ifndef MOCK_POWER_PLUGIN_H
1341+#define MOCK_POWER_PLUGIN_H
1342+
1343+#include <QtQml/QQmlEngine>
1344+#include <QtQml/QQmlExtensionPlugin>
1345+
1346+class PowerdPlugin : public QQmlExtensionPlugin
1347+{
1348+ Q_OBJECT
1349+ Q_PLUGIN_METADATA(IID "org.qt-project.Qt.QQmlExtensionInterface")
1350+
1351+public:
1352+ void registerTypes(const char *uri);
1353+};
1354+
1355+#endif
1356
1357=== added file 'tests/mocks/Lights/qmldir'
1358--- tests/mocks/Lights/qmldir 1970-01-01 00:00:00 +0000
1359+++ tests/mocks/Lights/qmldir 2014-12-17 11:19:14 +0000
1360@@ -0,0 +1,3 @@
1361+module Lights
1362+plugin MockLights-qml
1363+typeinfo Lights.qmltypes
1364
1365=== modified file 'tests/mocks/QMenuModel/CMakeLists.txt'
1366--- tests/mocks/QMenuModel/CMakeLists.txt 2014-11-14 17:47:00 +0000
1367+++ tests/mocks/QMenuModel/CMakeLists.txt 2014-12-17 11:19:14 +0000
1368@@ -4,6 +4,7 @@
1369 )
1370
1371 set(QMenuModelQml_SOURCES
1372+ actiondata.h
1373 actionstateparser.cpp
1374 dbus-enums.h
1375 plugin.cpp
1376
1377=== modified file 'tests/mocks/QMenuModel/QDBusActionGroup.qml'
1378--- tests/mocks/QMenuModel/QDBusActionGroup.qml 2014-11-21 19:28:16 +0000
1379+++ tests/mocks/QMenuModel/QDBusActionGroup.qml 2014-12-17 11:19:14 +0000
1380@@ -19,81 +19,34 @@
1381
1382 import QtQuick 2.0
1383 import Ubuntu.Settings.Menus 0.1 as Menus
1384+import QMenuModel 0.1
1385
1386 QtObject {
1387 id: actionGroup
1388 property int busType
1389 property string busName
1390 property string objectPath
1391+ property var actions: ActionData ? ActionData.data : undefined
1392+
1393+ signal dataChanged
1394+
1395 function start() {}
1396+
1397 function action(actionName) {
1398- switch (actionName) {
1399- case "transfer-state.queued":
1400- return {
1401- 'valid': true,
1402- 'state': {
1403- 'state': Menus.TransferState.Queued,
1404- 'percent': 0.0
1405- }
1406- }
1407- case "transfer-state.running":
1408- return {
1409- 'valid': true,
1410- 'state': {
1411- 'state': Menus.TransferState.Running,
1412- 'seconds-left': 100,
1413- 'percent': 0.1
1414- }
1415- }
1416- case "transfer-state.paused":
1417- return {
1418- 'valid': true,
1419- 'state': {
1420- 'state': Menus.TransferState.Paused,
1421- 'seconds-left': 100,
1422- 'percent': 0.5
1423- }
1424- }
1425- case "transfer-state.cancelled":
1426- return {
1427- 'valid': true,
1428- 'state': {
1429- 'state': Menus.TransferState.Canceled,
1430- 'percent': 0.4
1431- }
1432- }
1433- case "transfer-state.finished": return {
1434- 'valid': true,
1435- 'state': {
1436- 'state': Menus.TransferState.Finished,
1437- 'seconds-left': 0,
1438- 'percent': 1.0
1439- }
1440- }
1441- case "transfer-state.error":
1442- return {
1443- 'valid': true,
1444- 'state': {
1445- 'state': Menus.TransferState.Error,
1446- 'seconds-left': 100,
1447- 'percent': 0.0
1448- }
1449- }
1450- case "gps-detection-enabled":
1451- case "location-detection-enabled":
1452- return Qt.createQmlObject("
1453-import QtQuick 2.3
1454-QtObject {
1455- property bool valid: true
1456- property bool state: false
1457- function activate() {
1458- state = !state;
1459- }
1460-}", actionGroup);
1461- default:
1462- break;
1463- }
1464-
1465- return null;
1466+ return Qt.createQmlObject("
1467+ import QtQuick 2.3
1468+ import QMenuModel 0.1
1469+
1470+ QtObject {
1471+ signal activated
1472+
1473+ property string actionName: \"" + actionName + "\"
1474+ property bool valid: ActionData.data[actionName] != undefined ? ActionData.data[actionName].valid : false
1475+ property var state: ActionData.data[actionName] != undefined ? ActionData.data[actionName].state : undefined
1476+
1477+ function activate() {
1478+ activated();
1479+ }
1480+ }", actionGroup);
1481 }
1482 }
1483
1484=== added file 'tests/mocks/QMenuModel/actiondata.h'
1485--- tests/mocks/QMenuModel/actiondata.h 1970-01-01 00:00:00 +0000
1486+++ tests/mocks/QMenuModel/actiondata.h 2014-12-17 11:19:14 +0000
1487@@ -0,0 +1,52 @@
1488+/*
1489+ * Copyright (C) 2013 Canonical, Ltd.
1490+ *
1491+ * This program is free software; you can redistribute it and/or modify
1492+ * it under the terms of the GNU General Public License as published by
1493+ * the Free Software Foundation; version 3.
1494+ *
1495+ * This program is distributed in the hope that it will be useful,
1496+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1497+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1498+ * GNU General Public License for more details.
1499+ *
1500+ * You should have received a copy of the GNU General Public License
1501+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1502+ *
1503+ * Authors: Nick Dedekind <nick.dedekind@canonical.com>
1504+ */
1505+
1506+#ifndef ACTIONDATA_H
1507+#define ACTIONDATA_H
1508+
1509+#include <QObject>
1510+#include <QVariant>
1511+
1512+typedef struct _GVariant GVariant;
1513+
1514+class Q_DECL_EXPORT ActionData : public QObject
1515+{
1516+ Q_OBJECT
1517+ Q_PROPERTY(QVariant data READ data WRITE setData NOTIFY dataChanged)
1518+public:
1519+ ActionData(QObject* parent = 0)
1520+ : QObject(parent)
1521+ {}
1522+
1523+ QVariant data() const { return m_data; }
1524+ void setData(const QVariant& data)
1525+ {
1526+ if (m_data != data) {
1527+ m_data = data;
1528+ Q_EMIT dataChanged();
1529+ }
1530+ }
1531+
1532+Q_SIGNALS:
1533+ void dataChanged();
1534+
1535+private:
1536+ QVariant m_data;
1537+};
1538+
1539+#endif // ACTIONDATA_H
1540
1541=== modified file 'tests/mocks/QMenuModel/plugin.cpp'
1542--- tests/mocks/QMenuModel/plugin.cpp 2014-11-14 17:47:00 +0000
1543+++ tests/mocks/QMenuModel/plugin.cpp 2014-12-17 11:19:14 +0000
1544@@ -18,11 +18,19 @@
1545
1546 #include "plugin.h"
1547 #include "unitymenumodel.h"
1548+#include "actiondata.h"
1549 #include "actionstateparser.h"
1550 #include "dbus-enums.h"
1551
1552 #include <QtQml/qqml.h>
1553
1554+static QObject* actionDataSingleton(QQmlEngine* engine, QJSEngine* scriptEngine)
1555+{
1556+ Q_UNUSED(engine);
1557+ Q_UNUSED(scriptEngine);
1558+ return new ActionData;
1559+}
1560+
1561 void QMenuModelPlugin::registerTypes(const char *uri)
1562 {
1563 Q_ASSERT(uri == QLatin1String("QMenuModel"));
1564@@ -30,4 +38,6 @@
1565 "DBus is only a namespace");
1566 qmlRegisterType<UnityMenuModel>(uri, 0, 1, "UnityMenuModel");
1567 qmlRegisterType<ActionStateParser>(uri, 0, 1, "ActionStateParser");
1568+
1569+ qmlRegisterSingletonType<ActionData>(uri, 0, 1, "ActionData", actionDataSingleton);
1570 }
1571
1572=== added file 'tests/mocks/Unity/Indicators/ActionRootState.qml'
1573--- tests/mocks/Unity/Indicators/ActionRootState.qml 1970-01-01 00:00:00 +0000
1574+++ tests/mocks/Unity/Indicators/ActionRootState.qml 2014-12-17 11:19:14 +0000
1575@@ -0,0 +1,46 @@
1576+/*
1577+ * Copyright 2013 Canonical Ltd.
1578+ *
1579+ * This program is free software; you can redistribute it and/or modify
1580+ * it under the terms of the GNU Lesser General Public License as published by
1581+ * the Free Software Foundation; version 3.
1582+ *
1583+ * This program is distributed in the hope that it will be useful,
1584+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1585+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1586+ * GNU Lesser General Public License for more details.
1587+ *
1588+ * You should have received a copy of the GNU Lesser General Public License
1589+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1590+ *
1591+ * Authors:
1592+ * Nick Dedekind <nick.dedekind@canonical.com>
1593+ */
1594+
1595+import QtQuick 2.0
1596+
1597+QtObject {
1598+ property var actionGroup
1599+ property var actionName
1600+
1601+ property var action: actionGroup ? actionGroup.actions[actionName] : undefined
1602+ property var state: action && action.hasOwnProperty("state") ? action.state : undefined
1603+
1604+ property bool valid: action && action.hasOwnProperty("valid") ? action.valid : false
1605+ property string title: state && state.hasOwnProperty("title") ? state["title"] : ""
1606+ property string leftLabel: state && state.hasOwnProperty("pre-label") ? state["pre-label"] : ""
1607+ property string rightLabel: state && state.hasOwnProperty("label") ? state["label"] : ""
1608+ property var icons: state && state.hasOwnProperty("icons") ? state["icons"] : []
1609+ property string accessibleName: state && state.hasOwnProperty("accessible-desc") ? state["accessible-desc"] : ""
1610+ property bool visible: state && state.hasOwnProperty("visible") ? state["visible"] : true
1611+
1612+ signal updated
1613+
1614+ onValidChanged: updated()
1615+ onTitleChanged: updated()
1616+ onLeftLabelChanged: updated()
1617+ onRightLabelChanged: updated()
1618+ onIconsChanged: updated()
1619+ onAccessibleNameChanged: updated()
1620+ onVisibleChanged: updated()
1621+}
1622
1623=== renamed file 'tests/mocks/Unity/Indicators/RootActionState.qml' => 'tests/mocks/Unity/Indicators/ModelActionRootState.qml'
1624=== modified file 'tests/mocks/Unity/Indicators/qmldir'
1625--- tests/mocks/Unity/Indicators/qmldir 2014-10-07 10:28:59 +0000
1626+++ tests/mocks/Unity/Indicators/qmldir 2014-12-17 11:19:14 +0000
1627@@ -2,5 +2,6 @@
1628 plugin IndicatorsFakeQml
1629 typeinfo Indicators.qmltypes
1630
1631+ActionRootState 0.1 ActionRootState.qml
1632 IndicatorsModel 0.1 IndicatorsModel.qml
1633-RootActionState 0.1 RootActionState.qml
1634+ModelActionRootState 0.1 ModelActionRootState.qml
1635
1636=== modified file 'tests/plugins/Unity/Indicators/rootactionstatetest.cpp'
1637--- tests/plugins/Unity/Indicators/rootactionstatetest.cpp 2014-08-26 08:14:44 +0000
1638+++ tests/plugins/Unity/Indicators/rootactionstatetest.cpp 2014-12-17 11:19:14 +0000
1639@@ -17,7 +17,7 @@
1640 * Nick Dedekind <nick.dedekind@canonical.com>
1641 */
1642
1643-#include "rootactionstate.h"
1644+#include "modelactionrootstate.h"
1645
1646 #include <unitymenumodel.h>
1647 #include <QtTest>
1648@@ -32,7 +32,7 @@
1649 {
1650 UnityMenuModel* menuModel = new UnityMenuModel();
1651 ActionStateParser* originalParser = menuModel->actionStateParser();
1652- RootActionState* rootState = new RootActionState();
1653+ ModelActionRootState* rootState = new ModelActionRootState();
1654
1655 rootState->setMenu(menuModel);
1656
1657@@ -44,7 +44,7 @@
1658 void testDeleteUnityMenuModel()
1659 {
1660 UnityMenuModel* menuModel = new UnityMenuModel();
1661- RootActionState* rootState = new RootActionState();
1662+ ModelActionRootState* rootState = new ModelActionRootState();
1663
1664 rootState->setMenu(menuModel);
1665
1666@@ -77,7 +77,7 @@
1667
1668 GVariant* params = g_variant_builder_end (&builderParams);
1669
1670- RootActionState rootState;
1671+ RootStateParser rootState;
1672 QVariant result = rootState.toQVariant(params);
1673 g_variant_unref(params);
1674
1675
1676=== modified file 'tests/qmltests/CMakeLists.txt'
1677--- tests/qmltests/CMakeLists.txt 2014-12-08 13:39:01 +0000
1678+++ tests/qmltests/CMakeLists.txt 2014-12-17 11:19:14 +0000
1679@@ -79,6 +79,7 @@
1680 add_qml_test(Panel MenuContent ENVIRONMENT "LD_LIBRARY_PATH=${CMAKE_BINARY_DIR}/tests/mocks/QMenuModel")
1681 add_qml_test(Panel Panel ENVIRONMENT "LD_LIBRARY_PATH=${CMAKE_BINARY_DIR}/tests/mocks/QMenuModel")
1682 add_qml_test(Panel SearchIndicator)
1683+add_qml_test(Panel/Indicators IndicatorsLight ENVIRONMENT "LD_LIBRARY_PATH=${CMAKE_BINARY_DIR}/tests/mocks/QMenuModel")
1684 # These MenuItemFactory tests need the test/mocks/ to come before plugins/
1685 add_qml_test(Panel/Indicators MenuItemFactory IMPORT_PATHS ${CMAKE_BINARY_DIR}/tests/mocks ${qmltest_DEFAULT_IMPORT_PATHS})
1686 add_qml_test(Panel/Indicators MessageMenuItemFactory IMPORT_PATHS ${CMAKE_BINARY_DIR}/tests/mocks ${qmltest_DEFAULT_IMPORT_PATHS})
1687
1688=== added file 'tests/qmltests/Panel/Indicators/tst_IndicatorsLight.qml'
1689--- tests/qmltests/Panel/Indicators/tst_IndicatorsLight.qml 1970-01-01 00:00:00 +0000
1690+++ tests/qmltests/Panel/Indicators/tst_IndicatorsLight.qml 2014-12-17 11:19:14 +0000
1691@@ -0,0 +1,129 @@
1692+/*
1693+ * Copyright 2014 Canonical Ltd.
1694+ *
1695+ * This program is free software; you can redistribute it and/or modify
1696+ * it under the terms of the GNU General Public License as published by
1697+ * the Free Software Foundation; version 3.
1698+ *
1699+ * This program is distributed in the hope that it will be useful,
1700+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1701+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1702+ * GNU General Public License for more details.
1703+ *
1704+ * You should have received a copy of the GNU General Public License
1705+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1706+ */
1707+
1708+import QtQuick 2.0
1709+import QtQuick.Layouts 1.1
1710+import Unity.Test 0.1 as UT
1711+import Unity.Indicators 0.1 as Indicators
1712+import Ubuntu.Components 1.1
1713+import Powerd 0.1
1714+import Lights 0.1
1715+import QMenuModel 0.1
1716+import "../../../../qml/Panel/Indicators"
1717+
1718+Item {
1719+ id: root
1720+ width: units.gu(30)
1721+ height: units.gu(30)
1722+
1723+ property var newMessage: {
1724+ "messages" : {
1725+ 'valid': true,
1726+ 'state': {
1727+ 'icons': [ 'indicator-messages-new' ]
1728+ }
1729+ }
1730+ };
1731+ property var noNewMessage: {
1732+ "messages" : {
1733+ 'valid': true,
1734+ 'state': {
1735+ 'icons': [ 'indicator-messages' ]
1736+ }
1737+ }
1738+ };
1739+
1740+ Component {
1741+ id: light
1742+ IndicatorsLight {}
1743+ }
1744+
1745+ Loader {
1746+ id: loader
1747+ sourceComponent: light
1748+ }
1749+
1750+ Component.onCompleted: {
1751+ ActionData.data = newMessage;
1752+ Powerd.status = Powerd.On
1753+ }
1754+
1755+ RowLayout {
1756+ anchors.fill: parent
1757+ anchors.margins: units.gu(1)
1758+
1759+ Item {
1760+ Layout.fillWidth: true
1761+ Layout.fillHeight: true
1762+
1763+ Rectangle {
1764+ width: units.gu(4)
1765+ height: width
1766+ radius: width / 2
1767+ anchors.centerIn: parent
1768+
1769+ color: Lights.state === Lights.On ? Lights.color : "transparent"
1770+
1771+ border.color: "black"
1772+ border.width: 1
1773+ }
1774+ }
1775+
1776+ ColumnLayout {
1777+ Layout.alignment: Qt.AlignTop
1778+ Layout.fillWidth: false
1779+ Layout.preferredWidth: units.gu(15)
1780+
1781+ Button {
1782+ Layout.fillWidth: true
1783+ text: Powerd.status === Powerd.On ? "Power Off" : "Power On"
1784+ onClicked: {
1785+ if (Powerd.status === Powerd.On) Powerd.status = Powerd.Off;
1786+ else Powerd.status = Powerd.On;
1787+ }
1788+ }
1789+ }
1790+ }
1791+
1792+ UT.UnityTestCase {
1793+ name: "IndicatorsLight"
1794+ when: windowShown
1795+
1796+ function init() {
1797+ // reload
1798+ ActionData.data = noNewMessage;
1799+ loader.sourceComponent = undefined;
1800+ loader.sourceComponent = light;
1801+ Powerd.status = Powerd.On
1802+ }
1803+
1804+ function test_LightsStatus_data() {
1805+ return [
1806+ { tag: "Powerd.On with No Message", powerd: Powerd.On, actionData: noNewMessage, expected: Lights.Off },
1807+ { tag: "Powerd.Off with No Message", powerd: Powerd.Off, actionData: noNewMessage, expected: Lights.Off },
1808+ { tag: "Powerd.On with New Message", powerd: Powerd.On, actionData: newMessage, expected: Lights.Off },
1809+ { tag: "Powerd.Off with New Message", powerd: Powerd.Off, actionData: newMessage, expected: Lights.On },
1810+ ]
1811+ }
1812+
1813+ function test_LightsStatus(data) {
1814+ Powerd.status = data.powerd;
1815+ ActionData.data = data.actionData;
1816+
1817+ compare(Lights.state, data.expected, "Light does not match expected value");
1818+ }
1819+ }
1820+}
1821
1822=== modified file 'tests/qmltests/Panel/Indicators/tst_MenuItemFactory.qml'
1823--- tests/qmltests/Panel/Indicators/tst_MenuItemFactory.qml 2014-10-09 17:06:00 +0000
1824+++ tests/qmltests/Panel/Indicators/tst_MenuItemFactory.qml 2014-12-17 11:19:14 +0000
1825@@ -17,6 +17,7 @@
1826 import QtQuick 2.0
1827 import QtTest 1.0
1828 import Unity.Test 0.1 as UT
1829+import Ubuntu.Settings.Menus 0.1 as Menus
1830 import QMenuModel 0.1
1831 import Utils 0.1 as Utils
1832 import "../../../../qml/Panel/Indicators"
1833@@ -448,9 +449,59 @@
1834 }
1835
1836 function test_create_transferMenu(data) {
1837+ ActionData.data = {
1838+ "transfer-state.queued": {
1839+ 'valid': true,
1840+ 'state': {
1841+ 'state': Menus.TransferState.Queued,
1842+ 'percent': data.progress
1843+ }
1844+ },
1845+ "transfer-state.running": {
1846+ 'valid': true,
1847+ 'state': {
1848+ 'state': Menus.TransferState.Running,
1849+ 'seconds-left': 100,
1850+ 'percent': data.progress
1851+ }
1852+ },
1853+ "transfer-state.paused": {
1854+ 'valid': true,
1855+ 'state': {
1856+ 'state': Menus.TransferState.Paused,
1857+ 'seconds-left': 100,
1858+ 'percent': data.progress
1859+ }
1860+ },
1861+ "transfer-state.cancelled": {
1862+ 'valid': true,
1863+ 'state': {
1864+ 'state': Menus.TransferState.Canceled,
1865+ 'percent': data.progress
1866+ }
1867+ },
1868+ "transfer-state.finished": {
1869+ 'valid': true,
1870+ 'state': {
1871+ 'state': Menus.TransferState.Finished,
1872+ 'seconds-left': 0,
1873+ 'percent': data.progress
1874+ }
1875+ },
1876+ "transfer-state.error": {
1877+ 'valid': true,
1878+ 'state': {
1879+ 'state': Menus.TransferState.Error,
1880+ 'seconds-left': 100,
1881+ 'percent': data.progress
1882+ }
1883+ }
1884+ };
1885+
1886 menuData.type = "com.canonical.indicator.transfer";
1887 menuData.label = data.label;
1888 menuData.sensitive = data.enabled;
1889+ menuData.isToggled = data.active;
1890 menuData.icon = data.icon;
1891 menuData.ext = {
1892 'xCanonicalUid': data.tag
1893@@ -464,7 +515,7 @@
1894 compare(loader.item.text, data.label, "Label does not match data");
1895 compare(loader.item.iconSource, data.icon, "Icon does not match data");
1896 compare(loader.item.enabled, data.enabled, "Enabled does not match data");
1897- compare(loader.item.progress, data.progress, "Icon does not match data");
1898+ compare(loader.item.progress, data.progress, "Progress does not match data");
1899 compare(loader.item.active, data.active, "Active does not match data");
1900 compare(loader.item.stateText, data.stateText, "State text does not match data");
1901 }
1902
1903=== modified file 'tests/qmltests/Wizard/tst_Wizard.qml'
1904--- tests/qmltests/Wizard/tst_Wizard.qml 2014-12-02 17:43:25 +0000
1905+++ tests/qmltests/Wizard/tst_Wizard.qml 2014-12-17 11:19:14 +0000
1906@@ -18,6 +18,7 @@
1907 import QtTest 1.0
1908 import AccountsService 0.1
1909 import MeeGo.QOfono 0.2
1910+import QMenuModel 0.1
1911 import Ubuntu.Components 1.1
1912 import Ubuntu.SystemSettings.SecurityPrivacy 1.0
1913 import Unity.Test 0.1 as UT
1914@@ -58,6 +59,16 @@
1915 signalName: "setSecurityCalled"
1916 }
1917
1918+ SignalSpy {
1919+ id: activateLocationSpy
1920+ signalName: "activated"
1921+ }
1922+
1923+ SignalSpy {
1924+ id: activateGPSSpy
1925+ signalName: "activated"
1926+ }
1927+
1928 function setup() {
1929 AccountsService.hereEnabled = false;
1930 AccountsService.hereLicensePath = Qt.resolvedUrl("licenses");
1931@@ -68,6 +79,19 @@
1932
1933 updateSessionLanguageSpy.clear();
1934 setSecuritySpy.clear();
1935+ activateLocationSpy.clear();
1936+ activateGPSSpy.clear();
1937+
1938+ ActionData.data = {
1939+ "location-detection-enabled": {
1940+ 'valid': true,
1941+ 'state': false
1942+ },
1943+ "gps-detection-enabled": {
1944+ 'valid': true,
1945+ 'state': false
1946+ }
1947+ };
1948 }
1949
1950 Component.onCompleted: {
1951@@ -360,8 +384,8 @@
1952 var nopeCheck = findChild(page, "nopeCheck");
1953
1954 var locationActionGroup = findInvisibleChild(page, "locationActionGroup");
1955- tryCompare(locationActionGroup.location, "state", false);
1956- tryCompare(locationActionGroup.gps, "state", false);
1957+ activateLocationSpy.target = locationActionGroup.location;
1958+ activateGPSSpy.target = locationActionGroup.gps;
1959
1960 tap(gpsCheck);
1961 tryCompare(gpsCheck, "checked", true);
1962@@ -370,8 +394,8 @@
1963
1964 tap(findChild(page, "forwardButton"));
1965 tryCompare(AccountsService, "hereEnabled", false);
1966- tryCompare(locationActionGroup.location, "state", true);
1967- tryCompare(locationActionGroup.gps, "state", true);
1968+ tryCompare(activateLocationSpy, "count", 1)
1969+ tryCompare(activateGPSSpy, "count", 1)
1970 }
1971
1972 function test_locationNope() {
1973@@ -381,8 +405,8 @@
1974 var nopeCheck = findChild(page, "nopeCheck");
1975
1976 var locationActionGroup = findInvisibleChild(page, "locationActionGroup");
1977- tryCompare(locationActionGroup.location, "state", false);
1978- tryCompare(locationActionGroup.gps, "state", false);
1979+ activateLocationSpy.target = locationActionGroup.location;
1980+ activateGPSSpy.target = locationActionGroup.gps;
1981
1982 tap(nopeCheck);
1983 tryCompare(gpsCheck, "checked", false);
1984@@ -391,8 +415,8 @@
1985
1986 tap(findChild(page, "forwardButton"));
1987 tryCompare(AccountsService, "hereEnabled", false);
1988- tryCompare(locationActionGroup.location, "state", false);
1989- tryCompare(locationActionGroup.gps, "state", false);
1990+ tryCompare(activateLocationSpy, "count", 0)
1991+ tryCompare(activateGPSSpy, "count", 0)
1992 }
1993
1994 function test_locationHere() {
1995@@ -402,8 +426,8 @@
1996 var nopeCheck = findChild(page, "nopeCheck");
1997
1998 var locationActionGroup = findInvisibleChild(page, "locationActionGroup");
1999- tryCompare(locationActionGroup.location, "state", false);
2000- tryCompare(locationActionGroup.gps, "state", false);
2001+ activateLocationSpy.target = locationActionGroup.location;
2002+ activateGPSSpy.target = locationActionGroup.gps;
2003
2004 // no tap because HERE is the default
2005 tryCompare(gpsCheck, "checked", false);
2006@@ -412,8 +436,8 @@
2007
2008 tap(findChild(page, "forwardButton"));
2009 tryCompare(AccountsService, "hereEnabled", true);
2010- tryCompare(locationActionGroup.location, "state", true);
2011- tryCompare(locationActionGroup.gps, "state", true);
2012+ tryCompare(activateLocationSpy, "count", 1)
2013+ tryCompare(activateGPSSpy, "count", 1)
2014 }
2015
2016 function test_locationHereTerms() {

Subscribers

People subscribed via source and target branches