1 | /**************************************************************************** |
2 | ** |
3 | ** Copyright (C) 2016 The Qt Company Ltd. |
4 | ** Copyright (C) 2014 Olivier Goffart <ogoffart@woboq.com> |
5 | ** Contact: https://www.qt.io/licensing/ |
6 | ** |
7 | ** This file is part of the test suite of the Qt Toolkit. |
8 | ** |
9 | ** $QT_BEGIN_LICENSE:GPL-EXCEPT$ |
10 | ** Commercial License Usage |
11 | ** Licensees holding valid commercial Qt licenses may use this file in |
12 | ** accordance with the commercial license agreement provided with the |
13 | ** Software or, alternatively, in accordance with the terms contained in |
14 | ** a written agreement between you and The Qt Company. For licensing terms |
15 | ** and conditions see https://www.qt.io/terms-conditions. For further |
16 | ** information use the contact form at https://www.qt.io/contact-us. |
17 | ** |
18 | ** GNU General Public License Usage |
19 | ** Alternatively, this file may be used under the terms of the GNU |
20 | ** General Public License version 3 as published by the Free Software |
21 | ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT |
22 | ** included in the packaging of this file. Please review the following |
23 | ** information to ensure the GNU General Public License requirements will |
24 | ** be met: https://www.gnu.org/licenses/gpl-3.0.html. |
25 | ** |
26 | ** $QT_END_LICENSE$ |
27 | ** |
28 | ****************************************************************************/ |
29 | |
30 | |
31 | #include <QtTest/QtTest> |
32 | |
33 | #include <qobject.h> |
34 | #include <qmetaobject.h> |
35 | #include "wobjectimpl.h" |
36 | |
37 | class tst_QMetaMethod : public QObject |
38 | { |
39 | W_OBJECT(tst_QMetaMethod) |
40 | |
41 | private slots: |
42 | void method_data(); W_SLOT(method_data, W_Access::Private) |
43 | void method(); W_SLOT(method, W_Access::Private) |
44 | |
45 | void invalidMethod(); W_SLOT(invalidMethod, W_Access::Private) |
46 | |
47 | void comparisonOperators(); W_SLOT(comparisonOperators, W_Access::Private) |
48 | |
49 | void fromSignal(); W_SLOT(fromSignal, W_Access::Private) |
50 | |
51 | void gadget(); W_SLOT(gadget, W_Access::Private) |
52 | }; |
53 | |
54 | struct CustomType { }; |
55 | Q_DECLARE_METATYPE(CustomType) |
56 | W_REGISTER_ARGTYPE(CustomType) |
57 | |
58 | struct CustomUnregisteredType { }; |
59 | W_REGISTER_ARGTYPE(CustomUnregisteredType) |
60 | |
61 | Q_DECLARE_METATYPE(QMetaMethod::Access) |
62 | Q_DECLARE_METATYPE(QMetaMethod::MethodType) |
63 | |
64 | class MethodTestObject : public QObject |
65 | { |
66 | W_OBJECT(MethodTestObject) |
67 | public: |
68 | MethodTestObject(); |
69 | MethodTestObject(int constructorIntArg); |
70 | MethodTestObject(qreal constructorQRealArg); |
71 | MethodTestObject(const QString &constructorQStringArg); |
72 | MethodTestObject(CustomType constructorCustomTypeArg); |
73 | MethodTestObject(CustomUnregisteredType constructorCustomUnregisteredTypeArg); |
74 | MethodTestObject(bool boolArg, int intArg, uint uintArg, |
75 | qlonglong longlongArg, qulonglong ulonglongArg, |
76 | double doubleArg, long longArg, short shortArg, |
77 | char charArg, ulong ulongArg, ushort ushortArg, |
78 | uchar ucharArg, float floatArg); |
79 | MethodTestObject(bool, int); |
80 | |
81 | W_CONSTRUCTOR(); |
82 | W_CONSTRUCTOR(int); |
83 | W_CONSTRUCTOR(qreal); |
84 | W_CONSTRUCTOR(QString); |
85 | W_CONSTRUCTOR(CustomType); |
86 | W_CONSTRUCTOR(CustomUnregisteredType); |
87 | W_CONSTRUCTOR(bool, int, uint, qlonglong, qulonglong, double, long, short, char, ulong, ushort, uchar, float); |
88 | W_CONSTRUCTOR(bool, int); |
89 | |
90 | void voidInvokable(); |
91 | W_INVOKABLE(voidInvokable) |
92 | void voidInvokableInt(int voidInvokableIntArg); |
93 | W_INVOKABLE(voidInvokableInt) |
94 | void voidInvokableQReal(qreal voidInvokableQRealArg); |
95 | W_INVOKABLE(voidInvokableQReal) |
96 | void voidInvokableQString(const QString &voidInvokableQStringArg); |
97 | W_INVOKABLE(voidInvokableQString) |
98 | void voidInvokableCustomType(CustomType voidInvokableCustomTypeArg); |
99 | W_INVOKABLE(voidInvokableCustomType) |
100 | void voidInvokableCustomUnregisteredType(CustomUnregisteredType voidInvokableCustomUnregisteredTypeArg); |
101 | W_INVOKABLE(voidInvokableCustomUnregisteredType) |
102 | bool boolInvokable(); |
103 | W_INVOKABLE(boolInvokable) |
104 | qreal qrealInvokable(); |
105 | W_INVOKABLE(qrealInvokable) |
106 | QString qstringInvokable(); |
107 | W_INVOKABLE(qstringInvokable) |
108 | CustomType customTypeInvokable(); |
109 | W_INVOKABLE(customTypeInvokable) |
110 | CustomUnregisteredType customUnregisteredTypeInvokable(); |
111 | W_INVOKABLE(customUnregisteredTypeInvokable) |
112 | QVariant qvariantInvokableBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat( |
113 | bool boolArg, int intArg, uint uintArg, qlonglong longlongArg, qulonglong ulonglongArg, double doubleArg, |
114 | long longArg, short shortArg, char charArg, ulong ulongArg, ushort ushortArg, uchar ucharArg, float floatArg); |
115 | W_INVOKABLE(qvariantInvokableBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat) |
116 | void voidInvokableNoParameterNames(bool, int); |
117 | W_INVOKABLE(voidInvokableNoParameterNames) |
118 | public slots: |
119 | void voidSlot(); |
120 | W_SLOT(voidSlot) |
121 | void voidSlotInt(int voidSlotIntArg); |
122 | W_SLOT(voidSlotInt) |
123 | void voidSlotQReal(qreal voidSlotQRealArg); |
124 | W_SLOT(voidSlotQReal) |
125 | void voidSlotQString(const QString &voidSlotQStringArg); |
126 | W_SLOT(voidSlotQString) |
127 | void voidSlotCustomType(CustomType voidSlotCustomTypeArg); |
128 | W_SLOT(voidSlotCustomType) |
129 | void voidSlotCustomUnregisteredType(CustomUnregisteredType voidSlotCustomUnregisteredTypeArg); |
130 | W_SLOT(voidSlotCustomUnregisteredType) |
131 | bool boolSlot(); |
132 | W_SLOT(boolSlot) |
133 | qreal qrealSlot(); |
134 | W_SLOT(qrealSlot) |
135 | QString qstringSlot(); |
136 | W_SLOT(qstringSlot) |
137 | CustomType customTypeSlot(); |
138 | W_SLOT(customTypeSlot) |
139 | CustomUnregisteredType customUnregisteredTypeSlot(); |
140 | W_SLOT(customUnregisteredTypeSlot) |
141 | QVariant qvariantSlotBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat( |
142 | bool boolArg, int intArg, uint uintArg, qlonglong longlongArg, qulonglong ulonglongArg, double doubleArg, |
143 | long longArg, short shortArg, char charArg, ulong ulongArg, ushort ushortArg, uchar ucharArg, float floatArg); |
144 | W_SLOT(qvariantSlotBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat) |
145 | void voidSlotNoParameterNames(bool, int); |
146 | W_SLOT(voidSlotNoParameterNames) |
147 | signals: |
148 | void voidSignal() W_SIGNAL(voidSignal) |
149 | void voidSignalVoid(void) W_SIGNAL(voidSignalVoid) |
150 | void voidSignalInt(int voidSignalIntArg) W_SIGNAL(voidSignalInt,voidSignalIntArg) |
151 | void voidSignalQReal(qreal voidSignalQRealArg) W_SIGNAL(voidSignalQReal,voidSignalQRealArg) |
152 | void voidSignalQString(const QString &voidSignalQStringArg) W_SIGNAL(voidSignalQString,voidSignalQStringArg) |
153 | void voidSignalCustomType(CustomType voidSignalCustomTypeArg) W_SIGNAL(voidSignalCustomType,voidSignalCustomTypeArg) |
154 | void voidSignalCustomUnregisteredType(CustomUnregisteredType voidSignalCustomUnregisteredTypeArg) W_SIGNAL(voidSignalCustomUnregisteredType,voidSignalCustomUnregisteredTypeArg) |
155 | bool boolSignal() W_SIGNAL(boolSignal) |
156 | qreal qrealSignal() W_SIGNAL(qrealSignal) |
157 | QString qstringSignal() W_SIGNAL(qstringSignal) |
158 | CustomType customTypeSignal() W_SIGNAL(customTypeSignal) |
159 | CustomUnregisteredType customUnregisteredTypeSignal() W_SIGNAL(customUnregisteredTypeSignal) |
160 | QVariant qvariantSignalBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat( |
161 | bool boolArg, int intArg, uint uintArg, qlonglong longlongArg, qulonglong ulonglongArg, double doubleArg, |
162 | long longArg, short shortArg, char charArg, ulong ulongArg, ushort ushortArg, uchar ucharArg, float floatArg) |
163 | W_SIGNAL(qvariantSignalBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat, |
164 | boolArg, intArg, uintArg, longlongArg, ulonglongArg, doubleArg, |
165 | longArg, shortArg, charArg, ulongArg, ushortArg, ucharArg, floatArg) |
166 | void voidSignalNoParameterNames(bool _1, int _2) W_SIGNAL(voidSignalNoParameterNames, _1, _2) |
167 | }; |
168 | |
169 | MethodTestObject::MethodTestObject() {} |
170 | MethodTestObject::MethodTestObject(int) {} |
171 | MethodTestObject::MethodTestObject(qreal) {} |
172 | MethodTestObject::MethodTestObject(const QString &) {} |
173 | MethodTestObject::MethodTestObject(CustomType) {} |
174 | MethodTestObject::MethodTestObject(CustomUnregisteredType) {} |
175 | MethodTestObject::MethodTestObject(bool, int, uint, qlonglong, qulonglong, |
176 | double, long, short, char, ulong, ushort, |
177 | uchar, float) {} |
178 | MethodTestObject::MethodTestObject(bool, int) {} |
179 | |
180 | void MethodTestObject::voidInvokable() {} |
181 | void MethodTestObject::voidInvokableInt(int) {} |
182 | void MethodTestObject::voidInvokableQReal(qreal) {} |
183 | void MethodTestObject::voidInvokableQString(const QString &) {} |
184 | void MethodTestObject::voidInvokableCustomType(CustomType) {} |
185 | void MethodTestObject::voidInvokableCustomUnregisteredType(CustomUnregisteredType) {} |
186 | bool MethodTestObject::boolInvokable() { return true; } |
187 | qreal MethodTestObject::qrealInvokable() { return 1.0; } |
188 | QString MethodTestObject::qstringInvokable() { return QString(); } |
189 | CustomType MethodTestObject::customTypeInvokable() { return CustomType(); } |
190 | CustomUnregisteredType MethodTestObject::customUnregisteredTypeInvokable() |
191 | { |
192 | return CustomUnregisteredType(); |
193 | } |
194 | QVariant MethodTestObject::qvariantInvokableBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat( |
195 | bool, int, uint, qlonglong, qulonglong, double, long, short, char, ulong, ushort, uchar, float) |
196 | { |
197 | return QVariant(); |
198 | } |
199 | void MethodTestObject::voidInvokableNoParameterNames(bool, int) {} |
200 | |
201 | void MethodTestObject::voidSlot() {} |
202 | void MethodTestObject::voidSlotInt(int) {} |
203 | void MethodTestObject::voidSlotQReal(qreal) {} |
204 | void MethodTestObject::voidSlotQString(const QString &) {} |
205 | void MethodTestObject::voidSlotCustomType(CustomType) {} |
206 | void MethodTestObject::voidSlotCustomUnregisteredType(CustomUnregisteredType) {} |
207 | bool MethodTestObject::boolSlot() { return true; } |
208 | qreal MethodTestObject::qrealSlot() { return 1.0; } |
209 | QString MethodTestObject::qstringSlot() { return QString(); } |
210 | CustomType MethodTestObject::customTypeSlot() { return CustomType(); } |
211 | CustomUnregisteredType MethodTestObject::customUnregisteredTypeSlot() |
212 | { |
213 | return CustomUnregisteredType(); |
214 | } |
215 | QVariant MethodTestObject::qvariantSlotBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat( |
216 | bool, int, uint, qlonglong, qulonglong, double, long, short, char, ulong, ushort, uchar, float) |
217 | { |
218 | return QVariant(); |
219 | } |
220 | void MethodTestObject::voidSlotNoParameterNames(bool, int) {} |
221 | |
222 | void tst_QMetaMethod::method_data() |
223 | { |
224 | QTest::addColumn<QByteArray>("signature" ); |
225 | QTest::addColumn<int>("returnType" ); |
226 | QTest::addColumn<QByteArray>("returnTypeName" ); |
227 | QTest::addColumn<QList<int> >("parameterTypes" ); |
228 | QTest::addColumn<QList<QByteArray> >("parameterTypeNames" ); |
229 | QTest::addColumn<QList<QByteArray> >("parameterNames" ); |
230 | QTest::addColumn<QMetaMethod::Access>("access" ); |
231 | QTest::addColumn<QMetaMethod::MethodType>("methodType" ); |
232 | |
233 | QTest::newRow("voidSignal" ) |
234 | << QByteArray("voidSignal()" ) |
235 | << int(QMetaType::Void) << QByteArray("void" ) |
236 | << (QList<int>()) |
237 | << (QList<QByteArray>()) |
238 | << (QList<QByteArray>()) |
239 | << QMetaMethod::Public |
240 | << QMetaMethod::Signal; |
241 | |
242 | QTest::newRow("voidInvokable" ) |
243 | << QByteArray("voidInvokable()" ) |
244 | << int(QMetaType::Void) << QByteArray("void" ) |
245 | << (QList<int>()) |
246 | << (QList<QByteArray>()) |
247 | << (QList<QByteArray>()) |
248 | << QMetaMethod::Public |
249 | << QMetaMethod::Method; |
250 | |
251 | QTest::newRow("voidSlot" ) |
252 | << QByteArray("voidSlot()" ) |
253 | << int(QMetaType::Void) << QByteArray("void" ) |
254 | << (QList<int>()) |
255 | << (QList<QByteArray>()) |
256 | << (QList<QByteArray>()) |
257 | << QMetaMethod::Public |
258 | << QMetaMethod::Slot; |
259 | |
260 | QTest::newRow("MethodTestObject()" ) |
261 | << QByteArray("MethodTestObject()" ) |
262 | << int(QMetaType::UnknownType) << QByteArray("" ) |
263 | << (QList<int>()) |
264 | << (QList<QByteArray>()) |
265 | << (QList<QByteArray>()) |
266 | << QMetaMethod::Public |
267 | << QMetaMethod::Constructor; |
268 | |
269 | QTest::newRow("voidSignalVoid" ) |
270 | << QByteArray("voidSignalVoid()" ) |
271 | << int(QMetaType::Void) << QByteArray("void" ) |
272 | << QList<int>() |
273 | << QList<QByteArray>() |
274 | << QList<QByteArray>() |
275 | << QMetaMethod::Public |
276 | << QMetaMethod::Signal; |
277 | |
278 | QTest::newRow("voidSignalInt" ) |
279 | << QByteArray("voidSignalInt(int)" ) |
280 | << int(QMetaType::Void) << QByteArray("void" ) |
281 | << (QList<int>() << int(QMetaType::Int)) |
282 | << (QList<QByteArray>() << QByteArray("int" )) |
283 | << (QList<QByteArray>() << QByteArray("voidSignalIntArg" )) |
284 | << QMetaMethod::Public |
285 | << QMetaMethod::Signal; |
286 | |
287 | QTest::newRow("voidInvokableInt" ) |
288 | << QByteArray("voidInvokableInt(int)" ) |
289 | << int(QMetaType::Void) << QByteArray("void" ) |
290 | << (QList<int>() << int(QMetaType::Int)) |
291 | << (QList<QByteArray>() << QByteArray("int" )) |
292 | << (QList<QByteArray>() << QByteArray("voidInvokableIntArg" )) |
293 | << QMetaMethod::Public |
294 | << QMetaMethod::Method; |
295 | |
296 | QTest::newRow("voidSlotInt" ) |
297 | << QByteArray("voidSlotInt(int)" ) |
298 | << int(QMetaType::Void) << QByteArray("void" ) |
299 | << (QList<int>() << int(QMetaType::Int)) |
300 | << (QList<QByteArray>() << QByteArray("int" )) |
301 | << (QList<QByteArray>() << QByteArray("voidSlotIntArg" )) |
302 | << QMetaMethod::Public |
303 | << QMetaMethod::Slot; |
304 | |
305 | QTest::newRow("MethodTestObject(int)" ) |
306 | << QByteArray("MethodTestObject(int)" ) |
307 | << int(QMetaType::UnknownType) << QByteArray("" ) |
308 | << (QList<int>() << int(QMetaType::Int)) |
309 | << (QList<QByteArray>() << QByteArray("int" )) |
310 | << (QList<QByteArray>() << QByteArray("constructorIntArg" )) |
311 | << QMetaMethod::Public |
312 | << QMetaMethod::Constructor; |
313 | |
314 | QTest::newRow("voidSignalQReal" ) |
315 | << QByteArray("voidSignalQReal(qreal)" ) |
316 | << int(QMetaType::Void) << QByteArray("void" ) |
317 | << (QList<int>() << qMetaTypeId<qreal>()) |
318 | << (QList<QByteArray>() << QByteArray("qreal" )) |
319 | << (QList<QByteArray>() << QByteArray("voidSignalQRealArg" )) |
320 | << QMetaMethod::Public |
321 | << QMetaMethod::Signal; |
322 | |
323 | QTest::newRow("voidInvokableQReal" ) |
324 | << QByteArray("voidInvokableQReal(qreal)" ) |
325 | << int(QMetaType::Void) << QByteArray("void" ) |
326 | << (QList<int>() << qMetaTypeId<qreal>()) |
327 | << (QList<QByteArray>() << QByteArray("qreal" )) |
328 | << (QList<QByteArray>() << QByteArray("voidInvokableQRealArg" )) |
329 | << QMetaMethod::Public |
330 | << QMetaMethod::Method; |
331 | |
332 | QTest::newRow("voidSlotQReal" ) |
333 | << QByteArray("voidSlotQReal(qreal)" ) |
334 | << int(QMetaType::Void) << QByteArray("void" ) |
335 | << (QList<int>() << qMetaTypeId<qreal>()) |
336 | << (QList<QByteArray>() << QByteArray("qreal" )) |
337 | << (QList<QByteArray>() << QByteArray("voidSlotQRealArg" )) |
338 | << QMetaMethod::Public |
339 | << QMetaMethod::Slot; |
340 | |
341 | QTest::newRow("MethodTestObject(qreal)" ) |
342 | << QByteArray("MethodTestObject(qreal)" ) |
343 | << int(QMetaType::UnknownType) << QByteArray("" ) |
344 | << (QList<int>() << qMetaTypeId<qreal>()) |
345 | << (QList<QByteArray>() << QByteArray("qreal" )) |
346 | << (QList<QByteArray>() << QByteArray("constructorQRealArg" )) |
347 | << QMetaMethod::Public |
348 | << QMetaMethod::Constructor; |
349 | |
350 | QTest::newRow("voidSignalQString" ) |
351 | << QByteArray("voidSignalQString(QString)" ) |
352 | << int(QMetaType::Void) << QByteArray("void" ) |
353 | << (QList<int>() << int(QMetaType::QString)) |
354 | << (QList<QByteArray>() << QByteArray("QString" )) |
355 | << (QList<QByteArray>() << QByteArray("voidSignalQStringArg" )) |
356 | << QMetaMethod::Public |
357 | << QMetaMethod::Signal; |
358 | |
359 | QTest::newRow("voidInvokableQString" ) |
360 | << QByteArray("voidInvokableQString(QString)" ) |
361 | << int(QMetaType::Void) << QByteArray("void" ) |
362 | << (QList<int>() << int(QMetaType::QString)) |
363 | << (QList<QByteArray>() << QByteArray("QString" )) |
364 | << (QList<QByteArray>() << QByteArray("voidInvokableQStringArg" )) |
365 | << QMetaMethod::Public |
366 | << QMetaMethod::Method; |
367 | |
368 | QTest::newRow("voidSlotQString" ) |
369 | << QByteArray("voidSlotQString(QString)" ) |
370 | << int(QMetaType::Void) << QByteArray("void" ) |
371 | << (QList<int>() << int(QMetaType::QString)) |
372 | << (QList<QByteArray>() << QByteArray("QString" )) |
373 | << (QList<QByteArray>() << QByteArray("voidSlotQStringArg" )) |
374 | << QMetaMethod::Public |
375 | << QMetaMethod::Slot; |
376 | |
377 | QTest::newRow("MethodTestObject(QString)" ) |
378 | << QByteArray("MethodTestObject(QString)" ) |
379 | << int(QMetaType::UnknownType) << QByteArray("" ) |
380 | << (QList<int>() << int(QMetaType::QString)) |
381 | << (QList<QByteArray>() << QByteArray("QString" )) |
382 | << (QList<QByteArray>() << QByteArray("constructorQStringArg" )) |
383 | << QMetaMethod::Public |
384 | << QMetaMethod::Constructor; |
385 | |
386 | QTest::newRow("voidSignalCustomType" ) |
387 | << QByteArray("voidSignalCustomType(CustomType)" ) |
388 | << int(QMetaType::Void) << QByteArray("void" ) |
389 | << (QList<int>() << qMetaTypeId<CustomType>()) |
390 | << (QList<QByteArray>() << QByteArray("CustomType" )) |
391 | << (QList<QByteArray>() << QByteArray("voidSignalCustomTypeArg" )) |
392 | << QMetaMethod::Public |
393 | << QMetaMethod::Signal; |
394 | |
395 | QTest::newRow("voidInvokableCustomType" ) |
396 | << QByteArray("voidInvokableCustomType(CustomType)" ) |
397 | << int(QMetaType::Void) << QByteArray("void" ) |
398 | << (QList<int>() << qMetaTypeId<CustomType>()) |
399 | << (QList<QByteArray>() << QByteArray("CustomType" )) |
400 | << (QList<QByteArray>() << QByteArray("voidInvokableCustomTypeArg" )) |
401 | << QMetaMethod::Public |
402 | << QMetaMethod::Method; |
403 | |
404 | QTest::newRow("voidSlotCustomType" ) |
405 | << QByteArray("voidSlotCustomType(CustomType)" ) |
406 | << int(QMetaType::Void) << QByteArray("void" ) |
407 | << (QList<int>() << qMetaTypeId<CustomType>()) |
408 | << (QList<QByteArray>() << QByteArray("CustomType" )) |
409 | << (QList<QByteArray>() << QByteArray("voidSlotCustomTypeArg" )) |
410 | << QMetaMethod::Public |
411 | << QMetaMethod::Slot; |
412 | |
413 | QTest::newRow("MethodTestObject(CustomType)" ) |
414 | << QByteArray("MethodTestObject(CustomType)" ) |
415 | << int(QMetaType::UnknownType) << QByteArray("" ) |
416 | << (QList<int>() << qMetaTypeId<CustomType>()) |
417 | << (QList<QByteArray>() << QByteArray("CustomType" )) |
418 | << (QList<QByteArray>() << QByteArray("constructorCustomTypeArg" )) |
419 | << QMetaMethod::Public |
420 | << QMetaMethod::Constructor; |
421 | |
422 | QTest::newRow("voidSignalCustomUnregisteredType" ) |
423 | << QByteArray("voidSignalCustomUnregisteredType(CustomUnregisteredType)" ) |
424 | << int(QMetaType::Void) << QByteArray("void" ) |
425 | << (QList<int>() << 0) |
426 | << (QList<QByteArray>() << QByteArray("CustomUnregisteredType" )) |
427 | << (QList<QByteArray>() << QByteArray("voidSignalCustomUnregisteredTypeArg" )) |
428 | << QMetaMethod::Public |
429 | << QMetaMethod::Signal; |
430 | |
431 | QTest::newRow("voidInvokableCustomUnregisteredType" ) |
432 | << QByteArray("voidInvokableCustomUnregisteredType(CustomUnregisteredType)" ) |
433 | << int(QMetaType::Void) << QByteArray("void" ) |
434 | << (QList<int>() << 0) |
435 | << (QList<QByteArray>() << QByteArray("CustomUnregisteredType" )) |
436 | << (QList<QByteArray>() << QByteArray("voidInvokableCustomUnregisteredTypeArg" )) |
437 | << QMetaMethod::Public |
438 | << QMetaMethod::Method; |
439 | |
440 | QTest::newRow("voidSlotCustomUnregisteredType" ) |
441 | << QByteArray("voidSlotCustomUnregisteredType(CustomUnregisteredType)" ) |
442 | << int(QMetaType::Void) << QByteArray("void" ) |
443 | << (QList<int>() << 0) |
444 | << (QList<QByteArray>() << QByteArray("CustomUnregisteredType" )) |
445 | << (QList<QByteArray>() << QByteArray("voidSlotCustomUnregisteredTypeArg" )) |
446 | << QMetaMethod::Public |
447 | << QMetaMethod::Slot; |
448 | |
449 | QTest::newRow("MethodTestObject(CustomUnregisteredType)" ) |
450 | << QByteArray("MethodTestObject(CustomUnregisteredType)" ) |
451 | << int(QMetaType::UnknownType) << QByteArray("" ) |
452 | << (QList<int>() << 0) |
453 | << (QList<QByteArray>() << QByteArray("CustomUnregisteredType" )) |
454 | << (QList<QByteArray>() << QByteArray("constructorCustomUnregisteredTypeArg" )) |
455 | << QMetaMethod::Public |
456 | << QMetaMethod::Constructor; |
457 | |
458 | QTest::newRow("boolSignal" ) |
459 | << QByteArray("boolSignal()" ) |
460 | << int(QMetaType::Bool) << QByteArray("bool" ) |
461 | << (QList<int>()) |
462 | << (QList<QByteArray>()) |
463 | << (QList<QByteArray>()) |
464 | << QMetaMethod::Public |
465 | << QMetaMethod::Signal; |
466 | |
467 | QTest::newRow("boolInvokable" ) |
468 | << QByteArray("boolInvokable()" ) |
469 | << int(QMetaType::Bool) << QByteArray("bool" ) |
470 | << (QList<int>()) |
471 | << (QList<QByteArray>()) |
472 | << (QList<QByteArray>()) |
473 | << QMetaMethod::Public |
474 | << QMetaMethod::Method; |
475 | |
476 | QTest::newRow("boolSlot" ) |
477 | << QByteArray("boolSlot()" ) |
478 | << int(QMetaType::Bool) << QByteArray("bool" ) |
479 | << (QList<int>()) |
480 | << (QList<QByteArray>()) |
481 | << (QList<QByteArray>()) |
482 | << QMetaMethod::Public |
483 | << QMetaMethod::Slot; |
484 | |
485 | QTest::newRow("qrealSignal" ) |
486 | << QByteArray("qrealSignal()" ) |
487 | << int(QMetaType::QReal) << QByteArray("qreal" ) |
488 | << (QList<int>()) |
489 | << (QList<QByteArray>()) |
490 | << (QList<QByteArray>()) |
491 | << QMetaMethod::Public |
492 | << QMetaMethod::Signal; |
493 | |
494 | QTest::newRow("qrealInvokable" ) |
495 | << QByteArray("qrealInvokable()" ) |
496 | << int(QMetaType::QReal) << QByteArray("qreal" ) |
497 | << (QList<int>()) |
498 | << (QList<QByteArray>()) |
499 | << (QList<QByteArray>()) |
500 | << QMetaMethod::Public |
501 | << QMetaMethod::Method; |
502 | |
503 | QTest::newRow("qrealSlot" ) |
504 | << QByteArray("qrealSlot()" ) |
505 | << int(QMetaType::QReal) << QByteArray("qreal" ) |
506 | << (QList<int>()) |
507 | << (QList<QByteArray>()) |
508 | << (QList<QByteArray>()) |
509 | << QMetaMethod::Public |
510 | << QMetaMethod::Slot; |
511 | |
512 | QTest::newRow("qstringSignal" ) |
513 | << QByteArray("qstringSignal()" ) |
514 | << int(QMetaType::QString) << QByteArray("QString" ) |
515 | << (QList<int>()) |
516 | << (QList<QByteArray>()) |
517 | << (QList<QByteArray>()) |
518 | << QMetaMethod::Public |
519 | << QMetaMethod::Signal; |
520 | |
521 | QTest::newRow("qstringInvokable" ) |
522 | << QByteArray("qstringInvokable()" ) |
523 | << int(QMetaType::QString) << QByteArray("QString" ) |
524 | << (QList<int>()) |
525 | << (QList<QByteArray>()) |
526 | << (QList<QByteArray>()) |
527 | << QMetaMethod::Public |
528 | << QMetaMethod::Method; |
529 | |
530 | QTest::newRow("qstringSlot" ) |
531 | << QByteArray("qstringSlot()" ) |
532 | << int(QMetaType::QString) << QByteArray("QString" ) |
533 | << (QList<int>()) |
534 | << (QList<QByteArray>()) |
535 | << (QList<QByteArray>()) |
536 | << QMetaMethod::Public |
537 | << QMetaMethod::Slot; |
538 | |
539 | { |
540 | QList<int> parameterTypes = QList<int>() |
541 | << int(QMetaType::Bool) << int(QMetaType::Int) << int(QMetaType::UInt) |
542 | << int(QMetaType::LongLong) << int(QMetaType::ULongLong) << int(QMetaType::Double) |
543 | << int(QMetaType::Long) << int(QMetaType::Short) << int(QMetaType::Char) |
544 | << int(QMetaType::ULong) << int(QMetaType::UShort) << int(QMetaType::UChar) |
545 | << int(QMetaType::Float); |
546 | QList<QByteArray> parameterTypeNames = QList<QByteArray>() |
547 | << QByteArray("bool" ) << QByteArray("int" ) << QByteArray("uint" ) |
548 | << QByteArray("qlonglong" ) << QByteArray("qulonglong" ) << QByteArray("double" ) |
549 | << QByteArray("long" ) << QByteArray("short" ) << QByteArray("char" ) << QByteArray("ulong" ) |
550 | << QByteArray("ushort" ) << QByteArray("uchar" ) << QByteArray("float" ); |
551 | QList<QByteArray> parameterNames = QList<QByteArray>() |
552 | << QByteArray("boolArg" ) << QByteArray("intArg" ) << QByteArray("uintArg" ) |
553 | << QByteArray("longlongArg" ) << QByteArray("ulonglongArg" ) << QByteArray("doubleArg" ) |
554 | << QByteArray("longArg" ) << QByteArray("shortArg" ) << QByteArray("charArg" ) |
555 | << QByteArray("ulongArg" ) << QByteArray("ushortArg" ) << QByteArray("ucharArg" ) |
556 | << QByteArray("floatArg" ); |
557 | |
558 | QTest::newRow("qvariantSignalBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat" ) |
559 | << QByteArray("qvariantSignalBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat(" |
560 | "bool,int,uint,qlonglong,qulonglong,double,long,short,char,ulong,ushort,uchar,float)" ) |
561 | << int(QMetaType::QVariant) << QByteArray("QVariant" ) |
562 | << parameterTypes << parameterTypeNames << parameterNames |
563 | << QMetaMethod::Public |
564 | << QMetaMethod::Signal; |
565 | |
566 | QTest::newRow("qvariantInvokableBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat" ) |
567 | << QByteArray("qvariantInvokableBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat(" |
568 | "bool,int,uint,qlonglong,qulonglong,double,long,short,char,ulong,ushort,uchar,float)" ) |
569 | << int(QMetaType::QVariant) << QByteArray("QVariant" ) |
570 | << parameterTypes << parameterTypeNames << parameterNames |
571 | << QMetaMethod::Public |
572 | << QMetaMethod::Method; |
573 | |
574 | QTest::newRow("qvariantSlotBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat" ) |
575 | << QByteArray("qvariantSlotBoolIntUIntLonglongULonglongDoubleLongShortCharUlongUshortUcharFloat(" |
576 | "bool,int,uint,qlonglong,qulonglong,double,long,short,char,ulong,ushort,uchar,float)" ) |
577 | << int(QMetaType::QVariant) << QByteArray("QVariant" ) |
578 | << parameterTypes << parameterTypeNames << parameterNames |
579 | << QMetaMethod::Public |
580 | << QMetaMethod::Slot; |
581 | |
582 | QTest::newRow("MethodTestObject(bool,int,uint,qlonglong,qulonglong,double,long,short,char,ulong,ushort,uchar,float)" ) |
583 | << QByteArray("MethodTestObject(bool,int,uint,qlonglong,qulonglong,double,long,short,char,ulong,ushort,uchar,float)" ) |
584 | << int(QMetaType::UnknownType) << QByteArray("" ) |
585 | << parameterTypes << parameterTypeNames << parameterNames |
586 | << QMetaMethod::Public |
587 | << QMetaMethod::Constructor; |
588 | } |
589 | |
590 | QTest::newRow("voidSignalNoParameterNames" ) |
591 | << QByteArray("voidSignalNoParameterNames(bool,int)" ) |
592 | << int(QMetaType::Void) << QByteArray("void" ) |
593 | << (QList<int>() << int(QMetaType::Bool) << int(QMetaType::Int)) |
594 | << (QList<QByteArray>() << QByteArray("bool" ) << QByteArray("int" )) |
595 | << (QList<QByteArray>() << QByteArray("" ) << QByteArray("" )) |
596 | << QMetaMethod::Public |
597 | << QMetaMethod::Signal; |
598 | |
599 | QTest::newRow("voidInvokableNoParameterNames" ) |
600 | << QByteArray("voidInvokableNoParameterNames(bool,int)" ) |
601 | << int(QMetaType::Void) << QByteArray("void" ) |
602 | << (QList<int>() << int(QMetaType::Bool) << int(QMetaType::Int)) |
603 | << (QList<QByteArray>() << QByteArray("bool" ) << QByteArray("int" )) |
604 | << (QList<QByteArray>() << QByteArray("" ) << QByteArray("" )) |
605 | << QMetaMethod::Public |
606 | << QMetaMethod::Method; |
607 | |
608 | QTest::newRow("voidSlotNoParameterNames" ) |
609 | << QByteArray("voidSlotNoParameterNames(bool,int)" ) |
610 | << int(QMetaType::Void) << QByteArray("void" ) |
611 | << (QList<int>() << int(QMetaType::Bool) << int(QMetaType::Int)) |
612 | << (QList<QByteArray>() << QByteArray("bool" ) << QByteArray("int" )) |
613 | << (QList<QByteArray>() << QByteArray("" ) << QByteArray("" )) |
614 | << QMetaMethod::Public |
615 | << QMetaMethod::Slot; |
616 | |
617 | QTest::newRow("MethodTestObject(bool,int)" ) |
618 | << QByteArray("MethodTestObject(bool,int)" ) |
619 | << int(QMetaType::UnknownType) << QByteArray("" ) |
620 | << (QList<int>() << int(QMetaType::Bool) << int(QMetaType::Int)) |
621 | << (QList<QByteArray>() << QByteArray("bool" ) << QByteArray("int" )) |
622 | << (QList<QByteArray>() << QByteArray("" ) << QByteArray("" )) |
623 | << QMetaMethod::Public |
624 | << QMetaMethod::Constructor; |
625 | } |
626 | |
627 | void tst_QMetaMethod::method() |
628 | { |
629 | QFETCH(QByteArray, signature); |
630 | QFETCH(int, returnType); |
631 | QFETCH(QByteArray, returnTypeName); |
632 | QFETCH(QList<int>, parameterTypes); |
633 | QFETCH(QList<QByteArray>, parameterTypeNames); |
634 | QFETCH(QList<QByteArray>, parameterNames); |
635 | QFETCH(QMetaMethod::MethodType, methodType); |
636 | QFETCH(QMetaMethod::Access, access); |
637 | |
638 | QCOMPARE(parameterTypes.size(), parameterTypeNames.size()); |
639 | QCOMPARE(parameterTypes.size(), parameterNames.size()); |
640 | |
641 | const QMetaObject *mo = &MethodTestObject::staticMetaObject; |
642 | int index = (methodType == QMetaMethod::Constructor) |
643 | ? mo->indexOfConstructor(signature) : mo->indexOfMethod(signature); |
644 | QVERIFY(index != -1); |
645 | QMetaMethod method = (methodType == QMetaMethod::Constructor) |
646 | ? mo->constructor(index) : mo->method(index); |
647 | QVERIFY(method.isValid()); |
648 | QCOMPARE(method.methodType(), methodType); |
649 | QCOMPARE(method.access(), access); |
650 | |
651 | QVERIFY(!method.methodSignature().isEmpty()); |
652 | if (method.methodSignature() != signature) { |
653 | // QMetaMethod should always produce a semantically equivalent signature |
654 | int signatureIndex = (methodType == QMetaMethod::Constructor) |
655 | ? mo->indexOfConstructor(method.methodSignature()) |
656 | : mo->indexOfMethod(method.methodSignature()); |
657 | QCOMPARE(signatureIndex, index); |
658 | } |
659 | |
660 | QByteArray computedName = signature.left(signature.indexOf('(')); |
661 | QCOMPARE(method.name(), computedName); |
662 | |
663 | QCOMPARE(method.tag(), "" ); |
664 | QCOMPARE(method.returnType(), returnType); |
665 | QVERIFY(method.typeName() != 0); |
666 | if (QByteArray(method.typeName()) != returnTypeName) { |
667 | // QMetaMethod should always produce a semantically equivalent typename |
668 | QCOMPARE(QMetaType::type(method.typeName()), QMetaType::type(returnTypeName)); |
669 | } |
670 | |
671 | if (method.parameterTypes() != parameterTypeNames) { |
672 | // QMetaMethod should always produce semantically equivalent typenames |
673 | QList<QByteArray> actualTypeNames = method.parameterTypes(); |
674 | QCOMPARE(actualTypeNames.size(), parameterTypeNames.size()); |
675 | for (int i = 0; i < parameterTypeNames.size(); ++i) { |
676 | QCOMPARE(QMetaType::type(actualTypeNames.at(i)), |
677 | QMetaType::type(parameterTypeNames.at(i))); |
678 | } |
679 | } |
680 | //QCOMPARE(method.parameterNames(), parameterNames); // ### not supported by W_INVOKABLE |
681 | |
682 | QCOMPARE(method.parameterCount(), parameterTypes.size()); |
683 | for (int i = 0; i < parameterTypes.size(); ++i) |
684 | QCOMPARE(method.parameterType(i), parameterTypes.at(i)); |
685 | |
686 | { |
687 | QVector<int> actualParameterTypes(parameterTypes.size()); |
688 | method.getParameterTypes(actualParameterTypes.data()); |
689 | for (int i = 0; i < parameterTypes.size(); ++i) |
690 | QCOMPARE(actualParameterTypes.at(i), parameterTypes.at(i)); |
691 | } |
692 | |
693 | // Bogus indexes |
694 | QCOMPARE(method.parameterType(-1), 0); |
695 | QCOMPARE(method.parameterType(parameterTypes.size()), 0); |
696 | } |
697 | |
698 | void tst_QMetaMethod::invalidMethod() |
699 | { |
700 | QMetaMethod method; |
701 | QVERIFY(!method.isValid()); |
702 | |
703 | QMetaMethod method2 = staticMetaObject.method(staticMetaObject.methodCount()); |
704 | QVERIFY(!method2.isValid()); |
705 | |
706 | QMetaMethod method3 = staticMetaObject.method(-1); |
707 | QVERIFY(!method3.isValid()); |
708 | } |
709 | |
710 | void tst_QMetaMethod::comparisonOperators() |
711 | { |
712 | static const QMetaObject *mo = &MethodTestObject::staticMetaObject; |
713 | for (int x = 0; x < 2; ++x) { |
714 | int count = x ? mo->constructorCount() : mo->methodCount(); |
715 | for (int i = 0; i < count; ++i) { |
716 | QMetaMethod method = x ? mo->constructor(i) : mo->method(i); |
717 | const QMetaObject *methodMo = method.enclosingMetaObject(); |
718 | for (int j = 0; j < count; ++j) { |
719 | QMetaMethod other = x ? mo->constructor(j) : mo->method(j); |
720 | bool expectedEqual = ((methodMo == other.enclosingMetaObject()) |
721 | && (i == j)); |
722 | QCOMPARE(method == other, expectedEqual); |
723 | QCOMPARE(method != other, !expectedEqual); |
724 | QCOMPARE(other == method, expectedEqual); |
725 | QCOMPARE(other != method, !expectedEqual); |
726 | } |
727 | |
728 | QVERIFY(method != QMetaMethod()); |
729 | QVERIFY(QMetaMethod() != method); |
730 | QVERIFY(!(method == QMetaMethod())); |
731 | QVERIFY(!(QMetaMethod() == method)); |
732 | } |
733 | } |
734 | |
735 | // Constructors and normal methods with identical index should not |
736 | // compare equal |
737 | for (int i = 0; i < qMin(mo->methodCount(), mo->constructorCount()); ++i) { |
738 | QMetaMethod method = mo->method(i); |
739 | QMetaMethod constructor = mo->constructor(i); |
740 | QVERIFY(method != constructor); |
741 | QVERIFY(!(method == constructor)); |
742 | } |
743 | } |
744 | |
745 | void tst_QMetaMethod::fromSignal() |
746 | { |
747 | #define FROMSIGNAL_HELPER(ObjectType, Name, Arguments) { \ |
748 | const QMetaObject *signalMeta = &ObjectType::staticMetaObject; \ |
749 | QCOMPARE(QMetaMethod::fromSignal(&ObjectType::Name), \ |
750 | signalMeta->method(signalMeta->indexOfSignal(QMetaObject::normalizedSignature(#Name #Arguments)))); \ |
751 | } |
752 | |
753 | FROMSIGNAL_HELPER(MethodTestObject, voidSignal, ()) |
754 | FROMSIGNAL_HELPER(MethodTestObject, voidSignalQString, (const QString&)) |
755 | FROMSIGNAL_HELPER(QObject, destroyed, (QObject*)) |
756 | FROMSIGNAL_HELPER(QObject, objectNameChanged, (const QString &)) |
757 | |
758 | // Inherited from QObject |
759 | FROMSIGNAL_HELPER(MethodTestObject, destroyed, (QObject*)) |
760 | FROMSIGNAL_HELPER(MethodTestObject, objectNameChanged, (const QString &)) |
761 | |
762 | // Methods that are not signals; fromSignal should return invalid method |
763 | FROMSIGNAL_HELPER(MethodTestObject, voidSlot, ()) |
764 | FROMSIGNAL_HELPER(QObject, deleteLater, ()) |
765 | |
766 | #undef FROMSIGNAL_HELPER |
767 | } |
768 | |
769 | class MyGadget { |
770 | W_GADGET(MyGadget) |
771 | public: |
772 | QString m_value; |
773 | void setValue(const QString &value) { m_value = value; } |
774 | W_INVOKABLE(setValue) |
775 | QString getValue() { return m_value; } |
776 | W_INVOKABLE(getValue) |
777 | }; |
778 | |
779 | void tst_QMetaMethod::gadget() |
780 | { |
781 | int idx; |
782 | |
783 | idx = MyGadget::staticMetaObject.indexOfMethod("setValue(QString)" ); |
784 | QVERIFY(idx >= 0); |
785 | QMetaMethod setValueMethod = MyGadget::staticMetaObject.method(idx); |
786 | QVERIFY(setValueMethod.isValid()); |
787 | |
788 | idx = MyGadget::staticMetaObject.indexOfMethod("getValue()" ); |
789 | QVERIFY(idx >= 0); |
790 | QMetaMethod getValueMethod = MyGadget::staticMetaObject.method(idx); |
791 | QVERIFY(getValueMethod.isValid()); |
792 | |
793 | { |
794 | MyGadget gadget; |
795 | QString string; |
796 | |
797 | QVERIFY(getValueMethod.invokeOnGadget(&gadget, Q_RETURN_ARG(QString, string))); |
798 | QCOMPARE(string, gadget.m_value); |
799 | |
800 | QVERIFY(setValueMethod.invokeOnGadget(&gadget, Q_ARG(QString, QLatin1String("hello" )))); |
801 | QCOMPARE(gadget.m_value, QLatin1String("hello" )); |
802 | |
803 | QVERIFY(getValueMethod.invokeOnGadget(&gadget, Q_RETURN_ARG(QString, string))); |
804 | QCOMPARE(string, gadget.m_value); |
805 | } |
806 | |
807 | { |
808 | // Call with null should not crash |
809 | MyGadget *gadget = nullptr; |
810 | QString string; |
811 | QVERIFY(!setValueMethod.invokeOnGadget(gadget, Q_ARG(QString, QLatin1String("hi" )))); |
812 | QVERIFY(!getValueMethod.invokeOnGadget(gadget, Q_RETURN_ARG(QString, string))); |
813 | } |
814 | } |
815 | |
816 | W_OBJECT_IMPL(tst_QMetaMethod) |
817 | W_OBJECT_IMPL(MethodTestObject) |
818 | W_GADGET_IMPL(MyGadget) |
819 | |
820 | |
821 | QTEST_MAIN(tst_QMetaMethod) |
822 | |