on xenial help sign in
Added unitymenumodelstacktest
commitd6f59efb82bbc90d62d7d74bda76bb65244680ef authorNick Dedekind <nicholas.dedekind@gmail.com> dateFri 27 Sep 2013, 11:59 (13 years ago) parent9bb8e82
2 files changed+266
tests/plugins/Unity/Indicators/CMakeLists.txt+11 tests/plugins/Unity/Indicators/unitymenumodelstacktest.cpp+255
tests/plugins/Unity/Indicators/CMakeLists.txt+11
@@ -1,6 +1,13 @@
1+pkg_check_modules(GLIB REQUIRED glib-2.0>=2.32)
2+pkg_check_modules(GIO REQUIRED gio-2.0>=2.32)
3+pkg_check_modules(QMENUMODEL REQUIRED qmenumodel)
4+
15include_directories(
26 ${CMAKE_CURRENT_BINARY_DIR}
37 ${CMAKE_CURRENT_SOURCE_DIR}/../../../../plugins/Unity/Indicators
8+ ${GLIB_INCLUDE_DIRS}
9+ ${GIO_INCLUDE_DIRS}
10+ ${QMENUMODEL_INCLUDE_DIRS}
411 )
512
613macro(run_tests)
@@ -16,6 +23,9 @@ macro(run_tests)
1623 qt5_use_modules(${_test}Exec Test Core Qml)
1724 target_link_libraries(${_test}Exec
1825 IndicatorsQml
26+ ${GLIB_LIBRARIES}
27+ ${GIO_LIBRARIES}
28+ ${QMENUMODEL_LDFLAGS}
1929 )
2030 set(_test_list "${_test_list};${_test}")
2131 endforeach()
@@ -25,4 +35,5 @@ run_tests(
2535 indicatorsmanagertest
2636 indicatorsmodeltest
2737 menucontentactivatortest
38+ unitymenumodelstacktest
2839 )
tests/plugins/Unity/Indicators/unitymenumodelstacktest.cppnew file+255
@@ -0,0 +1,255 @@
1+/*
2+ * Copyright (C) 2013 Canonical, Ltd.
3+ *
4+ * This program is free software; you can redistribute it and/or modify
5+ * it under the terms of the GNU General Public License as published by
6+ * the Free Software Foundation; version 3.
7+ *
8+ * This program is distributed in the hope that it will be useful,
9+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11+ * GNU General Public License for more details.
12+ *
13+ * You should have received a copy of the GNU General Public License
14+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
15+ *
16+ * Authors:
17+ * Nick Dedekind <nick.dedekind@canonical.com>
18+ */
19+
20+#include "indicatorsmanager.h"
21+#include "paths.h"
22+#include "unitymenumodelstack.h"
23+
24+#include <QtTest>
25+#include <QDebug>
26+
27+#include <glib.h>
28+#include <gio/gio.h>
29+#include <unitymenumodel.h>
30+
31+ #define BUS_NAME "com.canonical.unity8.unitymenumodelstacktest"
32+ #define OBJECT_PATH "/com/canonical/unity8/unitymenumodelstack"
33+
34+static void on_bus_acquired (GDBusConnection *bus, const gchar *name, gpointer user_data);
35+static void on_name_aquired (GDBusConnection *bus, const gchar *name, gpointer user_data);
36+static void on_name_lost (GDBusConnection *bus, const gchar *name, gpointer user_data);
37+
38+
39+class UnityMenuModelStackTest : public QObject
40+{
41+ Q_OBJECT
42+private Q_SLOTS:
43+
44+ void initTestCase()
45+ {
46+ m_menuUid = 0;
47+ m_connection = NULL;
48+ m_connected = NULL;
49+ m_failed = false;
50+ m_menu = NULL;
51+
52+ GBusNameOwnerFlags flags;
53+ flags = (GBusNameOwnerFlags) (G_BUS_NAME_OWNER_FLAGS_ALLOW_REPLACEMENT | G_BUS_NAME_OWNER_FLAGS_REPLACE);
54+
55+ g_bus_own_name (G_BUS_TYPE_SESSION, BUS_NAME, flags,
56+ on_bus_acquired, on_name_aquired, on_name_lost, this, NULL);
57+ }
58+
59+ void cleanupTestCase()
60+ {
61+ if (m_connection) {
62+ g_object_unref(m_connection);
63+ m_connection = NULL;
64+ }
65+ }
66+
67+ void init()
68+ {
69+ QFETCH(QString, test);
70+ QFETCH(int, menuDepth);
71+ QFETCH(int, subMenuCount);
72+
73+ waitFor([this]() { return this->m_connected || this->m_failed; }, 500);
74+ QVERIFY(m_connected);
75+
76+ const QString& path = QString(OBJECT_PATH) + "/" + test;
77+
78+ m_menuUid = exportMenuModel(&m_menu, m_connection, path, subMenuCount, menuDepth);
79+
80+ m_model = new UnityMenuModel;
81+ m_model->setBusName(BUS_NAME);
82+ m_model->setMenuObjectPath(path.toUtf8());
83+ }
84+
85+ void cleanup() {
86+ if (m_model) {
87+ delete m_model;
88+ m_model = NULL;
89+ }
90+ if (m_menuUid != 0) {
91+ g_dbus_connection_unexport_menu_model(m_connection, m_menuUid);
92+ m_menuUid = 0;
93+ }
94+ if (m_menu) {
95+ g_object_unref(m_menu);
96+ }
97+ }
98+
99+
100+ void testPushPop_data() {
101+ QTest::addColumn<QString>("test");
102+ QTest::addColumn<int>("menuDepth");
103+ QTest::addColumn<int>("subMenuCount");
104+ QTest::addColumn<int>("subMenuIndex");
105+
106+ QTest::newRow("depth=0") << "testPushPop1" << 0 << 1 << 0;
107+ QTest::newRow("depth=1") << "testPushPop2" << 1 << 1 << 0;
108+ QTest::newRow("depth=8") << "testPushPop3" << 8 << 2 << 1;
109+ }
110+
111+ void testPushPop()
112+ {
113+ QFETCH(int, menuDepth);
114+ QFETCH(int, subMenuCount);
115+ QFETCH(int, subMenuIndex);
116+
117+ UnityMenuModelStack stack;
118+ QList<UnityMenuModel*> models;
119+
120+ UnityMenuModel* parent = m_model;
121+ UnityMenuModel* child = m_model;
122+
123+ while(child) {
124+ // submenus aren't immediate
125+ bool rows = waitFor([child, subMenuCount]() { return child->rowCount() == subMenuCount; }, 500);
126+ QVERIFY(rows);
127+
128+ stack.push(child, subMenuIndex);
129+ models << child;
130+
131+ parent = child;
132+ child = qobject_cast<UnityMenuModel*>(parent->submenu(subMenuIndex));
133+ }
134+
135+ QCOMPARE(stack.count(), models.count());
136+ QCOMPARE(stack.count(), menuDepth+1);
137+ while(stack.count() > 0) {
138+ QCOMPARE(stack.pop(), models.takeLast());
139+ }
140+ }
141+
142+ void testPopOnRemove_data() {
143+ QTest::addColumn<QString>("test");
144+ QTest::addColumn<int>("menuDepth");
145+ QTest::addColumn<int>("subMenuCount");
146+ QTest::addColumn<int>("subMenuIndex");
147+ QTest::addColumn<int>("removeIndex");
148+ QTest::addColumn<int>("resultCount");
149+
150+ QTest::newRow("removeIndexBefore") << "removeIndexBefore" << 4 << 2 << 1 << 0 << 5;
151+ QTest::newRow("removeCurrentIndex") << "removeCurrentIndex" << 4 << 2 << 0 << 0 << 1;
152+ QTest::newRow("removeIndexAfter") << "removeIndexAfter" << 4 << 2 << 0 << 1 << 5;
153+ }
154+
155+ void testPopOnRemove()
156+ {
157+ QFETCH(int, menuDepth);
158+ QFETCH(int, subMenuCount);
159+ QFETCH(int, subMenuIndex);
160+ QFETCH(int, removeIndex);
161+ QFETCH(int, resultCount);
162+
163+ UnityMenuModelStack stack;
164+
165+ UnityMenuModel* parent = m_model;
166+ UnityMenuModel* child = m_model;
167+
168+ while(child) {
169+ // submenus aren't immediate
170+ bool rows = waitFor([child, subMenuCount]() { return child->rowCount() == subMenuCount; }, 1000);
171+ QVERIFY(rows);
172+
173+ stack.push(child, subMenuIndex);
174+
175+ parent = child;
176+ child = qobject_cast<UnityMenuModel*>(parent->submenu(subMenuIndex));
177+ }
178+
179+ QCOMPARE(stack.count(), menuDepth+1);
180+ g_menu_remove(m_menu, removeIndex);
181+
182+ waitFor([&stack, resultCount]() { return stack.count() == resultCount; }, 1000);
183+ QCOMPARE(stack.count(), resultCount);
184+ }
185+
186+private:
187+ bool waitFor(std::function<bool()> functor, int ms) {
188+
189+ QElapsedTimer timer;
190+ timer.start();
191+ while(!functor() && timer.elapsed() < ms) { QTest::qWait(10); }
192+ return functor();
193+ }
194+ guint exportMenuModel(GMenu** menu, GDBusConnection* connection, const QString& object_path, int submenuCount, int depth);
195+
196+public:
197+ GDBusConnection* m_connection;
198+ bool m_failed;
199+ bool m_connected;
200+ guint m_menuUid;
201+ GMenu* m_menu;
202+ UnityMenuModel* m_model;
203+};
204+
205+void recuseAddMenu(GMenu* menu, int subMenuCount, int depth_remaining)
206+{
207+ for (int i = 0; i < subMenuCount; i ++) {
208+ GMenuItem* item = g_menu_item_new("", NULL);
209+
210+ if (depth_remaining > 0) {
211+ GMenu* submenu = g_menu_new ();
212+ recuseAddMenu(submenu, subMenuCount, depth_remaining-1);
213+ g_menu_item_set_submenu (item, G_MENU_MODEL (submenu));
214+ }
215+
216+ g_menu_append_item (menu, item);
217+ }
218+}
219+
220+guint UnityMenuModelStackTest::exportMenuModel(GMenu** menu, GDBusConnection* connection, const QString& object_path, int submenuCount, int depth)
221+{
222+ *menu=g_menu_new();
223+ recuseAddMenu(*menu, submenuCount, depth);
224+
225+ QByteArray path = object_path.toUtf8();
226+
227+ return g_dbus_connection_export_menu_model (connection, path.constData(), G_MENU_MODEL (*menu), NULL);
228+}
229+
230+static void
231+on_bus_acquired (GDBusConnection *bus, const gchar *, gpointer user_data)
232+{
233+ UnityMenuModelStackTest* test = (UnityMenuModelStackTest*)user_data;
234+ test->m_connection = bus;
235+}
236+
237+static void
238+on_name_aquired (GDBusConnection*, const gchar*, gpointer user_data)
239+{
240+ UnityMenuModelStackTest* test = (UnityMenuModelStackTest*)user_data;
241+ test->m_connected = true;
242+ test->m_failed = false;
243+}
244+
245+
246+static void
247+on_name_lost (GDBusConnection*, const gchar*, gpointer user_data)
248+{
249+ UnityMenuModelStackTest* test = (UnityMenuModelStackTest*)user_data;
250+ test->m_connected = false;
251+ test->m_failed = true;
252+}
253+
254+QTEST_GUILESS_MAIN(UnityMenuModelStackTest)
255+#include "unitymenumodelstacktest.moc"