Merge lp:~macslow/unity8/use-set-progress-api into lp:unity8
- use-set-progress-api
- Merge into trunk
Status: | Superseded |
---|---|
Proposed branch: | lp:~macslow/unity8/use-set-progress-api |
Merge into: | lp:unity8 |
Diff against target: |
1470 lines (+643/-69) 35 files modified
debian/control (+3/-3) plugins/Greeter/Unity/Launcher/CMakeLists.txt (+1/-1) plugins/Greeter/Unity/Launcher/launcheritem.cpp (+14/-0) plugins/Greeter/Unity/Launcher/launcheritem.h (+4/-0) plugins/Greeter/Unity/Launcher/launchermodelas.cpp (+29/-12) plugins/Greeter/Unity/Launcher/launchermodelas.h (+1/-0) plugins/Unity/Launcher/CMakeLists.txt (+1/-1) plugins/Unity/Launcher/asadapter.cpp (+1/-0) plugins/Unity/Launcher/dbusinterface.cpp (+39/-13) plugins/Unity/Launcher/dbusinterface.h (+2/-0) plugins/Unity/Launcher/launcheritem.cpp (+23/-0) plugins/Unity/Launcher/launcheritem.h (+3/-0) plugins/Unity/Launcher/launchermodel.cpp (+32/-0) plugins/Unity/Launcher/launchermodel.h (+2/-0) qml/Launcher/LauncherDelegate.qml (+101/-15) qml/Launcher/LauncherPanel.qml (+74/-4) qml/Launcher/graphics/progressbar-fill@30.sci (+0/-5) qml/Launcher/graphics/progressbar-trough@30.sci (+0/-5) tests/mocks/Unity/Launcher/CMakeLists.txt (+1/-1) tests/mocks/Unity/Launcher/MockLauncherItem.cpp (+19/-0) tests/mocks/Unity/Launcher/MockLauncherItem.h (+3/-0) tests/mocks/Unity/Launcher/MockLauncherModel.cpp (+50/-0) tests/mocks/Unity/Launcher/MockLauncherModel.h (+4/-0) tests/plugins/Greeter/Unity/Launcher/CMakeLists.txt (+1/-1) tests/plugins/Greeter/Unity/Launcher/launchermodelastest.cpp (+3/-0) tests/plugins/Unity/Launcher/CMakeLists.txt (+1/-1) tests/plugins/Unity/Launcher/launchermodeltest.cpp (+23/-7) tests/qmltests/Launcher/tst_Launcher.qml (+181/-0) tests/scripts/README (+9/-0) tests/scripts/alert-launcher-icon.sh (+3/-0) tests/scripts/get-progress.sh (+3/-0) tests/scripts/list-launcher-icons.sh (+3/-0) tests/scripts/set-count-visible.sh (+3/-0) tests/scripts/set-count.sh (+3/-0) tests/scripts/set-progress.sh (+3/-0) |
To merge this branch: | bzr merge lp:~macslow/unity8/use-set-progress-api |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
PS Jenkins bot (community) | continuous-integration | Needs Fixing | |
Michael Zanetti (community) | Approve | ||
Lukáš Tinkl (community) | Approve | ||
Nick Dedekind (community) | Needs Fixing | ||
Review via email: mp+262448@code.launchpad.net |
This proposal has been superseded by a proposal from 2015-07-23.
Commit message
Added corresponding tests and visual tweaks to a launcher-item's progress-overlay.
Description of the change
Added corresponding tests and visual tweaks to a launcher-item's progress-overlay.
For the reviewers convenience here's a screencast of the branch in action on a device: https:/
* Are there any related MPs required for this MP to build/function as expected? Please list.
No.
* 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?
Not applicable.
* If you changed the UI, has there been a design review?
Yes.
PS Jenkins bot (ps-jenkins) wrote : | # |
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1824
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1826
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1827
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
Michael Zanetti (mzanetti) wrote : | # |
As I commented on the related unity-api branch, I don't think we need to define an API for that. Unity8 itself doesn't ever set the progress.
* You can then completely revert the change in launchermodeas.
* I haven't tested it yet, but reading through the code it seems you didn't wire up the Set method on D-Bus.
* in asadapter.cpp you need to sync the progress value to AS too.
* in launchermodelas.cpp you need to read the change from AS and set that to the LauncherItems
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1828
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1829
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1831
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1831
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1832
http://
Executed test runs:
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
Lukáš Tinkl (lukas-kde) wrote : | # |
See inline comments
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1833
http://
Executed test runs:
FAILURE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1834
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1835
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1836
http://
Executed test runs:
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
Nick Dedekind (nick-dedekind) wrote : | # |
Small comment, otherwise code looks
Nick Dedekind (nick-dedekind) wrote : | # |
Having a "progressVisible" property only for the test is a bit of overkill. Can you go in on the "progressOverlay" named object with findChild and change visibility.
Nick Dedekind (nick-dedekind) wrote : | # |
*check visiblilty
Mirco Müller (macslow) wrote : | # |
> Having a "progressVisible" property only for the test is a bit of overkill.
> Can you go in on the "progressOverlay" named object with findChild and change
> visibility.
This and inline comment addressed with r1837.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1837
http://
Executed test runs:
FAILURE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
Lukáš Tinkl (lukas-kde) wrote : | # |
Approving, looks good now
* Are there any related MPs required for this MP to build/function as expected? Please list.
No
* 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?
Yes
* If you changed the UI, has there been a design review?
Yes
Michael Zanetti (mzanetti) wrote : | # |
> * Did you perform an exploratory manual test run of your code change and any related functionality?
> Yes.
So you did that? Both? How come it doesn't work then?
- 1838. By Mirco Müller
-
Fixed a missing signal-connect and added some handy shell-scripts for easier runtime-debugging of DBus-APIs on the device.
- 1839. By Mirco Müller
-
Make sure all changes are carried with the dataChanged signal.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1838
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1839
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild:
http://
- 1840. By Mirco Müller
-
Fixed whitespaces in scripts... added better explanation to helper-script README.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1840
http://
Executed test runs:
FAILURE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
- 1841. By Mirco Müller
-
Merged with trunk
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1841
http://
Executed test runs:
FAILURE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
- 1842. By Mirco Müller
-
Merged with trunk.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1842
http://
Executed test runs:
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1842
http://
Executed test runs:
FAILURE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
- 1843. By Mirco Müller
-
Merged with trunk.
- 1844. By Mirco Müller
-
There's no need for the adjusted width anymore for the new progress-bar visuals.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1843
http://
Executed test runs:
UNSTABLE: http://
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
- 1845. By Mirco Müller
-
Moving count-emblem to the bottom of launcher-icon to comply with latest design.
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1844
http://
Executed test runs:
UNSTABLE: http://
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1845
http://
Executed test runs:
UNSTABLE: http://
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
UNSTABLE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1845
http://
Executed test runs:
FAILURE: http://
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
Michael Zanetti (mzanetti) wrote : | # |
"progress" doesn't show up in introspection:
# qdbus com.canonical.Unity /com/canonical/
property readwrite int com.canonical.
property readwrite bool com.canonical.
signal void org.freedesktop
method QDBusVariant org.freedesktop
method QVariantMap org.freedesktop
method void org.freedesktop
method QString org.freedesktop
method QString org.freedesktop
method void org.freedesktop
====
There are some minor inline comments
- 1846. By Mirco Müller
-
Made sure progress is properly exposed in DBus-introspection and fixed other suggestions from MP-comments.
Michael Zanetti (mzanetti) wrote : | # |
* Did you perform an exploratory manual test run of the code change and any related functionality?
yes
* Did CI run pass? If not, please explain why.
as much as it could
* Did you make sure that the branch does not contain spurious tags?
yes
PS Jenkins bot (ps-jenkins) wrote : | # |
FAILED: Continuous integration, rev:1846
http://
Executed test runs:
FAILURE: http://
UNSTABLE: http://
SUCCESS: http://
SUCCESS: http://
FAILURE: http://
SUCCESS: http://
deb: http://
SUCCESS: http://
Click here to trigger a rebuild:
http://
- 1847. By Mirco Müller
-
Merged launcher-
icon-wobble branch and solved all conflicts. - 1848. By Mirco Müller
-
Limit dateChanged only to property that actually changed in the mock.
- 1849. By Mirco Müller
-
Merged again with launcher-
icon-wobble branch. - 1850. By Mirco Müller
-
Fixed alertViaCountAn
dCountVisible qmltest. - 1851. By Mirco Müller
-
Sorted out another issue with alertViaCountAn
dCountVisible qmltest.
Unmerged revisions
Preview Diff
1 | === modified file 'debian/control' |
2 | --- debian/control 2015-07-09 20:22:36 +0000 |
3 | +++ debian/control 2015-07-23 11:13:36 +0000 |
4 | @@ -30,7 +30,7 @@ |
5 | libqt5xmlpatterns5-dev, |
6 | libsystemsettings-dev, |
7 | libudev-dev, |
8 | - libunity-api-dev (>= 7.97), |
9 | + libunity-api-dev (>= 7.98), |
10 | libusermetricsoutput1-dev, |
11 | libxcb1-dev, |
12 | pkg-config, |
13 | @@ -101,7 +101,7 @@ |
14 | qtdeclarative5-ubuntu-telephony0.1, |
15 | qtdeclarative5-ubuntu-web-plugin, |
16 | ubuntu-system-settings, |
17 | - unity-launcher-impl-4, |
18 | + unity-launcher-impl-7, |
19 | unity8-common (= ${source:Version}), |
20 | unity8-private (= ${binary:Version}), |
21 | unity8-private | unity-launcher-impl, |
22 | @@ -191,7 +191,7 @@ |
23 | ${misc:Depends}, |
24 | ${shlibs:Depends}, |
25 | Provides: unity-launcher-impl, |
26 | - unity-launcher-impl-4, |
27 | + unity-launcher-impl-7, |
28 | Description: Unity 8 private libs |
29 | The Unity 8 shell is the primary user interface for Ubuntu devices. |
30 | . |
31 | |
32 | === modified file 'plugins/Greeter/Unity/Launcher/CMakeLists.txt' |
33 | --- plugins/Greeter/Unity/Launcher/CMakeLists.txt 2015-04-24 09:53:37 +0000 |
34 | +++ plugins/Greeter/Unity/Launcher/CMakeLists.txt 2015-07-23 11:13:36 +0000 |
35 | @@ -1,4 +1,4 @@ |
36 | -pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=6) |
37 | +pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=7) |
38 | pkg_check_modules(APPLICATION_API REQUIRED unity-shell-application=6) |
39 | pkg_check_modules(GSETTINGS_QT REQUIRED gsettings-qt) |
40 | |
41 | |
42 | === modified file 'plugins/Greeter/Unity/Launcher/launcheritem.cpp' |
43 | --- plugins/Greeter/Unity/Launcher/launcheritem.cpp 2015-02-11 14:02:24 +0000 |
44 | +++ plugins/Greeter/Unity/Launcher/launcheritem.cpp 2015-07-23 11:13:36 +0000 |
45 | @@ -31,6 +31,7 @@ |
46 | m_count(0), |
47 | m_countVisible(false), |
48 | m_focused(false), |
49 | + m_alerting(false), |
50 | m_quickList(new QuickListModel(this)) |
51 | { |
52 | QuickListEntry nameAction; |
53 | @@ -165,6 +166,19 @@ |
54 | } |
55 | } |
56 | |
57 | +bool LauncherItem::alerting() const |
58 | +{ |
59 | + return m_alerting; |
60 | +} |
61 | + |
62 | +void LauncherItem::setAlerting(bool alerting) |
63 | +{ |
64 | + if (m_alerting != alerting) { |
65 | + m_alerting = alerting; |
66 | + Q_EMIT alertingChanged(alerting); |
67 | + } |
68 | +} |
69 | + |
70 | unity::shell::launcher::QuickListModelInterface *LauncherItem::quickList() const |
71 | { |
72 | return m_quickList; |
73 | |
74 | === modified file 'plugins/Greeter/Unity/Launcher/launcheritem.h' |
75 | --- plugins/Greeter/Unity/Launcher/launcheritem.h 2015-02-11 14:02:24 +0000 |
76 | +++ plugins/Greeter/Unity/Launcher/launcheritem.h 2015-07-23 11:13:36 +0000 |
77 | @@ -41,6 +41,7 @@ |
78 | int count() const override; |
79 | bool countVisible() const override; |
80 | bool focused() const override; |
81 | + bool alerting() const override; |
82 | |
83 | unity::shell::launcher::QuickListModelInterface *quickList() const override; |
84 | |
85 | @@ -54,6 +55,8 @@ |
86 | void setCount(int count); |
87 | void setCountVisible(bool countVisible); |
88 | void setFocused(bool focused); |
89 | + void setAlerting(bool alerting); |
90 | + |
91 | |
92 | private: |
93 | QString m_appId; |
94 | @@ -66,6 +69,7 @@ |
95 | int m_count; |
96 | bool m_countVisible; |
97 | bool m_focused; |
98 | + bool m_alerting; |
99 | QuickListModel *m_quickList; |
100 | |
101 | friend class LauncherModel; |
102 | |
103 | === modified file 'plugins/Greeter/Unity/Launcher/launchermodelas.cpp' |
104 | --- plugins/Greeter/Unity/Launcher/launchermodelas.cpp 2015-02-11 14:02:24 +0000 |
105 | +++ plugins/Greeter/Unity/Launcher/launchermodelas.cpp 2015-07-23 11:13:36 +0000 |
106 | @@ -72,6 +72,13 @@ |
107 | return QVariant(); |
108 | } |
109 | |
110 | +void LauncherModel::setAlerting(const QString &appId, bool alerting) |
111 | +{ |
112 | + Q_UNUSED(appId) |
113 | + Q_UNUSED(alerting) |
114 | + qWarning() << "This is a read only implementation. Cannot set alert-state of items."; |
115 | +} |
116 | + |
117 | unity::shell::launcher::LauncherItemInterface *LauncherModel::get(int index) const |
118 | { |
119 | if (index < 0 || index >= m_list.count()) { |
120 | @@ -200,16 +207,24 @@ |
121 | Q_FOREACH (LauncherItem* item, m_list) { |
122 | bool found = false; |
123 | Q_FOREACH(const QVariant &asItem, items) { |
124 | - if (asItem.toMap().value("id").toString() == item->appId()) { |
125 | + QVariantMap cachedMap = asItem.toMap(); |
126 | + if (cachedMap.value("id").toString() == item->appId()) { |
127 | // Only keep and update it if we either show unpinned or it is pinned |
128 | - if (!m_onlyPinned || asItem.toMap().value("pinned").toBool()) { |
129 | + if (!m_onlyPinned || cachedMap.value("pinned").toBool()) { |
130 | found = true; |
131 | - item->setName(asItem.toMap().value("name").toString()); |
132 | - item->setIcon(asItem.toMap().value("icon").toString()); |
133 | - item->setCount(asItem.toMap().value("count").toInt()); |
134 | - item->setCountVisible(asItem.toMap().value("countVisible").toBool()); |
135 | + item->setName(cachedMap.value("name").toString()); |
136 | + item->setIcon(cachedMap.value("icon").toString()); |
137 | + item->setCount(cachedMap.value("count").toInt()); |
138 | + item->setCountVisible(cachedMap.value("countVisible").toBool()); |
139 | + item->setProgress(cachedMap.value("progress").toInt()); |
140 | int idx = m_list.indexOf(item); |
141 | - Q_EMIT dataChanged(index(idx), index(idx), QVector<int>() << RoleName << RoleIcon); |
142 | + Q_EMIT dataChanged(index(idx), |
143 | + index(idx), |
144 | + {RoleName, |
145 | + RoleIcon, |
146 | + RoleCount, |
147 | + RoleCountVisible, |
148 | + RoleProgress}); |
149 | } |
150 | break; |
151 | } |
152 | @@ -247,14 +262,16 @@ |
153 | } |
154 | |
155 | if (itemIndex == -1) { |
156 | + QVariantMap chachedMap = entry.toMap(); |
157 | // Need to add it. Just add it into the addedIndex to keep same ordering as the list in AS. |
158 | - LauncherItem *item = new LauncherItem(entry.toMap().value("id").toString(), |
159 | - entry.toMap().value("name").toString(), |
160 | - entry.toMap().value("icon").toString(), |
161 | + LauncherItem *item = new LauncherItem(chachedMap.value("id").toString(), |
162 | + chachedMap.value("name").toString(), |
163 | + chachedMap.value("icon").toString(), |
164 | this); |
165 | item->setPinned(true); |
166 | - item->setCount(entry.toMap().value("count").toInt()); |
167 | - item->setCountVisible(entry.toMap().value("countVisible").toBool()); |
168 | + item->setCount(chachedMap.value("count").toInt()); |
169 | + item->setCountVisible(chachedMap.value("countVisible").toBool()); |
170 | + item->setProgress(chachedMap.value("progress").toInt()); |
171 | beginInsertRows(QModelIndex(), newPosition, newPosition); |
172 | m_list.insert(newPosition, item); |
173 | endInsertRows(); |
174 | |
175 | === modified file 'plugins/Greeter/Unity/Launcher/launchermodelas.h' |
176 | --- plugins/Greeter/Unity/Launcher/launchermodelas.h 2015-04-30 09:31:51 +0000 |
177 | +++ plugins/Greeter/Unity/Launcher/launchermodelas.h 2015-07-23 11:13:36 +0000 |
178 | @@ -41,6 +41,7 @@ |
179 | |
180 | QVariant data(const QModelIndex &index, int role) const override; |
181 | |
182 | + Q_INVOKABLE void setAlerting(const QString &appId, bool alerting) override; |
183 | Q_INVOKABLE unity::shell::launcher::LauncherItemInterface* get(int index) const override; |
184 | Q_INVOKABLE void move(int oldIndex, int newIndex) override; |
185 | Q_INVOKABLE void pin(const QString &appId, int index = -1) override; |
186 | |
187 | === modified file 'plugins/Unity/Launcher/CMakeLists.txt' |
188 | --- plugins/Unity/Launcher/CMakeLists.txt 2015-04-24 09:53:37 +0000 |
189 | +++ plugins/Unity/Launcher/CMakeLists.txt 2015-07-23 11:13:36 +0000 |
190 | @@ -1,4 +1,4 @@ |
191 | -pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=6) |
192 | +pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=7) |
193 | pkg_check_modules(APPLICATION_API REQUIRED unity-shell-application=6) |
194 | pkg_check_modules(GSETTINGS_QT REQUIRED gsettings-qt) |
195 | |
196 | |
197 | === modified file 'plugins/Unity/Launcher/asadapter.cpp' |
198 | --- plugins/Unity/Launcher/asadapter.cpp 2015-02-11 14:13:26 +0000 |
199 | +++ plugins/Unity/Launcher/asadapter.cpp 2015-07-23 11:13:36 +0000 |
200 | @@ -56,5 +56,6 @@ |
201 | details.insert("count", item->count()); |
202 | details.insert("countVisible", item->countVisible()); |
203 | details.insert("pinned", item->pinned()); |
204 | + details.insert("progress", item->progress()); |
205 | return details; |
206 | } |
207 | |
208 | === modified file 'plugins/Unity/Launcher/dbusinterface.cpp' |
209 | --- plugins/Unity/Launcher/dbusinterface.cpp 2015-06-11 23:45:12 +0000 |
210 | +++ plugins/Unity/Launcher/dbusinterface.cpp 2015-07-23 11:13:36 +0000 |
211 | @@ -62,6 +62,8 @@ |
212 | "<interface name=\"com.canonical.Unity.Launcher.Item\">" |
213 | "<property name=\"count\" type=\"i\" access=\"readwrite\" />" |
214 | "<property name=\"countVisible\" type=\"b\" access=\"readwrite\" />" |
215 | + "<property name=\"progress\" type=\"i\" access=\"readwrite\" />" |
216 | + "<method name=\"Alert\" />" |
217 | "</interface>"; |
218 | return nodeiface; |
219 | } |
220 | @@ -122,6 +124,20 @@ |
221 | return false; |
222 | } |
223 | |
224 | + /* Break down the path to just the app id */ |
225 | + bool validpath = true; |
226 | + QString pathtemp = message.path(); |
227 | + if (!pathtemp.startsWith("/com/canonical/Unity/Launcher/")) { |
228 | + validpath = false; |
229 | + } |
230 | + pathtemp.remove("/com/canonical/Unity/Launcher/"); |
231 | + if (pathtemp.indexOf('/') >= 0) { |
232 | + validpath = false; |
233 | + } |
234 | + |
235 | + /* Find ourselves an appid */ |
236 | + QString appid = decodeAppId(pathtemp); |
237 | + |
238 | // First handle methods of the Launcher interface |
239 | if (message.interface() == "com.canonical.Unity.Launcher") { |
240 | if (message.member() == "Refresh") { |
241 | @@ -129,6 +145,13 @@ |
242 | Q_EMIT refreshCalled(); |
243 | return connection.send(reply); |
244 | } |
245 | + } else if (message.interface() == "com.canonical.Unity.Launcher.Item") { |
246 | + // Handle methods of the Launcher-Item interface |
247 | + if (message.member() == "Alert" && validpath) { |
248 | + QDBusMessage reply = message.createReply(); |
249 | + Q_EMIT alertCalled(appid); |
250 | + return connection.send(reply); |
251 | + } |
252 | } |
253 | |
254 | // Now handle dynamic properties (for launcher emblems) |
255 | @@ -140,50 +163,53 @@ |
256 | return false; |
257 | } |
258 | |
259 | - /* Break down the path to just the app id */ |
260 | - QString pathtemp = message.path(); |
261 | - if (!pathtemp.startsWith("/com/canonical/Unity/Launcher/")) { |
262 | - return false; |
263 | - } |
264 | - pathtemp.remove("/com/canonical/Unity/Launcher/"); |
265 | - if (pathtemp.indexOf('/') >= 0) { |
266 | + if (!validpath) { |
267 | return false; |
268 | } |
269 | |
270 | - /* Find ourselves an appid */ |
271 | - QString appid = decodeAppId(pathtemp); |
272 | int index = m_launcherModel->findApplication(appid); |
273 | LauncherItem *item = static_cast<LauncherItem*>(m_launcherModel->get(index)); |
274 | |
275 | QVariantList retval; |
276 | if (message.member() == "Get") { |
277 | + QString cachedString = message.arguments()[1].toString(); |
278 | if (!item) { |
279 | return false; |
280 | } |
281 | - if (message.arguments()[1].toString() == "count") { |
282 | + if (cachedString == "count") { |
283 | retval.append(QVariant::fromValue(QDBusVariant(item->count()))); |
284 | - } else if (message.arguments()[1].toString() == "countVisible") { |
285 | + } else if (cachedString == "countVisible") { |
286 | retval.append(QVariant::fromValue(QDBusVariant(item->countVisible()))); |
287 | + } else if (cachedString == "progress") { |
288 | + retval.append(QVariant::fromValue(QDBusVariant(item->progress()))); |
289 | } |
290 | } else if (message.member() == "Set") { |
291 | - if (message.arguments()[1].toString() == "count") { |
292 | + QString cachedString = message.arguments()[1].toString(); |
293 | + if (cachedString == "count") { |
294 | int newCount = message.arguments()[2].value<QDBusVariant>().variant().toInt(); |
295 | if (!item || newCount != item->count()) { |
296 | Q_EMIT countChanged(appid, newCount); |
297 | notifyPropertyChanged("com.canonical.Unity.Launcher.Item", encodeAppId(appid), "count", QVariant(newCount)); |
298 | } |
299 | - } else if (message.arguments()[1].toString() == "countVisible") { |
300 | + } else if (cachedString == "countVisible") { |
301 | bool newVisible = message.arguments()[2].value<QDBusVariant>().variant().toBool(); |
302 | if (!item || newVisible != item->countVisible()) { |
303 | Q_EMIT countVisibleChanged(appid, newVisible); |
304 | notifyPropertyChanged("com.canonical.Unity.Launcher.Item", encodeAppId(appid), "countVisible", newVisible); |
305 | } |
306 | + } else if (cachedString == "progress") { |
307 | + int newProgress = message.arguments()[2].value<QDBusVariant>().variant().toInt(); |
308 | + if (!item || newProgress != item->progress()) { |
309 | + Q_EMIT progressChanged(appid, newProgress); |
310 | + notifyPropertyChanged("com.canonical.Unity.Launcher.Item", encodeAppId(appid), "progress", QVariant(newProgress)); |
311 | + } |
312 | } |
313 | } else if (message.member() == "GetAll") { |
314 | if (item) { |
315 | QVariantMap all; |
316 | all.insert("count", item->count()); |
317 | all.insert("countVisible", item->countVisible()); |
318 | + all.insert("progress", item->progress()); |
319 | retval.append(all); |
320 | } |
321 | } else { |
322 | |
323 | === modified file 'plugins/Unity/Launcher/dbusinterface.h' |
324 | --- plugins/Unity/Launcher/dbusinterface.h 2015-06-11 23:45:12 +0000 |
325 | +++ plugins/Unity/Launcher/dbusinterface.h 2015-07-23 11:13:36 +0000 |
326 | @@ -36,7 +36,9 @@ |
327 | Q_SIGNALS: |
328 | void countChanged(const QString &appId, int count); |
329 | void countVisibleChanged(const QString &appId, bool countVisible); |
330 | + void progressChanged(const QString &appId, int progress); |
331 | void refreshCalled(); |
332 | + void alertCalled(const QString &appId); |
333 | |
334 | private: |
335 | static QString decodeAppId(const QString& path); |
336 | |
337 | === modified file 'plugins/Unity/Launcher/launcheritem.cpp' |
338 | --- plugins/Unity/Launcher/launcheritem.cpp 2014-11-19 17:43:09 +0000 |
339 | +++ plugins/Unity/Launcher/launcheritem.cpp 2015-07-23 11:13:36 +0000 |
340 | @@ -34,6 +34,7 @@ |
341 | m_count(0), |
342 | m_countVisible(false), |
343 | m_focused(false), |
344 | + m_alerting(false), |
345 | m_quickList(new QuickListModel(this)) |
346 | { |
347 | QuickListEntry nameAction; |
348 | @@ -150,6 +151,9 @@ |
349 | if (m_count != count) { |
350 | m_count = count; |
351 | Q_EMIT countChanged(count); |
352 | + if (m_countVisible) { |
353 | + setAlerting(true); |
354 | + } |
355 | } |
356 | } |
357 | |
358 | @@ -163,6 +167,9 @@ |
359 | if (m_countVisible != countVisible) { |
360 | m_countVisible = countVisible; |
361 | Q_EMIT countVisibleChanged(countVisible); |
362 | + if (countVisible) { |
363 | + setAlerting(true); |
364 | + } |
365 | } |
366 | } |
367 | |
368 | @@ -175,10 +182,26 @@ |
369 | { |
370 | if (m_focused != focused) { |
371 | m_focused = focused; |
372 | + if (focused) { |
373 | + setAlerting(false); |
374 | + } |
375 | Q_EMIT focusedChanged(focused); |
376 | } |
377 | } |
378 | |
379 | +bool LauncherItem::alerting() const |
380 | +{ |
381 | + return m_alerting; |
382 | +} |
383 | + |
384 | +void LauncherItem::setAlerting(bool alerting) |
385 | +{ |
386 | + if (m_alerting != alerting) { |
387 | + m_alerting = alerting; |
388 | + Q_EMIT alertingChanged(alerting); |
389 | + } |
390 | +} |
391 | + |
392 | unity::shell::launcher::QuickListModelInterface *LauncherItem::quickList() const |
393 | { |
394 | return m_quickList; |
395 | |
396 | === modified file 'plugins/Unity/Launcher/launcheritem.h' |
397 | --- plugins/Unity/Launcher/launcheritem.h 2014-09-02 18:22:37 +0000 |
398 | +++ plugins/Unity/Launcher/launcheritem.h 2015-07-23 11:13:36 +0000 |
399 | @@ -44,6 +44,7 @@ |
400 | int count() const override; |
401 | bool countVisible() const override; |
402 | bool focused() const override; |
403 | + bool alerting() const override; |
404 | |
405 | unity::shell::launcher::QuickListModelInterface *quickList() const override; |
406 | |
407 | @@ -57,6 +58,7 @@ |
408 | void setCount(int count); |
409 | void setCountVisible(bool countVisible); |
410 | void setFocused(bool focused); |
411 | + void setAlerting(bool alerting); |
412 | |
413 | private: |
414 | QString m_appId; |
415 | @@ -69,6 +71,7 @@ |
416 | int m_count; |
417 | bool m_countVisible; |
418 | bool m_focused; |
419 | + bool m_alerting; |
420 | QuickListModel *m_quickList; |
421 | |
422 | friend class LauncherModel; |
423 | |
424 | === modified file 'plugins/Unity/Launcher/launchermodel.cpp' |
425 | --- plugins/Unity/Launcher/launchermodel.cpp 2015-03-30 17:36:42 +0000 |
426 | +++ plugins/Unity/Launcher/launchermodel.cpp 2015-07-23 11:13:36 +0000 |
427 | @@ -40,7 +40,9 @@ |
428 | { |
429 | connect(m_dbusIface, &DBusInterface::countChanged, this, &LauncherModel::countChanged); |
430 | connect(m_dbusIface, &DBusInterface::countVisibleChanged, this, &LauncherModel::countVisibleChanged); |
431 | + connect(m_dbusIface, &DBusInterface::progressChanged, this, &LauncherModel::progressChanged); |
432 | connect(m_dbusIface, &DBusInterface::refreshCalled, this, &LauncherModel::refresh); |
433 | + connect(m_dbusIface, &DBusInterface::alertCalled, this, &LauncherModel::alert); |
434 | |
435 | connect(m_settings, &GSettings::changed, this, &LauncherModel::refresh); |
436 | |
437 | @@ -82,11 +84,25 @@ |
438 | return item->progress(); |
439 | case RoleFocused: |
440 | return item->focused(); |
441 | + case RoleAlerting: |
442 | + return item->alerting(); |
443 | } |
444 | |
445 | return QVariant(); |
446 | } |
447 | |
448 | +void LauncherModel::setAlerting(const QString &appId, bool alerting) { |
449 | + int index = findApplication(appId); |
450 | + if (index >= 0) { |
451 | + QModelIndex modelIndex = this->index(index); |
452 | + LauncherItem *item = m_list.at(index); |
453 | + if (!item->focused()) { |
454 | + item->setAlerting(alerting); |
455 | + Q_EMIT dataChanged(modelIndex, modelIndex, QVector<int>() << RoleAlerting); |
456 | + } |
457 | + } |
458 | +} |
459 | + |
460 | unity::shell::launcher::LauncherItemInterface *LauncherModel::get(int index) const |
461 | { |
462 | if (index < 0 || index >= m_list.count()) { |
463 | @@ -334,6 +350,9 @@ |
464 | if (idx >= 0) { |
465 | LauncherItem *item = m_list.at(idx); |
466 | item->setCount(count); |
467 | + if (item->countVisible()) { |
468 | + setAlerting(item->appId(), true); |
469 | + } |
470 | Q_EMIT dataChanged(index(idx), index(idx), QVector<int>() << RoleCount); |
471 | m_asAdapter->syncItems(m_list); |
472 | } |
473 | @@ -345,6 +364,9 @@ |
474 | if (idx >= 0) { |
475 | LauncherItem *item = m_list.at(idx); |
476 | item->setCountVisible(countVisible); |
477 | + if (countVisible) { |
478 | + setAlerting(item->appId(), true); |
479 | + } |
480 | Q_EMIT dataChanged(index(idx), index(idx), QVector<int>() << RoleCountVisible); |
481 | |
482 | // If countVisible goes to false, and the item is neither pinned nor recent we can drop it |
483 | @@ -453,6 +475,16 @@ |
484 | m_asAdapter->syncItems(m_list); |
485 | } |
486 | |
487 | +void LauncherModel::alert(const QString &appId) |
488 | +{ |
489 | + int idx = findApplication(appId); |
490 | + if (idx >= 0) { |
491 | + LauncherItem *item = m_list.at(idx); |
492 | + setAlerting(item->appId(), true); |
493 | + Q_EMIT dataChanged(index(idx), index(idx), QVector<int>() << RoleAlerting); |
494 | + } |
495 | +} |
496 | + |
497 | void LauncherModel::applicationAdded(const QModelIndex &parent, int row) |
498 | { |
499 | Q_UNUSED(parent); |
500 | |
501 | === modified file 'plugins/Unity/Launcher/launchermodel.h' |
502 | --- plugins/Unity/Launcher/launchermodel.h 2015-04-30 09:31:51 +0000 |
503 | +++ plugins/Unity/Launcher/launchermodel.h 2015-07-23 11:13:36 +0000 |
504 | @@ -45,6 +45,7 @@ |
505 | |
506 | QVariant data(const QModelIndex &index, int role) const override; |
507 | |
508 | + Q_INVOKABLE void setAlerting(const QString &appId, bool alerting) override; |
509 | Q_INVOKABLE unity::shell::launcher::LauncherItemInterface* get(int index) const override; |
510 | Q_INVOKABLE void move(int oldIndex, int newIndex) override; |
511 | Q_INVOKABLE void pin(const QString &appId, int index = -1) override; |
512 | @@ -63,6 +64,7 @@ |
513 | public Q_SLOTS: |
514 | void requestRemove(const QString &appId) override; |
515 | Q_INVOKABLE void refresh(); |
516 | + Q_INVOKABLE void alert(const QString &appId); |
517 | |
518 | private: |
519 | void storeAppList(); |
520 | |
521 | === modified file 'qml/Launcher/LauncherDelegate.qml' |
522 | --- qml/Launcher/LauncherDelegate.qml 2014-10-14 12:28:07 +0000 |
523 | +++ qml/Launcher/LauncherDelegate.qml 2015-07-23 11:13:36 +0000 |
524 | @@ -15,7 +15,7 @@ |
525 | */ |
526 | |
527 | import QtQuick 2.0 |
528 | -import Ubuntu.Components 0.1 |
529 | +import Ubuntu.Components 1.1 |
530 | |
531 | Item { |
532 | id: root |
533 | @@ -27,6 +27,8 @@ |
534 | property bool itemFocused: false |
535 | property real maxAngle: 0 |
536 | property bool inverted: false |
537 | + property bool alerting: false |
538 | + readonly property alias wiggling: wiggleAnim.running |
539 | |
540 | readonly property int effectiveHeight: Math.cos(angle * Math.PI / 180) * itemHeight |
541 | readonly property real foldedHeight: Math.cos(maxAngle * Math.PI / 180) * itemHeight |
542 | @@ -39,6 +41,82 @@ |
543 | property real offset: 0 |
544 | property real itemOpacity: 1 |
545 | property real brightness: 0 |
546 | + property double maxWiggleAngle: 5.0 |
547 | + |
548 | + QtObject { |
549 | + id: priv |
550 | + |
551 | + readonly property int wiggleDuration: UbuntuAnimation.SnapDuration |
552 | + property real wiggleAngle: 0 |
553 | + } |
554 | + |
555 | + SequentialAnimation { |
556 | + id: wiggleAnim |
557 | + |
558 | + running: alerting |
559 | + loops: 1 |
560 | + alwaysRunToEnd: true |
561 | + |
562 | + NumberAnimation { |
563 | + target: priv |
564 | + property: "wiggleAngle" |
565 | + from: 0 |
566 | + to: maxWiggleAngle |
567 | + duration: priv.wiggleDuration |
568 | + easing.type: Easing.InQuad |
569 | + } |
570 | + |
571 | + NumberAnimation { |
572 | + target: priv |
573 | + property: "wiggleAngle" |
574 | + from: maxWiggleAngle |
575 | + to: -maxWiggleAngle |
576 | + duration: priv.wiggleDuration |
577 | + easing.type: Easing.InOutQuad |
578 | + } |
579 | + |
580 | + NumberAnimation { |
581 | + target: priv |
582 | + property: "wiggleAngle" |
583 | + from: -maxWiggleAngle |
584 | + to: maxWiggleAngle |
585 | + duration: priv.wiggleDuration |
586 | + easing.type: Easing.InOutQuad |
587 | + } |
588 | + |
589 | + NumberAnimation { |
590 | + target: priv |
591 | + property: "wiggleAngle" |
592 | + from: maxWiggleAngle |
593 | + to: -maxWiggleAngle |
594 | + duration: priv.wiggleDuration |
595 | + easing.type: Easing.InOutQuad |
596 | + } |
597 | + |
598 | + NumberAnimation { |
599 | + target: priv |
600 | + property: "wiggleAngle" |
601 | + from: -maxWiggleAngle |
602 | + to: maxWiggleAngle |
603 | + duration: priv.wiggleDuration |
604 | + easing.type: Easing.InOutQuad |
605 | + } |
606 | + |
607 | + NumberAnimation { |
608 | + target: priv |
609 | + property: "wiggleAngle" |
610 | + from: maxWiggleAngle |
611 | + to: 0 |
612 | + duration: priv.wiggleDuration |
613 | + easing.type: Easing.OutQuad |
614 | + } |
615 | + |
616 | + UbuntuNumberAnimation { |
617 | + target: root |
618 | + property: "alerting" |
619 | + to: 0 |
620 | + } |
621 | + } |
622 | |
623 | Item { |
624 | id: iconItem |
625 | @@ -75,7 +153,7 @@ |
626 | objectName: "countEmblem" |
627 | anchors { |
628 | right: parent.right |
629 | - top: parent.top |
630 | + bottom: parent.bottom |
631 | margins: units.dp(3) |
632 | } |
633 | width: Math.min(root.itemWidth, Math.max(units.gu(2), countLabel.implicitWidth + units.gu(1))) |
634 | @@ -100,23 +178,21 @@ |
635 | } |
636 | } |
637 | |
638 | - BorderImage { |
639 | + UbuntuShape { |
640 | id: progressOverlay |
641 | objectName: "progressOverlay" |
642 | + |
643 | anchors { |
644 | left: iconItem.left |
645 | right: iconItem.right |
646 | - bottom: iconItem.bottom |
647 | - leftMargin: units.gu(1) |
648 | - rightMargin: units.gu(1) |
649 | - bottomMargin: units.gu(1) |
650 | + verticalCenter: parent.verticalCenter |
651 | + leftMargin: units.gu(1.5) |
652 | + rightMargin: units.gu(1.5) |
653 | } |
654 | - height: units.gu(1.5) |
655 | + height: units.gu(1) |
656 | visible: root.progress > -1 |
657 | - source: "graphics/progressbar-trough.sci" |
658 | - |
659 | - // For fill calculation we need to remove the 2 units of border defined in .sci file |
660 | - property int adjustedWidth: width - units.gu(2) |
661 | + color: UbuntuColors.darkGrey |
662 | + borderSource: "none" |
663 | |
664 | Item { |
665 | anchors { |
666 | @@ -124,20 +200,22 @@ |
667 | top: parent.top |
668 | bottom: parent.bottom |
669 | } |
670 | - width: Math.min(100, root.progress) / 100 * parent.adjustedWidth + units.gu(1) |
671 | + width: Math.min(100, root.progress) / 100 * parent.width |
672 | clip: true |
673 | |
674 | - BorderImage { |
675 | + UbuntuShape { |
676 | anchors { |
677 | left: parent.left |
678 | top: parent.top |
679 | bottom: parent.bottom |
680 | } |
681 | + color: "white" |
682 | + borderSource: "none" |
683 | width: progressOverlay.width |
684 | - source: "graphics/progressbar-fill.sci" |
685 | } |
686 | } |
687 | } |
688 | + |
689 | Image { |
690 | objectName: "focusedHighlight" |
691 | anchors { |
692 | @@ -167,6 +245,14 @@ |
693 | } |
694 | |
695 | transform: [ |
696 | + // The rotation about the icon's center/z-axis for the wiggle |
697 | + // needs to happen here too, because there's no other way to |
698 | + // align the wiggle with the icon-folding otherwise |
699 | + Rotation { |
700 | + axis { x: 0; y: 0; z: 1 } |
701 | + origin { x: iconItem.width / 2; y: iconItem.height / 2; z: 0 } |
702 | + angle: priv.wiggleAngle |
703 | + }, |
704 | // Rotating 3 times at top/bottom because that increases the perspective. |
705 | // This is a hack, but as QML does not support real 3D coordinates |
706 | // getting a higher perspective can only be done by a hack. This is the most |
707 | |
708 | === modified file 'qml/Launcher/LauncherPanel.qml' |
709 | --- qml/Launcher/LauncherPanel.qml 2015-07-01 11:39:49 +0000 |
710 | +++ qml/Launcher/LauncherPanel.qml 2015-07-23 11:13:36 +0000 |
711 | @@ -86,6 +86,7 @@ |
712 | height: parent.height - dashItem.height - parent.spacing*2 |
713 | |
714 | Item { |
715 | + id: launcherListViewItem |
716 | anchors.fill: parent |
717 | clip: true |
718 | |
719 | @@ -109,12 +110,21 @@ |
720 | preferredHighlightBegin: (height - itemHeight) / 2 |
721 | preferredHighlightEnd: (height + itemHeight) / 2 |
722 | |
723 | + // for the single peeking icon, when alert-state is set on delegate |
724 | + property int peekingIndex: -1 |
725 | + |
726 | // The size of the area the ListView is extended to make sure items are not |
727 | // destroyed when dragging them outside the list. This needs to be at least |
728 | // itemHeight to prevent folded items from disappearing and DragArea limits |
729 | // need to be smaller than this size to avoid breakage. |
730 | property int extensionSize: 0 |
731 | |
732 | + // These properties are needed to facilitate implicitly unfolding the |
733 | + // launcher to the peeking icon, if it is not already fully flat |
734 | + // and in view for the user |
735 | + property real moveToIndexYFrom |
736 | + property real moveToIndexYTo |
737 | + |
738 | // Setting extensionSize after the list has been populated because it has |
739 | // the potential to mess up with the intial positioning in combination |
740 | // with snapping to the center of the list. This catches all the cases |
741 | @@ -128,6 +138,14 @@ |
742 | flick(0, clickFlickSpeed) |
743 | } |
744 | |
745 | + UbuntuNumberAnimation { |
746 | + id: moveToIndexAnimation |
747 | + target: launcherListView |
748 | + property: "contentY" |
749 | + from: launcherListView.moveToIndexYFrom |
750 | + to: launcherListView.moveToIndexYTo |
751 | + } |
752 | + |
753 | // The height of the area where icons start getting folded |
754 | property int foldingStartHeight: units.gu(6.5) |
755 | // The height of the area where the items reach the final folding angle |
756 | @@ -180,10 +198,63 @@ |
757 | progress: model.progress |
758 | itemFocused: model.focused |
759 | inverted: root.inverted |
760 | + alerting: model.alerting |
761 | z: -Math.abs(offset) |
762 | maxAngle: 55 |
763 | property bool dragging: false |
764 | |
765 | + SequentialAnimation { |
766 | + id: peekingAnimation |
767 | + |
768 | + // revealing |
769 | + PropertyAction { target: root; property: "visible"; value: (launcher.visibleWidth === 0) ? 1 : 0 } |
770 | + PropertyAction { target: launcherListViewItem; property: "clip"; value: 0 } |
771 | + |
772 | + UbuntuNumberAnimation { |
773 | + target: launcherDelegate |
774 | + alwaysRunToEnd: true |
775 | + loops: 1 |
776 | + properties: "x" |
777 | + to: (units.gu(.5) + launcherListView.width * .5) * (root.inverted ? -1 : 1) |
778 | + duration: UbuntuAnimation.BriskDuration |
779 | + } |
780 | + |
781 | + // hiding |
782 | + UbuntuNumberAnimation { |
783 | + target: launcherDelegate |
784 | + alwaysRunToEnd: true |
785 | + loops: 1 |
786 | + properties: "x" |
787 | + to: 0 |
788 | + duration: UbuntuAnimation.BriskDuration |
789 | + } |
790 | + |
791 | + PropertyAction { target: launcherListViewItem; property: "clip"; value: 1 } |
792 | + PropertyAction { target: root; property: "visible"; value: (launcher.visibleWidth === 0) ? 0 : 1 } |
793 | + } |
794 | + |
795 | + onAlertingChanged: { |
796 | + if(alerting) { |
797 | + if (!dragging && (launcherListView.peekingIndex === -1 || launcher.visibleWidth > 0)) { |
798 | + launcherListView.moveToIndexYFrom = launcherListView.contentY |
799 | + launcherListView.positionViewAtIndex(index, ListView.Center) |
800 | + launcherListView.moveToIndexYTo = launcherListView.contentY |
801 | + moveToIndexAnimation.start() |
802 | + if (!dragging && launcher.state !== "visible") { |
803 | + peekingAnimation.start() |
804 | + } |
805 | + } |
806 | + |
807 | + if (launcherListView.peekingIndex === -1) { |
808 | + launcherListView.peekingIndex = index |
809 | + } |
810 | + } else { |
811 | + if (launcherListView.peekingIndex === index) { |
812 | + launcherListView.peekingIndex = -1 |
813 | + } |
814 | + } |
815 | + } |
816 | + |
817 | ThinDivider { |
818 | id: dropIndicator |
819 | objectName: "dropIndicator" |
820 | @@ -521,7 +592,7 @@ |
821 | Image { |
822 | anchors { |
823 | left: parent.left |
824 | - leftMargin: quickList.item ? (quickList.item.width - units.gu(1)) / 2 - width / 2 : 0 |
825 | + leftMargin: quickList.item !== undefined ? (quickList.item.width - units.gu(1)) / 2 - width / 2 : 0 |
826 | verticalCenter: parent.verticalCenter |
827 | verticalCenterOffset: (parent.height / 2 + units.dp(3)) * (quickList.offset > 0 ? 1 : -1) * (root.inverted ? 1 : -1) |
828 | } |
829 | @@ -564,10 +635,9 @@ |
830 | |
831 | // internal |
832 | property int itemCenter: item ? root.mapFromItem(quickList.item).y + (item.height / 2) : units.gu(1) |
833 | - property int offset: item ? itemCenter + (item.height/2) + height + units.gu(1) > parent.height ? |
834 | + property int offset: item !== undefined ? (itemCenter + (item.height/2) + height + units.gu(1) > parent.height ? |
835 | -(item.height/2) - height - units.gu(.5) : |
836 | - (item.height/2) + units.gu(.5) : |
837 | - 0 |
838 | + (item.height/2) + units.gu(.5)) : 0 |
839 | |
840 | Column { |
841 | id: quickListColumn |
842 | |
843 | === removed file 'qml/Launcher/graphics/progressbar-fill@30.png' |
844 | Binary files qml/Launcher/graphics/progressbar-fill@30.png 2013-08-19 19:34:03 +0000 and qml/Launcher/graphics/progressbar-fill@30.png 1970-01-01 00:00:00 +0000 differ |
845 | === removed file 'qml/Launcher/graphics/progressbar-fill@30.sci' |
846 | --- qml/Launcher/graphics/progressbar-fill@30.sci 2013-08-19 19:34:03 +0000 |
847 | +++ qml/Launcher/graphics/progressbar-fill@30.sci 1970-01-01 00:00:00 +0000 |
848 | @@ -1,5 +0,0 @@ |
849 | -border.left: 36 |
850 | -border.top: 16 |
851 | -border.bottom: 28 |
852 | -border.right: 36 |
853 | -source: progressbar-fill@30.png |
854 | \ No newline at end of file |
855 | |
856 | === removed file 'qml/Launcher/graphics/progressbar-trough@30.png' |
857 | Binary files qml/Launcher/graphics/progressbar-trough@30.png 2013-08-19 19:34:03 +0000 and qml/Launcher/graphics/progressbar-trough@30.png 1970-01-01 00:00:00 +0000 differ |
858 | === removed file 'qml/Launcher/graphics/progressbar-trough@30.sci' |
859 | --- qml/Launcher/graphics/progressbar-trough@30.sci 2013-08-19 19:34:03 +0000 |
860 | +++ qml/Launcher/graphics/progressbar-trough@30.sci 1970-01-01 00:00:00 +0000 |
861 | @@ -1,5 +0,0 @@ |
862 | -border.left: 36 |
863 | -border.top: 16 |
864 | -border.bottom: 26 |
865 | -border.right: 36 |
866 | -source: progressbar-trough@30.png |
867 | \ No newline at end of file |
868 | |
869 | === modified file 'tests/mocks/Unity/Launcher/CMakeLists.txt' |
870 | --- tests/mocks/Unity/Launcher/CMakeLists.txt 2015-04-13 09:33:28 +0000 |
871 | +++ tests/mocks/Unity/Launcher/CMakeLists.txt 2015-07-23 11:13:36 +0000 |
872 | @@ -1,4 +1,4 @@ |
873 | -pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=6) |
874 | +pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=7) |
875 | |
876 | include_directories( |
877 | ${CMAKE_CURRENT_SOURCE_DIR} |
878 | |
879 | === modified file 'tests/mocks/Unity/Launcher/MockLauncherItem.cpp' |
880 | --- tests/mocks/Unity/Launcher/MockLauncherItem.cpp 2014-09-03 13:30:52 +0000 |
881 | +++ tests/mocks/Unity/Launcher/MockLauncherItem.cpp 2015-07-23 11:13:36 +0000 |
882 | @@ -37,6 +37,7 @@ |
883 | m_count(0), |
884 | m_countVisible(false), |
885 | m_focused(false), |
886 | + m_alerting(false), |
887 | m_quickList(new MockQuickListModel(this)) |
888 | { |
889 | |
890 | @@ -129,6 +130,9 @@ |
891 | { |
892 | m_count = count; |
893 | Q_EMIT countChanged(count); |
894 | + if (m_countVisible) { |
895 | + setAlerting(true); |
896 | + } |
897 | } |
898 | } |
899 | |
900 | @@ -142,6 +146,9 @@ |
901 | if (m_countVisible != countVisible) { |
902 | m_countVisible = countVisible; |
903 | Q_EMIT countVisibleChanged(countVisible); |
904 | + if (countVisible) { |
905 | + setAlerting(true); |
906 | + } |
907 | } |
908 | } |
909 | |
910 | @@ -159,6 +166,18 @@ |
911 | } |
912 | } |
913 | |
914 | +bool MockLauncherItem::alerting() const |
915 | +{ |
916 | + return m_alerting; |
917 | +} |
918 | + |
919 | +void MockLauncherItem::setAlerting(bool alerting) |
920 | +{ |
921 | + if (m_alerting != alerting) { |
922 | + m_alerting = alerting; |
923 | + Q_EMIT alertingChanged(alerting); |
924 | + } |
925 | +} |
926 | |
927 | unity::shell::launcher::QuickListModelInterface *MockLauncherItem::quickList() const |
928 | { |
929 | |
930 | === modified file 'tests/mocks/Unity/Launcher/MockLauncherItem.h' |
931 | --- tests/mocks/Unity/Launcher/MockLauncherItem.h 2015-04-30 09:31:51 +0000 |
932 | +++ tests/mocks/Unity/Launcher/MockLauncherItem.h 2015-07-23 11:13:36 +0000 |
933 | @@ -44,6 +44,7 @@ |
934 | int count() const override; |
935 | bool countVisible() const override; |
936 | bool focused() const override; |
937 | + bool alerting() const override; |
938 | |
939 | unity::shell::launcher::QuickListModelInterface *quickList() const override; |
940 | |
941 | @@ -55,6 +56,7 @@ |
942 | void setCount(int count); |
943 | void setCountVisible(bool countVisible); |
944 | void setFocused(bool focused); |
945 | + void setAlerting(bool alerting); |
946 | |
947 | QString m_appId; |
948 | QString m_desktopFile; |
949 | @@ -67,6 +69,7 @@ |
950 | int m_count; |
951 | bool m_countVisible; |
952 | bool m_focused; |
953 | + bool m_alerting; |
954 | MockQuickListModel *m_quickList; |
955 | |
956 | friend class MockLauncherModel; |
957 | |
958 | === modified file 'tests/mocks/Unity/Launcher/MockLauncherModel.cpp' |
959 | --- tests/mocks/Unity/Launcher/MockLauncherModel.cpp 2015-03-06 04:44:11 +0000 |
960 | +++ tests/mocks/Unity/Launcher/MockLauncherModel.cpp 2015-07-23 11:13:36 +0000 |
961 | @@ -34,6 +34,7 @@ |
962 | item = new MockLauncherItem("gallery-app", "/usr/share/applications/gallery-app.desktop", "Gallery", "gallery", this); |
963 | item->setProgress(50); |
964 | item->setCountVisible(true); |
965 | + item->setAlerting(false); |
966 | m_list.append(item); |
967 | item = new MockLauncherItem("music-app", "/usr/share/applications/music-app.desktop", "Music", "soundcloud", this); |
968 | m_list.append(item); |
969 | @@ -43,25 +44,30 @@ |
970 | item = new MockLauncherItem("webbrowser-app", "/usr/share/applications/webbrowser-app.desktop", "Browser", "browser", this); |
971 | item->setCount(1); |
972 | item->setCountVisible(true); |
973 | + item->setAlerting(false); |
974 | m_list.append(item); |
975 | item = new MockLauncherItem("twitter-webapp", "/usr/share/applications/twitter-webapp.desktop", "Twitter", "twitter", this); |
976 | item->setCount(12); |
977 | item->setCountVisible(true); |
978 | + item->setAlerting(false); |
979 | item->setPinned(true); |
980 | m_list.append(item); |
981 | item = new MockLauncherItem("gmail-webapp", "/usr/share/applications/gmail-webapp.desktop", "GMail", "gmail", this); |
982 | item->setCount(123); |
983 | item->setCountVisible(true); |
984 | + item->setAlerting(false); |
985 | m_list.append(item); |
986 | item = new MockLauncherItem("ubuntu-weather-app", "/usr/share/applications/ubuntu-weather-app.desktop", "Weather", "weather", this); |
987 | item->setCount(1234567890); |
988 | item->setCountVisible(true); |
989 | + item->setAlerting(false); |
990 | item->setPinned(true); |
991 | m_list.append(item); |
992 | item = new MockLauncherItem("notes-app", "/usr/share/applications/notes-app.desktop", "Notepad", "notepad", this); |
993 | item->setProgress(50); |
994 | item->setCount(5); |
995 | item->setCountVisible(true); |
996 | + item->setAlerting(false); |
997 | item->setFocused(true); |
998 | item->setPinned(true); |
999 | m_list.append(item); |
1000 | @@ -105,6 +111,8 @@ |
1001 | return item->countVisible(); |
1002 | case RoleFocused: |
1003 | return item->focused(); |
1004 | + case RoleAlerting: |
1005 | + return item->alerting(); |
1006 | } |
1007 | |
1008 | return QVariant(); |
1009 | @@ -119,6 +127,18 @@ |
1010 | return m_list.at(index); |
1011 | } |
1012 | |
1013 | +void MockLauncherModel::setAlerting(const QString &appId, bool alerting) { |
1014 | + int index = findApp(appId); |
1015 | + if (index >= 0) { |
1016 | + QModelIndex modelIndex = this->index(index); |
1017 | + MockLauncherItem *item = m_list.at(index); |
1018 | + if (!item->focused()) { |
1019 | + item->setAlerting(alerting); |
1020 | + Q_EMIT dataChanged(modelIndex, modelIndex, QVector<int>() << RoleAlerting); |
1021 | + } |
1022 | + } |
1023 | +} |
1024 | + |
1025 | void MockLauncherModel::move(int oldIndex, int newIndex) |
1026 | { |
1027 | // Make sure its not moved outside the lists |
1028 | @@ -195,6 +215,16 @@ |
1029 | return -1; |
1030 | } |
1031 | |
1032 | +void MockLauncherModel::setProgress(const QString &appId, int progress) |
1033 | +{ |
1034 | + int index = findApp(appId); |
1035 | + if (index >= 0) { |
1036 | + m_list.at(index)->setProgress(progress); |
1037 | + QModelIndex modelIndex = this->index(index); |
1038 | + Q_EMIT dataChanged(modelIndex, modelIndex, QVector<int>() << RoleProgress); |
1039 | + } |
1040 | +} |
1041 | + |
1042 | void MockLauncherModel::setUser(const QString &username) |
1043 | { |
1044 | Q_UNUSED(username) |
1045 | @@ -226,6 +256,26 @@ |
1046 | Q_EMIT hint(); |
1047 | } |
1048 | |
1049 | +void MockLauncherModel::setCount(const QString &appId, int count) |
1050 | +{ |
1051 | + int index = findApp(appId); |
1052 | + if (index >= 0) { |
1053 | + m_list.at(index)->setCount(count); |
1054 | + QModelIndex modelIndex = this->index(index); |
1055 | + Q_EMIT dataChanged(modelIndex, modelIndex, QVector<int>() << RoleCount); |
1056 | + } |
1057 | +} |
1058 | + |
1059 | +void MockLauncherModel::setCountVisible(const QString &appId, bool countVisible) |
1060 | +{ |
1061 | + int index = findApp(appId); |
1062 | + if (index >= 0) { |
1063 | + m_list.at(index)->setCountVisible(countVisible); |
1064 | + QModelIndex modelIndex = this->index(index); |
1065 | + Q_EMIT dataChanged(modelIndex, modelIndex); |
1066 | + } |
1067 | +} |
1068 | + |
1069 | unity::shell::application::ApplicationManagerInterface *MockLauncherModel::applicationManager() const |
1070 | { |
1071 | return nullptr; |
1072 | |
1073 | === modified file 'tests/mocks/Unity/Launcher/MockLauncherModel.h' |
1074 | --- tests/mocks/Unity/Launcher/MockLauncherModel.h 2015-04-30 09:31:51 +0000 |
1075 | +++ tests/mocks/Unity/Launcher/MockLauncherModel.h 2015-07-23 11:13:36 +0000 |
1076 | @@ -38,6 +38,7 @@ |
1077 | |
1078 | QVariant data(const QModelIndex& index, int role) const override; |
1079 | |
1080 | + Q_INVOKABLE void setAlerting(const QString &appId, bool alerting) override; |
1081 | Q_INVOKABLE unity::shell::launcher::LauncherItemInterface *get(int index) const override; |
1082 | Q_INVOKABLE void move(int oldIndex, int newIndex) override; |
1083 | Q_INVOKABLE void pin(const QString &appId, int index = -1) override; |
1084 | @@ -54,6 +55,9 @@ |
1085 | |
1086 | // For testing |
1087 | Q_INVOKABLE void emitHint(); |
1088 | + Q_INVOKABLE void setProgress(const QString &appId, int progress); |
1089 | + Q_INVOKABLE void setCount(const QString &appId, int count); |
1090 | + Q_INVOKABLE void setCountVisible(const QString &appId, bool countVisible); |
1091 | |
1092 | Q_SIGNALS: |
1093 | void quickListTriggered(const QString &appId, int index); |
1094 | |
1095 | === modified file 'tests/plugins/Greeter/Unity/Launcher/CMakeLists.txt' |
1096 | --- tests/plugins/Greeter/Unity/Launcher/CMakeLists.txt 2015-06-17 12:14:27 +0000 |
1097 | +++ tests/plugins/Greeter/Unity/Launcher/CMakeLists.txt 2015-07-23 11:13:36 +0000 |
1098 | @@ -1,4 +1,4 @@ |
1099 | -pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=6) |
1100 | +pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=7) |
1101 | pkg_check_modules(APPLICATION_API REQUIRED unity-shell-application=6) |
1102 | |
1103 | include_directories( |
1104 | |
1105 | === modified file 'tests/plugins/Greeter/Unity/Launcher/launchermodelastest.cpp' |
1106 | --- tests/plugins/Greeter/Unity/Launcher/launchermodelastest.cpp 2015-02-11 14:11:26 +0000 |
1107 | +++ tests/plugins/Greeter/Unity/Launcher/launchermodelastest.cpp 2015-07-23 11:13:36 +0000 |
1108 | @@ -43,6 +43,7 @@ |
1109 | item.insert("name", "Item 1"); |
1110 | item.insert("icon", "fake.svg"); |
1111 | item.insert("count", 0); |
1112 | + item.insert("progress", 0); |
1113 | item.insert("countVisible", false); |
1114 | item.insert("pinned", true); |
1115 | list.append(item); |
1116 | @@ -67,6 +68,7 @@ |
1117 | inSync &= model->get(i)->name() == list.at(i).value("name").toString(); |
1118 | inSync &= model->get(i)->icon() == list.at(i).value("icon").toString(); |
1119 | inSync &= model->get(i)->count() == list.at(i).value("count").toInt(); |
1120 | + inSync &= model->get(i)->progress() == list.at(i).value("progress").toInt(); |
1121 | inSync &= model->get(i)->countVisible() == list.at(i).value("countVisible").toBool(); |
1122 | } |
1123 | return inSync; |
1124 | @@ -111,6 +113,7 @@ |
1125 | newEntry.insert("name", "New app"); |
1126 | newEntry.insert("icon", "some-icon.svg"); |
1127 | newEntry.insert("count", 0); |
1128 | + newEntry.insert("progress", 42); |
1129 | newEntry.insert("countVisible", false); |
1130 | newEntry.insert("pinned", true); |
1131 | newList.append(newEntry); |
1132 | |
1133 | === modified file 'tests/plugins/Unity/Launcher/CMakeLists.txt' |
1134 | --- tests/plugins/Unity/Launcher/CMakeLists.txt 2015-06-17 12:14:27 +0000 |
1135 | +++ tests/plugins/Unity/Launcher/CMakeLists.txt 2015-07-23 11:13:36 +0000 |
1136 | @@ -1,5 +1,5 @@ |
1137 | pkg_check_modules(GSETTINGS_QT REQUIRED gsettings-qt) |
1138 | -pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=6) |
1139 | +pkg_check_modules(LAUNCHER_API REQUIRED unity-shell-launcher=7) |
1140 | |
1141 | include_directories( |
1142 | ${CMAKE_CURRENT_SOURCE_DIR} |
1143 | |
1144 | === modified file 'tests/plugins/Unity/Launcher/launchermodeltest.cpp' |
1145 | --- tests/plugins/Unity/Launcher/launchermodeltest.cpp 2015-06-12 16:07:43 +0000 |
1146 | +++ tests/plugins/Unity/Launcher/launchermodeltest.cpp 2015-07-23 11:13:36 +0000 |
1147 | @@ -368,11 +368,18 @@ |
1148 | } |
1149 | |
1150 | void testCountEmblems() { |
1151 | + QSignalSpy spy(launcherModel, SIGNAL(dataChanged(QModelIndex,QModelIndex,QVector<int>))); |
1152 | + |
1153 | // Call GetAll on abs-icon |
1154 | QDBusInterface interface("com.canonical.Unity.Launcher", "/com/canonical/Unity/Launcher/abs_2Dicon", "org.freedesktop.DBus.Properties"); |
1155 | QDBusReply<QVariantMap> reply = interface.call("GetAll"); |
1156 | QVariantMap map = reply.value(); |
1157 | |
1158 | + // Check that the alerting-status is still false, and the item on the upper side of the API |
1159 | + int index = launcherModel->findApplication("abs-icon"); |
1160 | + QCOMPARE(index >= 0, true); |
1161 | + QVERIFY(launcherModel->get(index)->alerting() == false); |
1162 | + |
1163 | // Make sure GetAll returns a map with count and countVisible props |
1164 | QCOMPARE(map.contains("count"), true); |
1165 | QCOMPARE(map.contains("countVisible"), true); |
1166 | @@ -393,13 +400,8 @@ |
1167 | QCOMPARE(map.value("count").toInt(), 55); |
1168 | QCOMPARE(map.value("countVisible").toBool(), true); |
1169 | |
1170 | - // Now the item on the upper side of the API |
1171 | - int index = launcherModel->findApplication("abs-icon"); |
1172 | - QCOMPARE(index >= 0, true); |
1173 | - |
1174 | - // And make sure values have changed there as well |
1175 | - QCOMPARE(launcherModel->get(index)->countVisible(), true); |
1176 | - QCOMPARE(launcherModel->get(index)->count(), 55); |
1177 | + // Finally check, that the change to "count" implicitly also set the alerting-state to true |
1178 | + QVERIFY(launcherModel->get(index)->alerting() == true); |
1179 | } |
1180 | |
1181 | void testCountEmblemAddsRemovesItem_data() { |
1182 | @@ -459,6 +461,20 @@ |
1183 | QCOMPARE(index == -1, !isRunning && !isPinned && !startWhenVisible); |
1184 | } |
1185 | |
1186 | + void testAlert() { |
1187 | + // Check that the alerting-status is still false |
1188 | + int index = launcherModel->findApplication("abs-icon"); |
1189 | + QCOMPARE(index >= 0, true); |
1190 | + QVERIFY(launcherModel->get(index)->alerting() == false); |
1191 | + |
1192 | + // Call Alert() on "abs-icon" |
1193 | + QDBusInterface interface("com.canonical.Unity.Launcher", "/com/canonical/Unity/Launcher/abs_2Dicon", "com.canonical.Unity.Launcher.Item"); |
1194 | + interface.call("Alert"); |
1195 | + |
1196 | + // Check that the alerting-status is now true |
1197 | + QVERIFY(launcherModel->get(index)->alerting() == true); |
1198 | + } |
1199 | + |
1200 | void testRefreshAfterDeletedDesktopFiles_data() { |
1201 | QTest::addColumn<bool>("deleted"); |
1202 | QTest::newRow("have .desktop files") << false; |
1203 | |
1204 | === modified file 'tests/qmltests/Launcher/tst_Launcher.qml' |
1205 | --- tests/qmltests/Launcher/tst_Launcher.qml 2015-04-24 09:53:37 +0000 |
1206 | +++ tests/qmltests/Launcher/tst_Launcher.qml 2015-07-23 11:13:36 +0000 |
1207 | @@ -93,6 +93,57 @@ |
1208 | onClicked: launcherLoader.item.inverted = !launcherLoader.item.inverted |
1209 | Layout.fillWidth: true |
1210 | } |
1211 | + |
1212 | + Row { |
1213 | + spacing: units.gu(1) |
1214 | + |
1215 | + Button { |
1216 | + text: "35% bar" |
1217 | + onClicked: LauncherModel.setProgress(LauncherModel.get(parseInt(appIdEntryBar.displayText)).appId, 35) |
1218 | + Layout.fillWidth: true |
1219 | + } |
1220 | + |
1221 | + TextArea { |
1222 | + id: appIdEntryBar |
1223 | + anchors.verticalCenter: parent.verticalCenter |
1224 | + width: units.gu(4) |
1225 | + height: units.gu(4) |
1226 | + autoSize: true |
1227 | + text: "2" |
1228 | + maximumLineCount: 1 |
1229 | + } |
1230 | + |
1231 | + Button { |
1232 | + text: "no bar" |
1233 | + onClicked: LauncherModel.setProgress(LauncherModel.get(parseInt(appIdEntryBar.displayText)).appId, -1) |
1234 | + Layout.fillWidth: true |
1235 | + } |
1236 | + } |
1237 | + |
1238 | + Row { |
1239 | + spacing: units.gu(1) |
1240 | + |
1241 | + Button { |
1242 | + text: "set alert" |
1243 | + onClicked: LauncherModel.setAlerting(LauncherModel.get(parseInt(appIdEntryAlert.displayText)).appId, true) |
1244 | + } |
1245 | + |
1246 | + TextArea { |
1247 | + id: appIdEntryAlert |
1248 | + anchors.verticalCenter: parent.verticalCenter |
1249 | + width: units.gu(5) |
1250 | + height: units.gu(4) |
1251 | + autoSize: true |
1252 | + text: "2" |
1253 | + maximumLineCount: 1 |
1254 | + Layout.fillWidth: true |
1255 | + } |
1256 | + |
1257 | + Button { |
1258 | + text: "unset alert" |
1259 | + onClicked: LauncherModel.setAlerting(LauncherModel.get(parseInt(appIdEntryAlert.displayText)).appId, false) |
1260 | + } |
1261 | + } |
1262 | } |
1263 | |
1264 | SignalSpy { |
1265 | @@ -169,6 +220,16 @@ |
1266 | tryCompare(panel, "x", -panel.width, 1000); |
1267 | } |
1268 | |
1269 | + function waitForWiggleToStart(appIcon) { |
1270 | + verify(appIcon != undefined) |
1271 | + tryCompare(appIcon, "wiggling", true, 1000, "wiggle-anim should not be in stopped state") |
1272 | + } |
1273 | + |
1274 | + function waitForWiggleToStop(appIcon) { |
1275 | + verify(appIcon != undefined) |
1276 | + tryCompare(appIcon, "wiggling", false, 1000, "wiggle-anim should not be in running state") |
1277 | + } |
1278 | + |
1279 | function positionLauncherListAtBeginning() { |
1280 | var listView = testCase.findChild(launcherLoader.item, "launcherListView"); |
1281 | listView.contentY = -listView.topMargin; |
1282 | @@ -636,5 +697,125 @@ |
1283 | tryCompare(launcher, "state", "", 1000, "Launcher didn't hide after moving mouse away from it"); |
1284 | waitUntilLauncherDisappears(); |
1285 | } |
1286 | + |
1287 | + function test_progressChangeViaModel() { |
1288 | + dragLauncherIntoView(); |
1289 | + var item = findChild(launcher, "launcherDelegate0") |
1290 | + verify(item != undefined) |
1291 | + LauncherModel.setProgress(LauncherModel.get(0).appId, -1) |
1292 | + compare(findChild(item, "progressOverlay").visible, false) |
1293 | + LauncherModel.setProgress(LauncherModel.get(0).appId, 20) |
1294 | + compare(findChild(item, "progressOverlay").visible, true) |
1295 | + LauncherModel.setProgress(LauncherModel.get(0).appId, 0) |
1296 | + } |
1297 | + |
1298 | + function test_alertPeekingIcon() { |
1299 | + var listView = findChild(launcher, "launcherListView") |
1300 | + verify(listView != undefined) |
1301 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, true) |
1302 | + tryCompare(listView, "peekingIndex", 5, 1000, "Wrong appId set as peeking-index") |
1303 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, false) |
1304 | + tryCompare(listView, "peekingIndex", -1, 1000, "peeking-index should be -1") |
1305 | + } |
1306 | + |
1307 | + function test_alertHidingIcon() { |
1308 | + var listView = findChild(launcher, "launcherListView") |
1309 | + verify(listView != undefined) |
1310 | + var appIcon6 = findChild(launcher, "launcherDelegate6") |
1311 | + verify(appIcon6 != undefined) |
1312 | + LauncherModel.setAlerting(LauncherModel.get(6).appId, true) |
1313 | + waitForWiggleToStart(appIcon6) |
1314 | + LauncherModel.setAlerting(LauncherModel.get(6).appId, false) |
1315 | + waitForWiggleToStop(appIcon6) |
1316 | + tryCompare(appIcon6, "x", 0, 1000, "x-value of appId #6 should not be non-zero") |
1317 | + waitForRendering(listView) |
1318 | + } |
1319 | + |
1320 | + function test_alertIgnoreFocusedApp() { |
1321 | + LauncherModel.setAlerting(LauncherModel.get(0).appId, true) |
1322 | + compare(LauncherModel.get(0).alerting, false, "Focused app should not have the alert-state set") |
1323 | + } |
1324 | + |
1325 | + function test_alertOnlyOnePeekingIcon() { |
1326 | + var listView = findChild(launcher, "launcherListView") |
1327 | + verify(listView != undefined) |
1328 | + LauncherModel.setAlerting(LauncherModel.get(3).appId, true) |
1329 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, true) |
1330 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, true) |
1331 | + tryCompare(listView, "peekingIndex", 3, 1000, "Wrong appId set as peeking-index") |
1332 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, false) |
1333 | + LauncherModel.setAlerting(LauncherModel.get(3).appId, false) |
1334 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, false) |
1335 | + tryCompare(listView, "peekingIndex", -1, 1000, "peeking-index should be -1") |
1336 | + waitForRendering(listView) |
1337 | + } |
1338 | + |
1339 | + function test_alertMultipleApps() { |
1340 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, true) |
1341 | + LauncherModel.setAlerting(LauncherModel.get(3).appId, true) |
1342 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, true) |
1343 | + LauncherModel.setAlerting(LauncherModel.get(7).appId, true) |
1344 | + compare(LauncherModel.get(1).alerting, true, "Alert-state of appId #1 should not be false") |
1345 | + compare(LauncherModel.get(3).alerting, true, "Alert-state of appId #3 should not be false") |
1346 | + compare(LauncherModel.get(5).alerting, true, "Alert-state of appId #5 should not be false") |
1347 | + compare(LauncherModel.get(7).alerting, true, "Alert-state of appId #7 should not be false") |
1348 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, false) |
1349 | + LauncherModel.setAlerting(LauncherModel.get(3).appId, false) |
1350 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, false) |
1351 | + LauncherModel.setAlerting(LauncherModel.get(7).appId, false) |
1352 | + compare(LauncherModel.get(1).alerting, false, "Alert-state of appId #1 should not be true") |
1353 | + compare(LauncherModel.get(3).alerting, false, "Alert-state of appId #1 should not be true") |
1354 | + compare(LauncherModel.get(5).alerting, false, "Alert-state of appId #1 should not be true") |
1355 | + compare(LauncherModel.get(7).alerting, false, "Alert-state of appId #1 should not be true") |
1356 | + } |
1357 | + |
1358 | + function test_alertMoveIconIntoView() { |
1359 | + dragLauncherIntoView(); |
1360 | + var appIcon1 = findChild(launcher, "launcherDelegate1"); |
1361 | + var appIcon7 = findChild(launcher, "launcherDelegate7"); |
1362 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, true) |
1363 | + tryCompare(appIcon1, "angle", 0, 1000, "angle of appId #1 should not be non-zero") |
1364 | + waitForWiggleToStart(appIcon1) |
1365 | + LauncherModel.setAlerting(LauncherModel.get(7).appId, true) |
1366 | + tryCompare(appIcon7, "angle", 0, 1000, "angle of appId #7 should not be non-zero") |
1367 | + waitForWiggleToStart(appIcon7) |
1368 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, false) |
1369 | + waitForWiggleToStop(appIcon1) |
1370 | + LauncherModel.setAlerting(LauncherModel.get(7).appId, false) |
1371 | + waitForWiggleToStop(appIcon7) |
1372 | + } |
1373 | + |
1374 | + function test_alertWigglePeekDrag() { |
1375 | + var appIcon5 = findChild(launcher, "launcherDelegate5"); |
1376 | + var listView = findChild(launcher, "launcherListView") |
1377 | + verify(listView != undefined) |
1378 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, true) |
1379 | + tryCompare(listView, "peekingIndex", 5, 1000, "Wrong appId set as peeking-index") |
1380 | + waitForWiggleToStart(appIcon5) |
1381 | + tryCompare(appIcon5, "wiggling", true, 1000, "appId #6 should not be still") |
1382 | + dragLauncherIntoView(); |
1383 | + tryCompare(listView, "peekingIndex", -1, 1000, "peeking-index should be -1") |
1384 | + LauncherModel.setAlerting(LauncherModel.get(5).appId, false) |
1385 | + waitForWiggleToStop(appIcon5) |
1386 | + tryCompare(appIcon5, "wiggling", false, 1000, "appId #1 should not be wiggling") |
1387 | + } |
1388 | + |
1389 | + function test_alertViaCountAndCountVisible() { |
1390 | + dragLauncherIntoView(); |
1391 | + var appIcon1 = findChild(launcher, "launcherDelegate1") |
1392 | + var oldCount = LauncherModel.get(1).count |
1393 | + LauncherModel.setCount(LauncherModel.get(1).appId, 42) |
1394 | + tryCompare(appIcon1, "wiggling", false, 1000, "appId #1 should be still") |
1395 | + LauncherModel.setCountVisible(LauncherModel.get(1).appId, 1) |
1396 | + tryCompare(appIcon1, "wiggling", true, 1000, "appId #1 should not be still") |
1397 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, false) |
1398 | + waitForWiggleToStop(appIcon1) |
1399 | + LauncherModel.setCount(LauncherModel.get(1).appId, 4711) |
1400 | + tryCompare(appIcon1, "wiggling", true, 1000, "appId #1 should not be still") |
1401 | + LauncherModel.setAlerting(LauncherModel.get(1).appId, false) |
1402 | + waitForWiggleToStop(appIcon1) |
1403 | + LauncherModel.setCountVisible(LauncherModel.get(1).appId, 0) |
1404 | + LauncherModel.setCount(LauncherModel.get(1).appId, oldCount) |
1405 | + } |
1406 | } |
1407 | } |
1408 | |
1409 | === added directory 'tests/scripts' |
1410 | === added file 'tests/scripts/README' |
1411 | --- tests/scripts/README 1970-01-01 00:00:00 +0000 |
1412 | +++ tests/scripts/README 2015-07-23 11:13:36 +0000 |
1413 | @@ -0,0 +1,9 @@ |
1414 | +This directory holds a few handy shell-scripts to simplify runtime-testing of DBus-APIs (requires qdbus-qt5 to be installed). |
1415 | + |
1416 | +launcher-icon related: |
1417 | + * list-launcher-icons.sh - get all icons of unity8-launcher |
1418 | + * alert-launcher-icon.sh - trigger alert/wiggle of unfocused launcher-icon |
1419 | + * get-progress.sh - get progress-value of a launcher-icon |
1420 | + * set-progress.sh - set progress-value of a launcher-icon |
1421 | + * set-count.sh - set the count of a launcher-icon |
1422 | + * set-count-visible.sh - set the count-visible flag of a launcher-icon |
1423 | |
1424 | === added file 'tests/scripts/alert-launcher-icon.sh' |
1425 | --- tests/scripts/alert-launcher-icon.sh 1970-01-01 00:00:00 +0000 |
1426 | +++ tests/scripts/alert-launcher-icon.sh 2015-07-23 11:13:36 +0000 |
1427 | @@ -0,0 +1,3 @@ |
1428 | +#!/bin/sh |
1429 | + |
1430 | +qdbus com.canonical.Unity.Launcher /com/canonical/Unity/Launcher/$1 com.canonical.Unity.Launcher.Item.Alert |
1431 | |
1432 | === added file 'tests/scripts/get-progress.sh' |
1433 | --- tests/scripts/get-progress.sh 1970-01-01 00:00:00 +0000 |
1434 | +++ tests/scripts/get-progress.sh 2015-07-23 11:13:36 +0000 |
1435 | @@ -0,0 +1,3 @@ |
1436 | +#!/bin/sh |
1437 | + |
1438 | +qdbus com.canonical.Unity.Launcher /com/canonical/Unity/Launcher/$1 org.freedesktop.DBus.Properties.Get com.canonical.Unity.Launcher.Item progress |
1439 | |
1440 | === added file 'tests/scripts/list-launcher-icons.sh' |
1441 | --- tests/scripts/list-launcher-icons.sh 1970-01-01 00:00:00 +0000 |
1442 | +++ tests/scripts/list-launcher-icons.sh 2015-07-23 11:13:36 +0000 |
1443 | @@ -0,0 +1,3 @@ |
1444 | +#!/bin/sh |
1445 | + |
1446 | +qdbus com.canonical.Unity | grep Launcher | cut -f6 -d/ |
1447 | |
1448 | === added file 'tests/scripts/set-count-visible.sh' |
1449 | --- tests/scripts/set-count-visible.sh 1970-01-01 00:00:00 +0000 |
1450 | +++ tests/scripts/set-count-visible.sh 2015-07-23 11:13:36 +0000 |
1451 | @@ -0,0 +1,3 @@ |
1452 | +#!/bin/sh |
1453 | + |
1454 | +qdbus com.canonical.Unity.Launcher /com/canonical/Unity/Launcher/$1 org.freedesktop.DBus.Properties.Set com.canonical.Unity.Launcher.Item countVisible $2 |
1455 | |
1456 | === added file 'tests/scripts/set-count.sh' |
1457 | --- tests/scripts/set-count.sh 1970-01-01 00:00:00 +0000 |
1458 | +++ tests/scripts/set-count.sh 2015-07-23 11:13:36 +0000 |
1459 | @@ -0,0 +1,3 @@ |
1460 | +#!/bin/sh |
1461 | + |
1462 | +qdbus com.canonical.Unity.Launcher /com/canonical/Unity/Launcher/$1 org.freedesktop.DBus.Properties.Set com.canonical.Unity.Launcher.Item count $2 |
1463 | |
1464 | === added file 'tests/scripts/set-progress.sh' |
1465 | --- tests/scripts/set-progress.sh 1970-01-01 00:00:00 +0000 |
1466 | +++ tests/scripts/set-progress.sh 2015-07-23 11:13:36 +0000 |
1467 | @@ -0,0 +1,3 @@ |
1468 | +#!/bin/sh |
1469 | + |
1470 | +qdbus com.canonical.Unity.Launcher /com/canonical/Unity/Launcher/$1 org.freedesktop.DBus.Properties.Set com.canonical.Unity.Launcher.Item progress $2 |
FAILED: Continuous integration, rev:1823 jenkins. qa.ubuntu. com/job/ unity8- ci/5836/ jenkins. qa.ubuntu. com/job/ generic- deb-autopilot- wily-touch/ 130/console jenkins. qa.ubuntu. com/job/ unity8- wily-amd64- ci/116/ console jenkins. qa.ubuntu. com/job/ unity8- wily-i386- ci/117/ console jenkins. qa.ubuntu. com/job/ generic- mediumtests- builder- wily-armhf/ 130/console
http://
Executed test runs:
FAILURE: http://
FAILURE: http://
FAILURE: http://
FAILURE: http://
Click here to trigger a rebuild: s-jenkins. ubuntu- ci:8080/ job/unity8- ci/5836/ rebuild
http://