diff options
Diffstat (limited to 'tests/auto/qml')
-rw-r--r-- | tests/auto/qml/qjsengine/tst_qjsengine.cpp | 11 | ||||
-rw-r--r-- | tests/auto/qml/qml.pro | 2 | ||||
-rw-r--r-- | tests/auto/qml/qqmlecmascript/testtypes.cpp | 2 | ||||
-rw-r--r-- | tests/auto/qml/qqmlecmascript/testtypes.h | 8 | ||||
-rw-r--r-- | tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp | 107 | ||||
-rw-r--r-- | tests/auto/qml/qqmlengine/tst_qqmlengine.cpp | 29 | ||||
-rw-r--r-- | tests/auto/qml/qqmllanguage/testtypes.cpp | 4 | ||||
-rw-r--r-- | tests/auto/qml/qqmllanguage/testtypes.h | 54 | ||||
-rw-r--r-- | tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp | 59 | ||||
-rw-r--r-- | tests/auto/qml/qqmllistreference/data/propertyList.qml | 12 | ||||
-rw-r--r-- | tests/auto/qml/qqmllistreference/qqmllistreference.pro | 2 | ||||
-rw-r--r-- | tests/auto/qml/qqmllistreference/tst_qqmllistreference.cpp | 24 | ||||
-rw-r--r-- | tests/auto/qml/qqmlmetatype/data/testExternalEnums.qml | 12 | ||||
-rw-r--r-- | tests/auto/qml/qqmlmetatype/tst_qqmlmetatype.cpp | 33 | ||||
-rw-r--r-- | tests/auto/qml/qqmlproperty/data/aliasPropertyBindings2.qml | 23 | ||||
-rw-r--r-- | tests/auto/qml/qqmlproperty/tst_qqmlproperty.cpp | 40 | ||||
-rw-r--r-- | tests/auto/qml/v4misc/tst_v4misc.cpp | 92 |
17 files changed, 492 insertions, 22 deletions
diff --git a/tests/auto/qml/qjsengine/tst_qjsengine.cpp b/tests/auto/qml/qjsengine/tst_qjsengine.cpp index 82bc3d0c59..39f6d80fa0 100644 --- a/tests/auto/qml/qjsengine/tst_qjsengine.cpp +++ b/tests/auto/qml/qjsengine/tst_qjsengine.cpp @@ -566,10 +566,6 @@ void tst_QJSEngine::newDate() QCOMPARE(date.isDate(), true); QCOMPARE(date.isObject(), true); QVERIFY(!date.isCallable()); - // prototype should be Date.prototype - QVERIFY(!date.prototype().isUndefined()); - QCOMPARE(date.prototype().isDate(), true); - QCOMPARE(date.prototype().strictlyEquals(eng.evaluate("Date.prototype")), true); } { @@ -578,10 +574,6 @@ void tst_QJSEngine::newDate() QVERIFY(!date.isUndefined()); QCOMPARE(date.isDate(), true); QCOMPARE(date.isObject(), true); - // prototype should be Date.prototype - QVERIFY(!date.prototype().isUndefined()); - QCOMPARE(date.prototype().isDate(), true); - QCOMPARE(date.prototype().strictlyEquals(eng.evaluate("Date.prototype")), true); QCOMPARE(date.toDateTime(), dt); } @@ -1099,7 +1091,7 @@ void tst_QJSEngine::builtinFunctionNames_data() QTest::newRow("Date.prototype.setFullYear") << QString("Date.prototype.setFullYear") << QString("setFullYear"); QTest::newRow("Date.prototype.setUTCFullYear") << QString("Date.prototype.setUTCFullYear") << QString("setUTCFullYear"); QTest::newRow("Date.prototype.toUTCString") << QString("Date.prototype.toUTCString") << QString("toUTCString"); - QTest::newRow("Date.prototype.toGMTString") << QString("Date.prototype.toGMTString") << QString("toGMTString"); + QTest::newRow("Date.prototype.toGMTString") << QString("Date.prototype.toGMTString") << QString("toUTCString"); // yes, this is per spec QTest::newRow("Error") << QString("Error") << QString("Error"); // QTest::newRow("Error.prototype.backtrace") << QString("Error.prototype.backtrace") << QString("backtrace"); @@ -1177,6 +1169,7 @@ void tst_QJSEngine::builtinFunctionNames_data() QTest::newRow("String.prototype.lastIndexOf") << QString("String.prototype.lastIndexOf") << QString("lastIndexOf"); QTest::newRow("String.prototype.localeCompare") << QString("String.prototype.localeCompare") << QString("localeCompare"); QTest::newRow("String.prototype.match") << QString("String.prototype.match") << QString("match"); + QTest::newRow("String.prototype.repeat") << QString("String.prototype.repeat") << QString("repeat"); QTest::newRow("String.prototype.replace") << QString("String.prototype.replace") << QString("replace"); QTest::newRow("String.prototype.search") << QString("String.prototype.search") << QString("search"); QTest::newRow("String.prototype.slice") << QString("String.prototype.slice") << QString("slice"); diff --git a/tests/auto/qml/qml.pro b/tests/auto/qml/qml.pro index 04e4b04114..7d182b7255 100644 --- a/tests/auto/qml/qml.pro +++ b/tests/auto/qml/qml.pro @@ -73,7 +73,7 @@ qtHaveModule(widgets) { SUBDIRS += $$PUBLICTESTS \ qqmlextensionplugin SUBDIRS += $$METATYPETESTS -!qtConfig(process) { +qtConfig(process) { !contains(QT_CONFIG, no-qml-debug): SUBDIRS += debugger SUBDIRS += qmllint qmlplugindump } diff --git a/tests/auto/qml/qqmlecmascript/testtypes.cpp b/tests/auto/qml/qqmlecmascript/testtypes.cpp index d9ddcd71a7..63c2918325 100644 --- a/tests/auto/qml/qqmlecmascript/testtypes.cpp +++ b/tests/auto/qml/qqmlecmascript/testtypes.cpp @@ -515,6 +515,8 @@ void registerTypes() qmlRegisterType<QObjectContainer>("Qt.test", 1, 0, "QObjectContainer"); qmlRegisterType<QObjectContainerWithGCOnAppend>("Qt.test", 1, 0, "QObjectContainerWithGCOnAppend"); qmlRegisterType<FloatingQObject>("Qt.test", 1, 0, "FloatingQObject"); + + qmlRegisterType<ClashingNames>("Qt.test", 1, 0, "ClashingNames"); } #include "testtypes.moc" diff --git a/tests/auto/qml/qqmlecmascript/testtypes.h b/tests/auto/qml/qqmlecmascript/testtypes.h index 1f7f3344ef..eedeb66647 100644 --- a/tests/auto/qml/qqmlecmascript/testtypes.h +++ b/tests/auto/qml/qqmlecmascript/testtypes.h @@ -1714,6 +1714,14 @@ public: virtual void componentComplete(); }; +class ClashingNames : public QObject +{ + Q_OBJECT + Q_PROPERTY(bool clashes READ clashes CONSTANT) +public: + Q_INVOKABLE bool clashes() const { return true; } +}; + void registerTypes(); #endif // TESTTYPES_H diff --git a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp index 1f0248c258..91ceed7697 100644 --- a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp +++ b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp @@ -47,6 +47,7 @@ #include <private/qv4runtime_p.h> #include <private/qv4object_p.h> #include <private/qqmlcomponentattached_p.h> +#include <private/qv4objectiterator_p.h> #ifdef Q_CC_MSVC #define NO_INLINE __declspec(noinline) @@ -261,6 +262,7 @@ private slots: void nonNotifyable(); void deleteWhileBindingRunning(); void callQtInvokables(); + void resolveClashingProperties(); void invokableObjectArg(); void invokableObjectRet(); void invokableEnumRet(); @@ -336,6 +338,8 @@ private slots: void instanceof(); void constkw_data(); void constkw(); + void redefineGlobalProp(); + void freeze_empty_object(); private: // static void propertyVarWeakRefCallback(v8::Persistent<v8::Value> object, void* parameter); @@ -2989,6 +2993,48 @@ void tst_qqmlecmascript::callQtInvokables() QVERIFY(callback.isCallable()); } +void tst_qqmlecmascript::resolveClashingProperties() +{ + ClashingNames *o = new ClashingNames(); + QQmlEngine qmlengine; + QQmlEnginePrivate *ep = QQmlEnginePrivate::get(&qmlengine); + + QV4::ExecutionEngine *engine = QV8Engine::getV4(ep->v8engine()); + QV4::Scope scope(engine); + + QV4::ScopedValue object(scope, QV4::QObjectWrapper::wrap(engine, o)); + QV4::ObjectIterator it(scope, object->as<QV4::Object>(), QV4::ObjectIterator::EnumerableOnly); + QV4::ScopedValue name(scope); + QV4::ScopedValue value(scope); + + bool seenProperty = false; + bool seenMethod = false; + while (true) { + QV4::Value v; + name = it.nextPropertyNameAsString(&v); + if (name->isNull()) + break; + QString key = name->toQStringNoThrow(); + if (key == QLatin1String("clashes")) { + value = v; + QV4::ScopedValue typeString(scope, QV4::Runtime::method_typeofValue(engine, value)); + QString type = typeString->toQStringNoThrow(); + if (type == QLatin1String("boolean")) { + QVERIFY(!seenProperty); + seenProperty = true; + } else if (type == QLatin1String("function")) { + QVERIFY(!seenMethod); + seenMethod = true; + } else { + QFAIL(qPrintable(QString::fromLatin1("found 'clashes' property of type %1") + .arg(type))); + } + } + } + QVERIFY(seenProperty); + QVERIFY(seenMethod); +} + // QTBUG-13047 (check that you can pass registered object types as args) void tst_qqmlecmascript::invokableObjectArg() { @@ -8208,6 +8254,12 @@ void tst_qqmlecmascript::constkw_data() "v + i\n" << false << QVariant(25); + QTest::newRow("const-multiple-scopes-same-var") + << "const v = 3\n" + "function f() { const v = 1; return v; }\n" + "v + f()\n" + << false + << QVariant(4); // error cases QTest::newRow("const-no-initializer") @@ -8218,6 +8270,35 @@ void tst_qqmlecmascript::constkw_data() << "const v = 1, i\n" << true << QVariant("SyntaxError: Missing initializer in const declaration"); + QTest::newRow("const-no-duplicate") + << "const v = 1, v = 2\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); + QTest::newRow("const-no-duplicate-2") + << "const v = 1\n" + "const v = 2\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); + QTest::newRow("const-no-duplicate-var") + << "const v = 1\n" + "var v = 1\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); + QTest::newRow("var-no-duplicate-const") + << "var v = 1\n" + "const v = 1\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); + QTest::newRow("const-no-duplicate-let") + << "const v = 1\n" + "let v = 1\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); + QTest::newRow("let-no-duplicate-const") + << "let v = 1\n" + "const v = 1\n" + << true + << QVariant("SyntaxError: Identifier v has already been declared"); } void tst_qqmlecmascript::constkw() @@ -8238,6 +8319,32 @@ void tst_qqmlecmascript::constkw() } } +// Redefine a property found on the global object. It shouldn't throw. +void tst_qqmlecmascript::redefineGlobalProp() +{ + { + QJSEngine engine; + QJSValue ret = engine.evaluate("\"use strict\"\n var toString = 1;"); + QVERIFY2(!ret.isError(), qPrintable(ret.toString())); + } + { + QJSEngine engine; + QJSValue ret = engine.evaluate("var toString = 1;"); + QVERIFY2(!ret.isError(), qPrintable(ret.toString())); + } +} + +void tst_qqmlecmascript::freeze_empty_object() +{ + // this shouldn't crash + QJSEngine engine; + QJSValue v = engine.evaluate(QString::fromLatin1( + "var obj = {};\n" + "Object.freeze(obj);\n" + )); + QVERIFY(!v.isError()); + QCOMPARE(v.toBool(), true); +} QTEST_MAIN(tst_qqmlecmascript) diff --git a/tests/auto/qml/qqmlengine/tst_qqmlengine.cpp b/tests/auto/qml/qqmlengine/tst_qqmlengine.cpp index 9c155eda5b..e170920486 100644 --- a/tests/auto/qml/qqmlengine/tst_qqmlengine.cpp +++ b/tests/auto/qml/qqmlengine/tst_qqmlengine.cpp @@ -56,6 +56,7 @@ private slots: void baseUrl(); void contextForObject(); void offlineStoragePath(); + void offlineDatabaseStoragePath(); void clearComponentCache(); void trimComponentCache(); void trimComponentCache_data(); @@ -252,6 +253,34 @@ void tst_qqmlengine::offlineStoragePath() QCOMPARE(engine.offlineStoragePath(), QDir::homePath()); } +void tst_qqmlengine::offlineDatabaseStoragePath() +{ + // Without these set, QDesktopServices::storageLocation returns + // strings with extra "//" at the end. We set them to ignore this problem. + qApp->setApplicationName("tst_qqmlengine"); + qApp->setOrganizationName("QtProject"); + qApp->setOrganizationDomain("www.qt-project.org"); + + QQmlEngine engine; + QString dataLocation = QStandardPaths::writableLocation(QStandardPaths::DataLocation); + const QString databaseName = QLatin1String("foo"); + QString databaseLocation = engine.offlineStorageDatabaseFilePath(databaseName); + QCOMPARE(dataLocation.isEmpty(), databaseLocation.isEmpty()); + + QDir dir(dataLocation); + dir.mkpath("QML"); + dir.cd("QML"); + dir.mkpath("OfflineStorage"); + dir.cd("OfflineStorage"); + dir.mkpath("Databases"); + dir.cd("Databases"); + QCOMPARE(QFileInfo(databaseLocation).dir().path(), dir.path()); + + QCryptographicHash md5(QCryptographicHash::Md5); + md5.addData(databaseName.toUtf8()); + QCOMPARE(databaseLocation, QDir::toNativeSeparators(dir.filePath(QLatin1String(md5.result().toHex())))); +} + void tst_qqmlengine::clearComponentCache() { QQmlEngine engine; diff --git a/tests/auto/qml/qqmllanguage/testtypes.cpp b/tests/auto/qml/qqmllanguage/testtypes.cpp index bc8c192a61..bdcdaa8137 100644 --- a/tests/auto/qml/qqmllanguage/testtypes.cpp +++ b/tests/auto/qml/qqmllanguage/testtypes.cpp @@ -87,6 +87,10 @@ void registerTypes() qmlRegisterUncreatableType<MyUncreateableBaseClass,1>("Test", 1, 1, "MyUncreateableBaseClass", "Cannot create MyUncreateableBaseClass"); qmlRegisterType<MyCreateableDerivedClass,1>("Test", 1, 1, "MyCreateableDerivedClass"); + qmlRegisterExtendedUncreatableType<MyExtendedUncreateableBaseClass, MyExtendedUncreateableBaseClassExtension>("Test", 1, 0, "MyExtendedUncreateableBaseClass", "Cannot create MyExtendedUncreateableBaseClass"); + qmlRegisterExtendedUncreatableType<MyExtendedUncreateableBaseClass, MyExtendedUncreateableBaseClassExtension, 1>("Test", 1, 1, "MyExtendedUncreateableBaseClass", "Cannot create MyExtendedUncreateableBaseClass"); + qmlRegisterType<MyExtendedCreateableDerivedClass>("Test", 1, 0, "MyExtendedCreateableDerivedClass"); + qmlRegisterCustomType<CustomBinding>("Test", 1, 0, "CustomBinding", new CustomBindingParser); qmlRegisterCustomType<SimpleObjectWithCustomParser>("Test", 1, 0, "SimpleObjectWithCustomParser", new SimpleObjectCustomParser); diff --git a/tests/auto/qml/qqmllanguage/testtypes.h b/tests/auto/qml/qqmllanguage/testtypes.h index 6c62bcf7b9..7d7a8ac6d3 100644 --- a/tests/auto/qml/qqmllanguage/testtypes.h +++ b/tests/auto/qml/qqmllanguage/testtypes.h @@ -1021,6 +1021,60 @@ public: } }; +class MyExtendedUncreateableBaseClass : public QObject +{ + Q_OBJECT + Q_PROPERTY(bool prop1 READ prop1 WRITE setprop1) + Q_PROPERTY(bool prop2 READ prop2 WRITE setprop2 REVISION 1) + Q_PROPERTY(bool prop3 READ prop3 WRITE setprop3 REVISION 1) +public: + explicit MyExtendedUncreateableBaseClass(QObject *parent = 0) + : QObject(parent), _prop1(false), _prop2(false), _prop3(false) + { + } + + bool _prop1; + bool prop1() const { return _prop1; } + void setprop1(bool p) { _prop1 = p; } + bool _prop2; + bool prop2() const { return _prop2; } + void setprop2(bool p) { _prop2 = p; } + bool _prop3; + bool prop3() const { return _prop3; } + void setprop3(bool p) { _prop3 = p; } +}; + +class MyExtendedUncreateableBaseClassExtension : public QObject +{ + Q_OBJECT + Q_PROPERTY(bool prop4 READ prop4 WRITE setprop4) +public: + explicit MyExtendedUncreateableBaseClassExtension(QObject *parent = 0) + : QObject(parent), _prop4(false) + { + } + + bool _prop4; + bool prop4() const { return _prop4; } + void setprop4(bool p) { _prop4 = p; } +}; + +class MyExtendedCreateableDerivedClass : public MyExtendedUncreateableBaseClass +{ + Q_OBJECT + Q_PROPERTY(bool prop5 READ prop5 WRITE setprop5) + +public: + MyExtendedCreateableDerivedClass(QObject *parent = 0) + : MyExtendedUncreateableBaseClass(parent), _prop5(false) + { + } + + bool _prop5; + bool prop5() const { return _prop5; } + void setprop5(bool p) { _prop5 = p; } +}; + class MyVersion2Class : public QObject { Q_OBJECT diff --git a/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp b/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp index c0500afddd..750c32cc3c 100644 --- a/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp +++ b/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp @@ -189,6 +189,9 @@ private slots: void subclassedUncreateableRevision_data(); void subclassedUncreateableRevision(); + void subclassedExtendedUncreateableRevision_data(); + void subclassedExtendedUncreateableRevision(); + void uncreatableTypesAsProperties(); void propertyInit(); @@ -3228,6 +3231,62 @@ void tst_qqmllanguage::subclassedUncreateableRevision() delete obj; } +void tst_qqmllanguage::subclassedExtendedUncreateableRevision_data() +{ + QTest::addColumn<QString>("version"); + QTest::addColumn<QString>("prop"); + QTest::addColumn<bool>("shouldWork"); + + QTest::newRow("prop1 exists in 1.0") << "1.0" << "prop1" << true; + QTest::newRow("prop2 does not exist in 1.0") << "1.0" << "prop2" << false; + QTest::newRow("prop3 does not exist in 1.0") << "1.0" << "prop3" << false; + QTest::newRow("prop4 exists in 1.0") << "1.0" << "prop4" << true; + QTest::newRow("prop5 exists in 1.0") << "1.0" << "prop5" << true; + + QTest::newRow("prop1 exists in 1.1") << "1.1" << "prop1" << true; + QTest::newRow("prop2 exists in 1.1") << "1.1" << "prop2" << true; + QTest::newRow("prop3 exists in 1.1") << "1.1" << "prop3" << true; + QTest::newRow("prop4 exists in 1.1") << "1.1" << "prop4" << true; + QTest::newRow("prop5 exists in 1.1") << "1.1" << "prop5" << true; +} + +void tst_qqmllanguage::subclassedExtendedUncreateableRevision() +{ + QFETCH(QString, version); + QFETCH(QString, prop); + QFETCH(bool, shouldWork); + + { + QQmlEngine engine; + QString qml = QString("import QtQuick 2.0\nimport Test %1\nMyExtendedUncreateableBaseClass {}").arg(version); + QQmlComponent c(&engine); + QTest::ignoreMessage(QtWarningMsg, "QQmlComponent: Component is not ready"); + c.setData(qml.toUtf8(), QUrl::fromLocalFile(QDir::currentPath())); + QObject *obj = c.create(); + QCOMPARE(obj, static_cast<QObject*>(0)); + QCOMPARE(c.errors().count(), 1); + QCOMPARE(c.errors().first().description(), QString("Cannot create MyExtendedUncreateableBaseClass")); + } + + QQmlEngine engine; + QString qml = QString("import QtQuick 2.0\nimport Test %1\nMyExtendedCreateableDerivedClass {\n%3: true\n}").arg(version).arg(prop); + QQmlComponent c(&engine); + if (!shouldWork) + QTest::ignoreMessage(QtWarningMsg, "QQmlComponent: Component is not ready"); + c.setData(qml.toUtf8(), QUrl::fromLocalFile(QDir::currentPath())); + QObject *obj = c.create(); + if (!shouldWork) { + QCOMPARE(obj, static_cast<QObject*>(0)); + return; + } + + QVERIFY(obj); + MyExtendedUncreateableBaseClass *base = qobject_cast<MyExtendedUncreateableBaseClass*>(obj); + QVERIFY(base); + QCOMPARE(base->property(prop.toLatin1()).toBool(), true); + delete obj; +} + void tst_qqmllanguage::uncreatableTypesAsProperties() { QQmlEngine engine; diff --git a/tests/auto/qml/qqmllistreference/data/propertyList.qml b/tests/auto/qml/qqmllistreference/data/propertyList.qml new file mode 100644 index 0000000000..c791c6dcf0 --- /dev/null +++ b/tests/auto/qml/qqmllistreference/data/propertyList.qml @@ -0,0 +1,12 @@ +import QtQuick 2.7 + +Item { + id:root + + Component.onCompleted : { + var st1 = Qt.createQmlObject( "import QtQuick 2.7; State{ name: 'MyState1' }", root, "dynamicState1" ); + var st2 = Qt.createQmlObject( "import QtQuick 2.7; State{ name: 'MyState2' }", root, "dynamicState2" ); + root.states.push( st1, st2 ); + root.state = "MyState2"; + } +} diff --git a/tests/auto/qml/qqmllistreference/qqmllistreference.pro b/tests/auto/qml/qqmllistreference/qqmllistreference.pro index dceb7d1133..110d0d9c81 100644 --- a/tests/auto/qml/qqmllistreference/qqmllistreference.pro +++ b/tests/auto/qml/qqmllistreference/qqmllistreference.pro @@ -8,4 +8,4 @@ include (../../shared/util.pri) TESTDATA = data/* -QT += core-private gui-private qml-private testlib +QT += core-private gui-private quick-private qml-private testlib diff --git a/tests/auto/qml/qqmllistreference/tst_qqmllistreference.cpp b/tests/auto/qml/qqmllistreference/tst_qqmllistreference.cpp index 4d33359eaa..5c16a48378 100644 --- a/tests/auto/qml/qqmllistreference/tst_qqmllistreference.cpp +++ b/tests/auto/qml/qqmllistreference/tst_qqmllistreference.cpp @@ -36,6 +36,7 @@ #include <QtQml/qqmlprivate.h> #include <QtQml/qqmlproperty.h> #include <QDebug> +#include <private/qquickstate_p.h> #include "../../shared/util.h" class tst_qqmllistreference : public QQmlDataTest @@ -65,6 +66,7 @@ private slots: void qmlmetaproperty(); void engineTypes(); void variantToList(); + void listProperty(); }; class TestType : public QObject @@ -618,6 +620,28 @@ void tst_qqmllistreference::variantToList() delete o; } +void tst_qqmllistreference::listProperty() +{ + QQmlEngine engine; + QQmlComponent component(&engine, testFileUrl("propertyList.qml")); + + QScopedPointer<QObject> object( component.create() ); + QVERIFY(object != 0); + + QCOMPARE( object->property("state").toString(), QStringLiteral("MyState2") ); + QQmlListReference list( object.data(), "states"); + QCOMPARE( list.count(), 2 ); + + QQuickState* state1 = dynamic_cast<QQuickState*>( list.at( 0 ) ); + QVERIFY(state1 != 0); + QCOMPARE( state1->name(), QStringLiteral("MyState1") ); + QQuickState* state2 = dynamic_cast<QQuickState*>( list.at( 1 ) ); + QVERIFY(state2 != 0); + + QCOMPARE( state2->name(), QStringLiteral("MyState2") ); +} + + QTEST_MAIN(tst_qqmllistreference) #include "tst_qqmllistreference.moc" diff --git a/tests/auto/qml/qqmlmetatype/data/testExternalEnums.qml b/tests/auto/qml/qqmlmetatype/data/testExternalEnums.qml new file mode 100644 index 0000000000..8eb5616ab2 --- /dev/null +++ b/tests/auto/qml/qqmlmetatype/data/testExternalEnums.qml @@ -0,0 +1,12 @@ +import QtQml 2.2 +import x.y.z 1.0 + +QtObject { + function x() { + eval("1"); + return ExternalEnums.DocumentsLocation; + } + + property var a: ExternalEnums.DocumentsLocation + property var b: x() +} diff --git a/tests/auto/qml/qqmlmetatype/tst_qqmlmetatype.cpp b/tests/auto/qml/qqmlmetatype/tst_qqmlmetatype.cpp index 19cda21685..9fbd719d7b 100644 --- a/tests/auto/qml/qqmlmetatype/tst_qqmlmetatype.cpp +++ b/tests/auto/qml/qqmlmetatype/tst_qqmlmetatype.cpp @@ -26,6 +26,7 @@ ** ****************************************************************************/ +#include <qstandardpaths.h> #include <qtest.h> #include <qqml.h> #include <qqmlprivate.h> @@ -53,6 +54,7 @@ private slots: void invalidQmlTypeName(); void registrationType(); void compositeType(); + void externalEnums(); void isList(); @@ -70,6 +72,20 @@ public: }; QML_DECLARE_TYPE(TestType); +class ExternalEnums : public QObject +{ + Q_OBJECT + Q_ENUMS(QStandardPaths::StandardLocation QStandardPaths::LocateOptions) +public: + ExternalEnums(QObject *parent = nullptr) : QObject(parent) {} + + static QObject *create(QQmlEngine *engine, QJSEngine *scriptEngine) { + Q_UNUSED(scriptEngine); + return new ExternalEnums(engine); + } +}; +QML_DECLARE_TYPE(ExternalEnums); + QObject *testTypeProvider(QQmlEngine *engine, QJSEngine *scriptEngine) { Q_UNUSED(engine); @@ -271,6 +287,23 @@ void tst_qqmlmetatype::compositeType() QCOMPARE(type->sourceUrl(), testFileUrl("ImplicitType.qml")); } +void tst_qqmlmetatype::externalEnums() +{ + QQmlEngine engine; + qmlRegisterSingletonType<ExternalEnums>("x.y.z", 1, 0, "ExternalEnums", ExternalEnums::create); + + QQmlComponent c(&engine, testFileUrl("testExternalEnums.qml")); + QObject *obj = c.create(); + QVERIFY(obj); + QVariant a = obj->property("a"); + QCOMPARE(a.type(), QVariant::Int); + QCOMPARE(a.toInt(), int(QStandardPaths::DocumentsLocation)); + QVariant b = obj->property("b"); + QCOMPARE(b.type(), QVariant::Int); + QCOMPARE(b.toInt(), int(QStandardPaths::DocumentsLocation)); + +} + QTEST_MAIN(tst_qqmlmetatype) #include "tst_qqmlmetatype.moc" diff --git a/tests/auto/qml/qqmlproperty/data/aliasPropertyBindings2.qml b/tests/auto/qml/qqmlproperty/data/aliasPropertyBindings2.qml new file mode 100644 index 0000000000..60cb088209 --- /dev/null +++ b/tests/auto/qml/qqmlproperty/data/aliasPropertyBindings2.qml @@ -0,0 +1,23 @@ +import QtQuick 2.0 + +Item { + id: root + + property real test: 9 + property real test2: 3 + + property alias aliasProperty: innerObject.realProperty + + property QtObject innerObject: QtObject { + id: innerObject + property real realProperty: test * test + test + } + + states: State { + name: "switch" + PropertyChanges { + target: root + aliasProperty: 32 * test2 + } + } +} diff --git a/tests/auto/qml/qqmlproperty/tst_qqmlproperty.cpp b/tests/auto/qml/qqmlproperty/tst_qqmlproperty.cpp index 385ffc523a..84a1bd9cc5 100644 --- a/tests/auto/qml/qqmlproperty/tst_qqmlproperty.cpp +++ b/tests/auto/qml/qqmlproperty/tst_qqmlproperty.cpp @@ -135,6 +135,7 @@ private slots: // Bugs void crashOnValueProperty(); + void aliasPropertyBindings_data(); void aliasPropertyBindings(); void noContext(); void assignEmptyVariantMap(); @@ -1833,23 +1834,40 @@ void tst_qqmlproperty::crashOnValueProperty() QCOMPARE(p.read(), QVariant(20)); } -// QTBUG-13719 +void tst_qqmlproperty::aliasPropertyBindings_data() +{ + QTest::addColumn<QString>("file"); + QTest::addColumn<QString>("subObject"); + + QTest::newRow("same object") << "aliasPropertyBindings.qml" << ""; + QTest::newRow("different objects") << "aliasPropertyBindings2.qml" << "innerObject"; +} + +// QTBUG-13719, QTBUG-58271 void tst_qqmlproperty::aliasPropertyBindings() { - QQmlComponent component(&engine, testFileUrl("aliasPropertyBindings.qml")); + QFETCH(QString, file); + QFETCH(QString, subObject); + + QQmlComponent component(&engine, testFileUrl(file)); QObject *object = component.create(); QVERIFY(object != 0); - QCOMPARE(object->property("realProperty").toReal(), 90.); + // the object where realProperty lives + QObject *realPropertyObject = object; + if (!subObject.isEmpty()) + realPropertyObject = object->property(subObject.toLatin1()).value<QObject*>(); + + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 90.); QCOMPARE(object->property("aliasProperty").toReal(), 90.); object->setProperty("test", 10); - QCOMPARE(object->property("realProperty").toReal(), 110.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 110.); QCOMPARE(object->property("aliasProperty").toReal(), 110.); - QQmlProperty realProperty(object, QLatin1String("realProperty")); + QQmlProperty realProperty(realPropertyObject, QLatin1String("realProperty")); QQmlProperty aliasProperty(object, QLatin1String("aliasProperty")); // Check there is a binding on these two properties @@ -1868,18 +1886,18 @@ void tst_qqmlproperty::aliasPropertyBindings() QCOMPARE(QQmlPropertyPrivate::binding(realProperty), QQmlPropertyPrivate::binding(aliasProperty)); - QCOMPARE(object->property("realProperty").toReal(), 96.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 96.); QCOMPARE(object->property("aliasProperty").toReal(), 96.); // Check the old binding really has not effect any more object->setProperty("test", 4); - QCOMPARE(object->property("realProperty").toReal(), 96.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 96.); QCOMPARE(object->property("aliasProperty").toReal(), 96.); object->setProperty("test2", 9); - QCOMPARE(object->property("realProperty").toReal(), 288.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 288.); QCOMPARE(object->property("aliasProperty").toReal(), 288.); // Revert @@ -1890,12 +1908,12 @@ void tst_qqmlproperty::aliasPropertyBindings() QCOMPARE(QQmlPropertyPrivate::binding(realProperty), QQmlPropertyPrivate::binding(aliasProperty)); - QCOMPARE(object->property("realProperty").toReal(), 20.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 20.); QCOMPARE(object->property("aliasProperty").toReal(), 20.); object->setProperty("test2", 3); - QCOMPARE(object->property("realProperty").toReal(), 20.); + QCOMPARE(realPropertyObject->property("realProperty").toReal(), 20.); QCOMPARE(object->property("aliasProperty").toReal(), 20.); delete object; @@ -1996,7 +2014,7 @@ void tst_qqmlproperty::warnOnInvalidBinding() QTest::ignoreMessage(QtWarningMsg, expectedWarning.toLatin1().constData()); // V8 error message for invalid binding to anchor - expectedWarning = testUrl.toString() + QString::fromLatin1(":14:33: Unable to assign QQuickItem_QML_6 to QQuickAnchorLine"); + expectedWarning = testUrl.toString() + QString::fromLatin1(":14:33: Unable to assign QQuickItem_QML_8 to QQuickAnchorLine"); QTest::ignoreMessage(QtWarningMsg, expectedWarning.toLatin1().constData()); QQmlComponent component(&engine, testUrl); diff --git a/tests/auto/qml/v4misc/tst_v4misc.cpp b/tests/auto/qml/v4misc/tst_v4misc.cpp index 057714e175..88b6ae92a8 100644 --- a/tests/auto/qml/v4misc/tst_v4misc.cpp +++ b/tests/auto/qml/v4misc/tst_v4misc.cpp @@ -28,6 +28,7 @@ #include <qtest.h> +#define V4_AUTOTEST #include <private/qv4ssa_p.h> class tst_v4misc: public QObject @@ -40,6 +41,9 @@ private slots: void rangeSplitting_1(); void rangeSplitting_2(); void rangeSplitting_3(); + + void moveMapping_1(); + void moveMapping_2(); }; QT_BEGIN_NAMESPACE @@ -139,6 +143,94 @@ void tst_v4misc::rangeSplitting_3() QCOMPARE(interval.end(), 71); } +void tst_v4misc::moveMapping_1() +{ + Temp fp2(DoubleType, Temp::PhysicalRegister, 2); + Temp fp3(DoubleType, Temp::PhysicalRegister, 3); + Temp fp4(DoubleType, Temp::PhysicalRegister, 4); + Temp fp5(DoubleType, Temp::PhysicalRegister, 5); + + MoveMapping mapping; + mapping.add(&fp2, &fp3); + mapping.add(&fp2, &fp4); + mapping.add(&fp2, &fp5); + mapping.add(&fp3, &fp2); + + mapping.order(); +// mapping.dump(); + + QCOMPARE(mapping._moves.size(), 3); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp2, &fp4, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp2, &fp5, false))); + QVERIFY(mapping._moves.last() == MoveMapping::Move(&fp2, &fp3, true) || + mapping._moves.last() == MoveMapping::Move(&fp3, &fp2, true)); +} + +void tst_v4misc::moveMapping_2() +{ + Temp fp1(DoubleType, Temp::PhysicalRegister, 1); + Temp fp2(DoubleType, Temp::PhysicalRegister, 2); + Temp fp3(DoubleType, Temp::PhysicalRegister, 3); + Temp fp4(DoubleType, Temp::PhysicalRegister, 4); + Temp fp5(DoubleType, Temp::PhysicalRegister, 5); + Temp fp6(DoubleType, Temp::PhysicalRegister, 6); + Temp fp7(DoubleType, Temp::PhysicalRegister, 7); + Temp fp8(DoubleType, Temp::PhysicalRegister, 8); + Temp fp9(DoubleType, Temp::PhysicalRegister, 9); + Temp fp10(DoubleType, Temp::PhysicalRegister, 10); + Temp fp11(DoubleType, Temp::PhysicalRegister, 11); + Temp fp12(DoubleType, Temp::PhysicalRegister, 12); + Temp fp13(DoubleType, Temp::PhysicalRegister, 13); + + MoveMapping mapping; + mapping.add(&fp2, &fp1); + mapping.add(&fp2, &fp3); + mapping.add(&fp3, &fp2); + mapping.add(&fp3, &fp4); + + mapping.add(&fp9, &fp8); + mapping.add(&fp8, &fp7); + mapping.add(&fp7, &fp6); + mapping.add(&fp7, &fp5); + + mapping.add(&fp10, &fp11); + mapping.add(&fp11, &fp12); + mapping.add(&fp12, &fp13); + mapping.add(&fp13, &fp10); + + mapping.order(); +// mapping.dump(); + + QCOMPARE(mapping._moves.size(), 10); + + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp2, &fp1, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp3, &fp4, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp7, &fp6, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp7, &fp5, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp8, &fp7, false))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp9, &fp8, false))); + + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp2, &fp3, true)) || + mapping._moves.contains(MoveMapping::Move(&fp3, &fp2, true))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp10, &fp13, true)) || + mapping._moves.contains(MoveMapping::Move(&fp13, &fp10, true))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp12, &fp13, true)) || + mapping._moves.contains(MoveMapping::Move(&fp13, &fp12, true))); + QVERIFY(mapping._moves.contains(MoveMapping::Move(&fp12, &fp11, true)) || + mapping._moves.contains(MoveMapping::Move(&fp11, &fp12, true))); + + QVERIFY(!mapping._moves.at(0).needsSwap); + QVERIFY(!mapping._moves.at(1).needsSwap); + QVERIFY(!mapping._moves.at(2).needsSwap); + QVERIFY(!mapping._moves.at(3).needsSwap); + QVERIFY(!mapping._moves.at(4).needsSwap); + QVERIFY(!mapping._moves.at(5).needsSwap); + QVERIFY(mapping._moves.at(6).needsSwap); + QVERIFY(mapping._moves.at(7).needsSwap); + QVERIFY(mapping._moves.at(8).needsSwap); + QVERIFY(mapping._moves.at(9).needsSwap); +} + QTEST_MAIN(tst_v4misc) #include "tst_v4misc.moc" |