aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/3rdparty/masm/assembler/MacroAssemblerMIPS.h48
-rw-r--r--src/qml/animations/qabstractanimationjob.cpp3
-rw-r--r--src/qml/animations/qabstractanimationjob_p.h4
-rw-r--r--src/qml/doc/src/qmlfunctions.qdoc2
-rw-r--r--src/qml/qml/qqmlexpression.cpp2
-rw-r--r--src/qml/qml/qqmlfileselector.cpp6
-rw-r--r--src/qml/qml/qqmlimport.cpp3
-rw-r--r--src/qml/qml/qqmlinfo.cpp2
-rw-r--r--src/qmltest/quicktest.cpp22
-rw-r--r--src/quick/items/qquickitem.cpp160
-rw-r--r--src/quick/items/qquicktext.cpp5
-rw-r--r--src/quick/items/qquicktextedit.cpp11
-rw-r--r--src/quick/items/qquicktextinput.cpp28
-rw-r--r--src/quick/items/qquicktextinput_p.h1
-rw-r--r--src/quick/items/qquickwindow.cpp25
-rw-r--r--src/quick/scenegraph/qsgdefaultglyphnode_p.cpp10
-rw-r--r--src/quick/scenegraph/qsgrenderloop.cpp7
-rw-r--r--src/quick/scenegraph/qsgthreadedrenderloop.cpp6
-rw-r--r--src/quick/scenegraph/qsgwindowsrenderloop.cpp1
-rw-r--r--src/quick/scenegraph/shaders/smoothtexture.vert5
-rw-r--r--src/quick/util/qquickanimator.cpp6
-rw-r--r--src/quick/util/qquickanimatorjob.cpp15
-rw-r--r--src/quick/util/qquickanimatorjob_p.h2
-rw-r--r--src/quick/util/qquickstate.cpp5
-rw-r--r--src/quickwidgets/qquickwidget.cpp21
-rw-r--r--src/quickwidgets/qquickwidget.h2
-rw-r--r--tests/auto/auto.pro2
-rw-r--r--tests/auto/headersclean/headersclean.pro2
-rw-r--r--tests/auto/particles/qquickcustomparticle/qquickcustomparticle.pro3
-rw-r--r--tests/auto/particles/qquicktrailemitter/qquicktrailemitter.pro2
-rw-r--r--tests/auto/qml/debugger/qqmldebugjs/qqmldebugjs.pro2
-rw-r--r--tests/auto/qml/debugger/qqmlprofilerservice/tst_qqmlprofilerservice.cpp228
-rw-r--r--tests/auto/qml/debugger/qv4profilerservice/data/console.qml14
-rw-r--r--tests/auto/qml/debugger/qv4profilerservice/data/exit.qml11
-rw-r--r--tests/auto/qml/debugger/qv4profilerservice/data/test.qml5
-rw-r--r--tests/auto/qml/debugger/qv4profilerservice/qv4profilerservice.pro16
-rw-r--r--tests/auto/qml/debugger/qv4profilerservice/tst_qv4profilerservice.cpp326
-rw-r--r--tests/auto/quick/qquickanimations/BLACKLIST40
-rw-r--r--tests/auto/quick/qquickanimations/qquickanimations.pro1
-rw-r--r--tests/auto/quick/qquickflickable/BLACKLIST19
-rw-r--r--tests/auto/quick/qquickflickable/qquickflickable.pro1
-rw-r--r--tests/auto/quick/qquickgridview/qquickgridview.pro3
-rw-r--r--tests/auto/quick/qquickitem/data/contains.qml26
-rw-r--r--tests/auto/quick/qquickitem/tst_qquickitem.cpp45
-rw-r--r--tests/auto/quick/qquickloader/qquickloader.pro1
-rw-r--r--tests/auto/quick/qquickpathview/qquickpathview.pro2
-rw-r--r--tests/auto/quick/qquickstates/data/revertListMemoryLeak.qml16
-rw-r--r--tests/auto/quick/qquickstates/tst_qquickstates.cpp25
-rw-r--r--tests/auto/quick/qquicktext/qquicktext.pro2
-rw-r--r--tests/auto/quick/qquicktextedit/qquicktextedit.pro3
-rw-r--r--tests/auto/quick/qquickwindow/BLACKLIST2
-rw-r--r--tests/auto/quickwidgets/qquickwidget/tst_qquickwidget.cpp33
-rw-r--r--tests/manual/scenegraph_lancelot/data/text/textedit_table.qml21
53 files changed, 663 insertions, 590 deletions
diff --git a/src/3rdparty/masm/assembler/MacroAssemblerMIPS.h b/src/3rdparty/masm/assembler/MacroAssemblerMIPS.h
index e18d86c5b3..55a3c7bf9b 100644
--- a/src/3rdparty/masm/assembler/MacroAssemblerMIPS.h
+++ b/src/3rdparty/masm/assembler/MacroAssemblerMIPS.h
@@ -765,7 +765,53 @@ public:
void load16Unaligned(BaseIndex address, RegisterID dest)
{
- load16(address, dest);
+ if (address.offset >= -32768 && address.offset <= 32766 && !m_fixedWidth) {
+ /*
+ sll addrtemp, address.index, address.scale
+ addu addrtemp, addrtemp, address.base
+ lbu immTemp, address.offset+x(addrtemp) (x=0 for LE, x=1 for BE)
+ lbu dest, address.offset+x(addrtemp) (x=1 for LE, x=0 for BE)
+ sll dest, dest, 8
+ or dest, dest, immTemp
+ */
+ m_assembler.sll(addrTempRegister, address.index, address.scale);
+ m_assembler.addu(addrTempRegister, addrTempRegister, address.base);
+#if CPU(BIG_ENDIAN)
+ m_assembler.lbu(immTempRegister, addrTempRegister, address.offset + 1);
+ m_assembler.lbu(dest, addrTempRegister, address.offset);
+#else
+ m_assembler.lbu(immTempRegister, addrTempRegister, address.offset);
+ m_assembler.lbu(dest, addrTempRegister, address.offset + 1);
+#endif
+ m_assembler.sll(dest, dest, 8);
+ m_assembler.orInsn(dest, dest, immTempRegister);
+ } else {
+ /*
+ sll addrTemp, address.index, address.scale
+ addu addrTemp, addrTemp, address.base
+ lui immTemp, address.offset >> 16
+ ori immTemp, immTemp, address.offset & 0xffff
+ addu addrTemp, addrTemp, immTemp
+ lbu immTemp, x(addrtemp) (x=0 for LE, x=1 for BE)
+ lbu dest, x(addrtemp) (x=1 for LE, x=0 for BE)
+ sll dest, dest, 8
+ or dest, dest, immTemp
+ */
+ m_assembler.sll(addrTempRegister, address.index, address.scale);
+ m_assembler.addu(addrTempRegister, addrTempRegister, address.base);
+ m_assembler.lui(immTempRegister, address.offset >> 16);
+ m_assembler.ori(immTempRegister, immTempRegister, address.offset);
+ m_assembler.addu(addrTempRegister, addrTempRegister, immTempRegister);
+#if CPU(BIG_ENDIAN)
+ m_assembler.lbu(immTempRegister, addrTempRegister, 1);
+ m_assembler.lbu(dest, addrTempRegister, 0);
+#else
+ m_assembler.lbu(immTempRegister, addrTempRegister, 0);
+ m_assembler.lbu(dest, addrTempRegister, 1);
+#endif
+ m_assembler.sll(dest, dest, 8);
+ m_assembler.orInsn(dest, dest, immTempRegister);
+ }
}
void load32WithUnalignedHalfWords(BaseIndex address, RegisterID dest)
diff --git a/src/qml/animations/qabstractanimationjob.cpp b/src/qml/animations/qabstractanimationjob.cpp
index 9548a18553..7fcf383bcb 100644
--- a/src/qml/animations/qabstractanimationjob.cpp
+++ b/src/qml/animations/qabstractanimationjob.cpp
@@ -652,7 +652,8 @@ void QAbstractAnimationJob::removeAnimationChangeListener(QAnimationJobChangeLis
void QAbstractAnimationJob::debugAnimation(QDebug d) const
{
- d << "AbstractAnimationJob(" << hex << (void *) this << dec << ")" << "duration:" << duration();
+ d << "AbstractAnimationJob(" << hex << (void *) this << dec << ") state:"
+ << m_state << "duration:" << duration();
}
QDebug operator<<(QDebug d, const QAbstractAnimationJob *job)
diff --git a/src/qml/animations/qabstractanimationjob_p.h b/src/qml/animations/qabstractanimationjob_p.h
index cba6e35170..5a3e9d2025 100644
--- a/src/qml/animations/qabstractanimationjob_p.h
+++ b/src/qml/animations/qabstractanimationjob_p.h
@@ -163,7 +163,7 @@ protected:
friend class QQmlAnimationTimer;
friend class QAnimationGroupJob;
- friend QDebug operator<<(QDebug, const QAbstractAnimationJob *job);
+ friend Q_QML_PRIVATE_EXPORT QDebug operator<<(QDebug, const QAbstractAnimationJob *job);
};
class Q_QML_PRIVATE_EXPORT QAnimationJobChangeListener
@@ -234,7 +234,7 @@ private:
Q_DECLARE_OPERATORS_FOR_FLAGS(QAbstractAnimationJob::ChangeTypes)
-QDebug operator<<(QDebug, const QAbstractAnimationJob *job);
+Q_QML_PRIVATE_EXPORT QDebug operator<<(QDebug, const QAbstractAnimationJob *job);
QT_END_NAMESPACE
diff --git a/src/qml/doc/src/qmlfunctions.qdoc b/src/qml/doc/src/qmlfunctions.qdoc
index 4a6ed2fc84..5732be6b26 100644
--- a/src/qml/doc/src/qmlfunctions.qdoc
+++ b/src/qml/doc/src/qmlfunctions.qdoc
@@ -183,7 +183,7 @@
\a versionMinor.
While the type has a name and a type, it cannot be created, and the
- given error \a message will result if creation is attempted.
+ given error \a reason will result if creation is attempted.
This is useful where the type is only intended for providing attached
properties, enum values or an abstract base class with its extension.
diff --git a/src/qml/qml/qqmlexpression.cpp b/src/qml/qml/qqmlexpression.cpp
index bcdbf5b2df..18f882e1e0 100644
--- a/src/qml/qml/qqmlexpression.cpp
+++ b/src/qml/qml/qqmlexpression.cpp
@@ -364,7 +364,7 @@ int QQmlExpression::columnNumber() const
}
/*!
- Set the location of this expression to \a line of \a url. This information
+ Set the location of this expression to \a line and \a column of \a url. This information
is used by the script engine.
*/
void QQmlExpression::setSourceLocation(const QString &url, int line, int column)
diff --git a/src/qml/qml/qqmlfileselector.cpp b/src/qml/qml/qqmlfileselector.cpp
index 2b3c2ade4f..3ee7bb3040 100644
--- a/src/qml/qml/qqmlfileselector.cpp
+++ b/src/qml/qml/qqmlfileselector.cpp
@@ -121,9 +121,9 @@ QQmlFileSelectorPrivate::QQmlFileSelectorPrivate()
}
/*!
- Sets a different QFileSelector instance for use by the QQmlFileSelector. QQmlFileSelector does not
- take ownership of the new QFileSelector. To reset QQmlFileSelector to use its internal
- QFileSelector instance, call setSelector(0).
+ Sets the QFileSelector instance for use by the QQmlFileSelector to \a selector.
+ QQmlFileSelector does not take ownership of the new QFileSelector. To reset QQmlFileSelector
+ to use its internal QFileSelector instance, call setSelector(0).
*/
void QQmlFileSelector::setSelector(QFileSelector *selector)
diff --git a/src/qml/qml/qqmlimport.cpp b/src/qml/qml/qqmlimport.cpp
index 370b221c92..6a5cab02fd 100644
--- a/src/qml/qml/qqmlimport.cpp
+++ b/src/qml/qml/qqmlimport.cpp
@@ -1973,9 +1973,8 @@ bool QQmlImportDatabase::importDynamicPlugin(const QString &filePath, const QStr
QQmlError error;
error.setDescription(loader->errorString());
errors->prepend(error);
-
- delete loader;
}
+ delete loader;
return false;
}
} else {
diff --git a/src/qml/qml/qqmlinfo.cpp b/src/qml/qml/qqmlinfo.cpp
index 1608cb85ed..85979b8dc0 100644
--- a/src/qml/qml/qqmlinfo.cpp
+++ b/src/qml/qml/qqmlinfo.cpp
@@ -44,7 +44,7 @@
QT_BEGIN_NAMESPACE
/*!
- \fn QQmlInfo qmlInfo(const QObject *object)
+ \fn QQmlInfo QtQml::qmlInfo(const QObject *object)
\relates QQmlEngine
Prints warning messages that include the file and line number for the
diff --git a/src/qmltest/quicktest.cpp b/src/qmltest/quicktest.cpp
index 947039f60e..5e9712d202 100644
--- a/src/qmltest/quicktest.cpp
+++ b/src/qmltest/quicktest.cpp
@@ -350,6 +350,8 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
if (QTest::printAvailableFunctions)
continue;
+ while (view->status() == QQuickView::Loading)
+ QTest::qWait(10);
if (view->status() == QQuickView::Error) {
handleCompileErrors(fi, view);
continue;
@@ -368,14 +370,22 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
view->resize(200, 200);
}
view->show();
+ if (!QTest::qWaitForWindowExposed(view)) {
+ qWarning().nospace()
+ << "Test '" << QDir::toNativeSeparators(path) << "' window not exposed after show().";
+ }
view->requestActivate();
-
- while (view->status() == QQuickView::Loading)
- QTest::qWait(10);
-
- QTest::qWaitForWindowActive(view);
- if (view->isExposed())
+ if (!QTest::qWaitForWindowActive(view)) {
+ qWarning().nospace()
+ << "Test '" << QDir::toNativeSeparators(path) << "' window not active after requestActivate().";
+ }
+ if (view->isExposed()) {
QTestRootObject::instance()->setWindowShown(true);
+ } else {
+ qWarning().nospace()
+ << "Test '" << QDir::toNativeSeparators(path) << "' window was never exposed! "
+ << "If the test case was expecting windowShown, it will hang.";
+ }
if (!QTestRootObject::instance()->hasQuit && QTestRootObject::instance()->hasTestCase())
eventLoop.exec();
// view->hide(); Causes a crash in Qt 3D due to deletion of the GL context, see QTBUG-27696
diff --git a/src/quick/items/qquickitem.cpp b/src/quick/items/qquickitem.cpp
index 776da86b7e..4d1bb696fa 100644
--- a/src/quick/items/qquickitem.cpp
+++ b/src/quick/items/qquickitem.cpp
@@ -49,7 +49,6 @@
#include <QtGui/qstylehints.h>
#include <QtGui/private/qguiapplication_p.h>
#include <QtGui/qinputmethod.h>
-#include <QtCore/qdebug.h>
#include <QtCore/qcoreevent.h>
#include <QtCore/qnumeric.h>
#include <QtGui/qpa/qplatformtheme.h>
@@ -66,6 +65,7 @@
#include <private/qv4engine_p.h>
#include <private/qv4object_p.h>
+#include <private/qdebug_p.h>
#ifndef QT_NO_CURSOR
# include <QtGui/qcursor.h>
@@ -4113,8 +4113,8 @@ void QQuickItem::polish()
\qmlmethod object QtQuick::Item::mapFromItem(Item item, real x, real y, real width, real height)
Maps the point (\a x, \a y) or rect (\a x, \a y, \a width, \a height), which is in \a
- item's coordinate system, to this item's coordinate system, and returns an object with \c x and
- \c y (and optionally \c width and \c height) properties matching the mapped coordinate.
+ item's coordinate system, to this item's coordinate system, and returns a \l point or \rect
+ matching the mapped coordinate.
If \a item is a \c null value, this maps the point or rect from the coordinate system of
the root QML view.
@@ -4124,50 +4124,43 @@ void QQuickItem::polish()
*/
void QQuickItem::mapFromItem(QQmlV4Function *args) const
{
- if (args->length() != 0) {
- QV4::ExecutionEngine *v4 = args->v4engine();
- QV4::Scope scope(v4);
- QV4::ScopedValue item(scope, (*args)[0]);
-
- QQuickItem *itemObj = 0;
- if (!item->isNull()) {
- QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
- if (qobjectWrapper)
- itemObj = qobject_cast<QQuickItem*>(qobjectWrapper->object());
- }
-
- if (!itemObj && !item->isNull()) {
- qmlInfo(this) << "mapFromItem() given argument \"" << item->toQStringNoThrow()
- << "\" which is neither null nor an Item";
- return;
- }
+ if (args->length() == 0)
+ return;
- QV4::ScopedObject rv(scope, v4->newObject());
- args->setReturnValue(rv.asReturnedValue());
+ QV4::ExecutionEngine *v4 = args->v4engine();
+ QV4::Scope scope(v4);
+ QV4::ScopedValue item(scope, (*args)[0]);
- QV4::ScopedString s(scope);
- QV4::ScopedValue v(scope);
+ QQuickItem *itemObj = 0;
+ if (!item->isNull()) {
+ QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
+ if (qobjectWrapper)
+ itemObj = qobject_cast<QQuickItem*>(qobjectWrapper->object());
+ }
- qreal x = (args->length() > 1) ? (v = (*args)[1])->asDouble() : 0;
- qreal y = (args->length() > 2) ? (v = (*args)[2])->asDouble() : 0;
+ if (!itemObj && !item->isNull()) {
+ qmlInfo(this) << "mapFromItem() given argument \"" << item->toQStringNoThrow()
+ << "\" which is neither null nor an Item";
+ return;
+ }
- if (args->length() > 3) {
- qreal w = (v = (*args)[3])->asDouble();
- qreal h = (args->length() > 4) ? (v = (*args)[4])->asDouble() : 0;
+ QV4::ScopedValue v(scope);
- QRectF r = mapRectFromItem(itemObj, QRectF(x, y, w, h));
+ qreal x = (args->length() > 1) ? (v = (*args)[1])->asDouble() : 0;
+ qreal y = (args->length() > 2) ? (v = (*args)[2])->asDouble() : 0;
- rv->put((s = v4->newString(QStringLiteral("x"))), (v = QV4::Primitive::fromDouble(r.x())));
- rv->put((s = v4->newString(QStringLiteral("y"))), (v = QV4::Primitive::fromDouble(r.y())));
- rv->put((s = v4->newString(QStringLiteral("width"))), (v = QV4::Primitive::fromDouble(r.width())));
- rv->put((s = v4->newString(QStringLiteral("height"))), (v = QV4::Primitive::fromDouble(r.height())));
- } else {
- QPointF p = mapFromItem(itemObj, QPointF(x, y));
+ QVariant result;
- rv->put((s = v4->newString(QStringLiteral("x"))), (v = QV4::Primitive::fromDouble(p.x())));
- rv->put((s = v4->newString(QStringLiteral("y"))), (v = QV4::Primitive::fromDouble(p.y())));
- }
+ if (args->length() > 3) {
+ qreal w = (v = (*args)[3])->asDouble();
+ qreal h = (args->length() > 4) ? (v = (*args)[4])->asDouble() : 0;
+ result = mapRectFromItem(itemObj, QRectF(x, y, w, h));
+ } else {
+ result = mapFromItem(itemObj, QPointF(x, y));
}
+
+ QV4::ScopedObject rv(scope, v4->fromVariant(result));
+ args->setReturnValue(rv.asReturnedValue());
}
/*!
@@ -4192,8 +4185,8 @@ QTransform QQuickItem::itemTransform(QQuickItem *other, bool *ok) const
\qmlmethod object QtQuick::Item::mapToItem(Item item, real x, real y, real width, real height)
Maps the point (\a x, \a y) or rect (\a x, \a y, \a width, \a height), which is in this
- item's coordinate system, to \a item's coordinate system, and returns an object with \c x and
- \c y (and optionally \c width and \c height) properties matching the mapped coordinate.
+ item's coordinate system, to \a item's coordinate system, and returns a \l point or \l rect
+ matching the mapped coordinate.
If \a item is a \c null value, this maps the point or rect to the coordinate system of the
root QML view.
@@ -4203,51 +4196,43 @@ QTransform QQuickItem::itemTransform(QQuickItem *other, bool *ok) const
*/
void QQuickItem::mapToItem(QQmlV4Function *args) const
{
- if (args->length() != 0) {
- QV4::ExecutionEngine *v4 = args->v4engine();
- QV4::Scope scope(v4);
- QV4::ScopedValue item(scope, (*args)[0]);
-
- QQuickItem *itemObj = 0;
- if (!item->isNull()) {
- QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
- if (qobjectWrapper)
- itemObj = qobject_cast<QQuickItem*>(qobjectWrapper->object());
- }
-
- if (!itemObj && !item->isNull()) {
- qmlInfo(this) << "mapToItem() given argument \"" << item->toQStringNoThrow()
- << "\" which is neither null nor an Item";
- return;
- }
-
- QV4::ScopedObject rv(scope, v4->newObject());
- args->setReturnValue(rv.asReturnedValue());
+ if (args->length() == 0)
+ return;
- QV4::ScopedValue v(scope);
+ QV4::ExecutionEngine *v4 = args->v4engine();
+ QV4::Scope scope(v4);
+ QV4::ScopedValue item(scope, (*args)[0]);
- qreal x = (args->length() > 1) ? (v = (*args)[1])->asDouble() : 0;
- qreal y = (args->length() > 2) ? (v = (*args)[2])->asDouble() : 0;
+ QQuickItem *itemObj = 0;
+ if (!item->isNull()) {
+ QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
+ if (qobjectWrapper)
+ itemObj = qobject_cast<QQuickItem*>(qobjectWrapper->object());
+ }
- QV4::ScopedString s(scope);
+ if (!itemObj && !item->isNull()) {
+ qmlInfo(this) << "mapToItem() given argument \"" << item->toQStringNoThrow()
+ << "\" which is neither null nor an Item";
+ return;
+ }
- if (args->length() > 3) {
- qreal w = (v = (*args)[3])->asDouble();
- qreal h = (args->length() > 4) ? (v = (*args)[4])->asDouble() : 0;
+ QV4::ScopedValue v(scope);
+ QVariant result;
- QRectF r = mapRectToItem(itemObj, QRectF(x, y, w, h));
+ qreal x = (args->length() > 1) ? (v = (*args)[1])->asDouble() : 0;
+ qreal y = (args->length() > 2) ? (v = (*args)[2])->asDouble() : 0;
- rv->put((s = v4->newString(QStringLiteral("x"))), (v = QV4::Primitive::fromDouble(r.x())));
- rv->put((s = v4->newString(QStringLiteral("y"))), (v = QV4::Primitive::fromDouble(r.y())));
- rv->put((s = v4->newString(QStringLiteral("width"))), (v = QV4::Primitive::fromDouble(r.width())));
- rv->put((s = v4->newString(QStringLiteral("height"))), (v = QV4::Primitive::fromDouble(r.height())));
- } else {
- QPointF p = mapToItem(itemObj, QPointF(x, y));
+ if (args->length() > 3) {
+ qreal w = (v = (*args)[3])->asDouble();
+ qreal h = (args->length() > 4) ? (v = (*args)[4])->asDouble() : 0;
- rv->put((s = v4->newString(QStringLiteral("x"))), (v = QV4::Primitive::fromDouble(p.x())));
- rv->put((s = v4->newString(QStringLiteral("y"))), (v = QV4::Primitive::fromDouble(p.y())));
- }
+ result = mapRectToItem(itemObj, QRectF(x, y, w, h));
+ } else {
+ result = mapToItem(itemObj, QPointF(x, y));
}
+
+ QV4::ScopedObject rv(scope, v4->fromVariant(result));
+ args->setReturnValue(rv.asReturnedValue());
}
/*!
@@ -7315,18 +7300,27 @@ bool QQuickItem::event(QEvent *ev)
}
#ifndef QT_NO_DEBUG_STREAM
+// FIXME: Qt 6: Make this QDebug operator<<(QDebug debug, const QQuickItem *item)
QDebug operator<<(QDebug debug, QQuickItem *item)
{
+ QDebugStateSaver saver(debug);
+ debug.nospace();
if (!item) {
debug << "QQuickItem(0)";
return debug;
}
- debug << item->metaObject()->className() << "(this =" << ((void*)item)
- << ", name=" << item->objectName()
- << ", parent =" << ((void*)item->parentItem())
- << ", geometry =" << QRectF(item->position(), QSizeF(item->width(), item->height()))
- << ", z =" << item->z() << ')';
+ const QRectF rect(item->position(), QSizeF(item->width(), item->height()));
+
+ debug << item->metaObject()->className() << '(' << static_cast<void *>(item);
+ if (!item->objectName().isEmpty())
+ debug << ", name=" << item->objectName();
+ debug << ", parent=" << static_cast<void *>(item->parentItem())
+ << ", geometry=";
+ QtDebugUtils::formatQRect(debug, rect);
+ if (const qreal z = item->z())
+ debug << ", z=" << z;
+ debug << ')';
return debug;
}
#endif
diff --git a/src/quick/items/qquicktext.cpp b/src/quick/items/qquicktext.cpp
index f33f171738..9db5fa2059 100644
--- a/src/quick/items/qquicktext.cpp
+++ b/src/quick/items/qquicktext.cpp
@@ -1667,7 +1667,10 @@ void QQuickText::setLinkColor(const QColor &color)
return;
d->linkColor = rgb;
- update();
+ if (isComponentComplete()) {
+ d->updateType = QQuickTextPrivate::UpdatePaintNode;
+ update();
+ }
emit linkColorChanged();
}
diff --git a/src/quick/items/qquicktextedit.cpp b/src/quick/items/qquicktextedit.cpp
index 29300644b9..e10aec229e 100644
--- a/src/quick/items/qquicktextedit.cpp
+++ b/src/quick/items/qquicktextedit.cpp
@@ -1890,6 +1890,10 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
int currentNodeSize = 0;
int nodeStart = firstDirtyPos;
QPointF basePosition(d->xoff, d->yoff);
+ QMatrix4x4 basePositionMatrix;
+ basePositionMatrix.translate(basePosition.x(), basePosition.y());
+ rootNode->setMatrix(basePositionMatrix);
+
QPointF nodeOffset;
TextNode *firstCleanNode = (nodeIterator != d->textNodeMap.end()) ? *nodeIterator : 0;
@@ -1901,7 +1905,6 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
frames.append(textFrame->childFrames());
rootNode->frameDecorationsNode->m_engine->addFrameDecorations(d->document, textFrame);
-
if (textFrame->lastPosition() < firstDirtyPos || (firstCleanNode && textFrame->firstPosition() >= firstCleanNode->startPos()))
continue;
node = d->createTextNode();
@@ -1922,7 +1925,7 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
nodeOffset = d->document->documentLayout()->frameBoundingRect(textFrame).topLeft();
updateNodeTransform(node, nodeOffset);
while (!it.atEnd())
- node->m_engine->addTextBlock(d->document, (it++).currentBlock(), basePosition - nodeOffset, d->color, QColor(), selectionStart(), selectionEnd() - 1);
+ node->m_engine->addTextBlock(d->document, (it++).currentBlock(), -nodeOffset, d->color, QColor(), selectionStart(), selectionEnd() - 1);
nodeStart = textFrame->firstPosition();
} else {
// Having nodes spanning across frame boundaries will break the current bookkeeping mechanism. We need to prevent that.
@@ -1945,7 +1948,7 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
nodeStart = block.position();
}
- node->m_engine->addTextBlock(d->document, block, basePosition - nodeOffset, d->color, QColor(), selectionStart(), selectionEnd() - 1);
+ node->m_engine->addTextBlock(d->document, block, -nodeOffset, d->color, QColor(), selectionStart(), selectionEnd() - 1);
currentNodeSize += block.length();
if ((it.atEnd()) || (firstCleanNode && block.next().position() >= firstCleanNode->startPos())) // last node that needed replacing or last block of the frame
@@ -1989,7 +1992,7 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
if (d->cursorComponent == 0 && !isReadOnly()) {
QSGRectangleNode* cursor = 0;
if (d->cursorVisible && d->control->cursorOn())
- cursor = d->sceneGraphContext()->createRectangleNode(cursorRectangle(), d->color);
+ cursor = d->sceneGraphContext()->createRectangleNode(d->control->cursorRect(), d->color);
rootNode->resetCursorNode(cursor);
}
diff --git a/src/quick/items/qquicktextinput.cpp b/src/quick/items/qquicktextinput.cpp
index c6a6bd9c45..db19f12f83 100644
--- a/src/quick/items/qquicktextinput.cpp
+++ b/src/quick/items/qquicktextinput.cpp
@@ -1398,15 +1398,8 @@ void QQuickTextInput::mousePressEvent(QMouseEvent *event)
int cursor = d->positionAt(event->localPos());
d->moveCursor(cursor, mark);
- if (d->focusOnPress) {
- bool hadActiveFocus = hasActiveFocus();
- forceActiveFocus();
-#ifndef QT_NO_IM
- // re-open input panel on press if already focused
- if (hasActiveFocus() && hadActiveFocus && !d->m_readOnly)
- qGuiApp->inputMethod()->show();
-#endif
- }
+ if (d->focusOnPress && !qGuiApp->styleHints()->setFocusOnTouchRelease())
+ ensureActiveFocus();
event->setAccepted(true);
}
@@ -1456,6 +1449,10 @@ void QQuickTextInput::mouseReleaseEvent(QMouseEvent *event)
}
}
#endif
+
+ if (d->focusOnPress && qGuiApp->styleHints()->setFocusOnTouchRelease())
+ ensureActiveFocus();
+
if (!event->isAccepted())
QQuickImplicitSizeItem::mouseReleaseEvent(event);
}
@@ -1688,6 +1685,19 @@ void QQuickTextInput::invalidateFontCaches()
d->m_textLayout.engine()->resetFontEngineCache();
}
+void QQuickTextInput::ensureActiveFocus()
+{
+ Q_D(QQuickTextInput);
+
+ bool hadActiveFocus = hasActiveFocus();
+ forceActiveFocus();
+#ifndef QT_NO_IM
+ // re-open input panel on press if already focused
+ if (hasActiveFocus() && hadActiveFocus && !d->m_readOnly)
+ qGuiApp->inputMethod()->show();
+#endif
+}
+
QSGNode *QQuickTextInput::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *data)
{
Q_UNUSED(data);
diff --git a/src/quick/items/qquicktextinput_p.h b/src/quick/items/qquicktextinput_p.h
index 1550e4eef7..333f55b35f 100644
--- a/src/quick/items/qquicktextinput_p.h
+++ b/src/quick/items/qquicktextinput_p.h
@@ -334,6 +334,7 @@ Q_SIGNALS:
private:
void invalidateFontCaches();
+ void ensureActiveFocus();
protected:
void geometryChanged(const QRectF &newGeometry,
diff --git a/src/quick/items/qquickwindow.cpp b/src/quick/items/qquickwindow.cpp
index 696f8f9080..bccebb1a14 100644
--- a/src/quick/items/qquickwindow.cpp
+++ b/src/quick/items/qquickwindow.cpp
@@ -72,6 +72,7 @@
QT_BEGIN_NAMESPACE
Q_LOGGING_CATEGORY(DBG_TOUCH, "qt.quick.touch");
+Q_LOGGING_CATEGORY(DBG_TOUCH_TARGET, "qt.quick.touch.target");
Q_LOGGING_CATEGORY(DBG_MOUSE, "qt.quick.mouse");
Q_LOGGING_CATEGORY(DBG_FOCUS, "qt.quick.focus");
Q_LOGGING_CATEGORY(DBG_DIRTY, "qt.quick.dirty");
@@ -552,6 +553,7 @@ bool QQuickWindowPrivate::translateTouchToMouse(QQuickItem *item, QTouchEvent *e
// handler spins the event loop all subsequent moves and releases get lost.
touchMouseId = p.id();
itemForTouchPointId[touchMouseId] = item;
+ qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << p.id() << "->" << item;
QScopedPointer<QMouseEvent> mousePress(touchToMouseEvent(QEvent::MouseButtonPress, p, event, item, false));
// Send a single press and see if that's accepted
@@ -563,8 +565,10 @@ bool QQuickWindowPrivate::translateTouchToMouse(QQuickItem *item, QTouchEvent *e
event->setAccepted(mousePress->isAccepted());
if (!mousePress->isAccepted()) {
touchMouseId = -1;
- if (itemForTouchPointId.value(p.id()) == item)
+ if (itemForTouchPointId.value(p.id()) == item) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << p.id() << "disassociated";
itemForTouchPointId.remove(p.id());
+ }
if (mouseGrabberItem == item)
item->ungrabMouse();
@@ -599,6 +603,7 @@ bool QQuickWindowPrivate::translateTouchToMouse(QQuickItem *item, QTouchEvent *e
QCoreApplication::sendEvent(item, me.data());
event->setAccepted(me->isAccepted());
if (me->isAccepted()) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << p.id() << "->" << mouseGrabberItem;
itemForTouchPointId[p.id()] = mouseGrabberItem; // N.B. the mouseGrabberItem may be different after returning from sendEvent()
return true;
}
@@ -650,8 +655,10 @@ void QQuickWindowPrivate::setMouseGrabber(QQuickItem *grabber)
if (touchMouseId != -1) {
// update the touch item for mouse touch id to the new grabber
itemForTouchPointId.remove(touchMouseId);
- if (grabber)
+ if (grabber) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << touchMouseId << "->" << mouseGrabberItem;
itemForTouchPointId[touchMouseId] = grabber;
+ }
}
if (oldGrabber) {
@@ -1972,6 +1979,7 @@ void QQuickWindowPrivate::reallyDeliverTouchEvent(QTouchEvent *event)
if (event->touchPointStates() & Qt::TouchPointReleased) {
for (int i=0; i<touchPoints.count(); i++) {
if (touchPoints[i].state() == Qt::TouchPointReleased) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP" << touchPoints[i].id() << "released";
itemForTouchPointId.remove(touchPoints[i].id());
if (touchPoints[i].id() == touchMouseId)
touchMouseId = -1;
@@ -2079,7 +2087,7 @@ bool QQuickWindowPrivate::deliverMatchingPointsToItem(QQuickItem *item, QTouchEv
touchEvent.data()->setTarget(item);
bool touchEventAccepted = false;
- qCDebug(DBG_TOUCH) << " - considering delivering " << touchEvent << " to " << item;
+ qCDebug(DBG_TOUCH) << " - considering delivering " << touchEvent.data() << " to " << item;
// First check whether the parent wants to be a filter,
// and if the parent accepts the event we are done.
@@ -2093,11 +2101,13 @@ bool QQuickWindowPrivate::deliverMatchingPointsToItem(QQuickItem *item, QTouchEv
}
// Since it can change in sendEvent, update itemForTouchPointId now
- foreach (int id, matchingNewPoints)
+ foreach (int id, matchingNewPoints) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP" << id << "->" << item;
itemForTouchPointId[id] = item;
+ }
// Deliver the touch event to the given item
- qCDebug(DBG_TOUCH) << " - actually delivering " << touchEvent << " to " << item;
+ qCDebug(DBG_TOUCH) << " - actually delivering " << touchEvent.data() << " to " << item;
QCoreApplication::sendEvent(item, touchEvent.data());
touchEventAccepted = touchEvent->isAccepted();
@@ -2120,8 +2130,10 @@ bool QQuickWindowPrivate::deliverMatchingPointsToItem(QQuickItem *item, QTouchEv
// But if the event was not accepted then we know this item
// will not be interested in further updates for those touchpoint IDs either.
foreach (int id, matchingNewPoints)
- if (itemForTouchPointId[id] == item)
+ if (itemForTouchPointId[id] == item) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP" << id << "disassociated";
itemForTouchPointId.remove(id);
+ }
}
return touchEventAccepted;
@@ -2410,6 +2422,7 @@ bool QQuickWindowPrivate::sendFilteredTouchEvent(QQuickItem *target, QQuickItem
if (target->childMouseEventFilter(item, mouseEvent.data())) {
qCDebug(DBG_TOUCH) << " - second chance intercepted on childMouseEventFilter by " << target;
if (t != QEvent::MouseButtonRelease) {
+ qCDebug(DBG_TOUCH_TARGET) << "TP" << tp.id() << "->" << target;
itemForTouchPointId[tp.id()] = target;
touchMouseId = tp.id();
target->grabMouse();
diff --git a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
index ec9106e86b..0c4b2f9af9 100644
--- a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
+++ b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
@@ -92,6 +92,7 @@ protected:
int m_matrix_id;
int m_color_id;
int m_textureScale_id;
+ float m_devicePixelRatio;
QFontEngine::GlyphFormat m_glyphFormat;
};
@@ -124,7 +125,8 @@ void QSGTextMaskShader::initialize()
m_matrix_id = program()->uniformLocation("matrix");
m_color_id = program()->uniformLocation("color");
m_textureScale_id = program()->uniformLocation("textureScale");
- program()->setUniformValue("dpr", (float) qsg_device_pixel_ratio(QOpenGLContext::currentContext()));
+ m_devicePixelRatio = (float) qsg_device_pixel_ratio(QOpenGLContext::currentContext());
+ program()->setUniformValue("dpr", m_devicePixelRatio);
}
void QSGTextMaskShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
@@ -152,6 +154,12 @@ void QSGTextMaskShader::updateState(const RenderState &state, QSGMaterial *newEf
}
}
+ float devicePixelRatio = (float) qsg_device_pixel_ratio(QOpenGLContext::currentContext());
+ if (m_devicePixelRatio != devicePixelRatio) {
+ m_devicePixelRatio = devicePixelRatio;
+ program()->setUniformValue("dpr", m_devicePixelRatio);
+ }
+
if (state.isMatrixDirty())
program()->setUniformValue(m_matrix_id, state.combinedMatrix());
}
diff --git a/src/quick/scenegraph/qsgrenderloop.cpp b/src/quick/scenegraph/qsgrenderloop.cpp
index 61de81576c..ce3bf7d61d 100644
--- a/src/quick/scenegraph/qsgrenderloop.cpp
+++ b/src/quick/scenegraph/qsgrenderloop.cpp
@@ -91,12 +91,8 @@ void QSGRenderLoop::cleanup()
foreach (QQuickWindow *w, s_instance->windows()) {
QQuickWindowPrivate *wd = QQuickWindowPrivate::get(w);
if (wd->windowManager == s_instance) {
- // windowDestroyed() triggers a sendPostedEvent(DeferredDelete),
- // so wd will be null if the window was deleteLater()'ed
- bool wasDeleted = wd->wasDeleted;
s_instance->windowDestroyed(w);
- if (!wasDeleted)
- wd->windowManager = 0;
+ wd->windowManager = 0;
}
}
delete s_instance;
@@ -300,7 +296,6 @@ void QSGGuiThreadRenderLoop::windowDestroyed(QQuickWindow *window)
d->cleanupNodesOnShutdown();
if (m_windows.size() == 0) {
rc->invalidate();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
delete gl;
gl = 0;
} else if (gl && window == gl->surface() && current) {
diff --git a/src/quick/scenegraph/qsgthreadedrenderloop.cpp b/src/quick/scenegraph/qsgthreadedrenderloop.cpp
index e1a54810b7..7b1e24246b 100644
--- a/src/quick/scenegraph/qsgthreadedrenderloop.cpp
+++ b/src/quick/scenegraph/qsgthreadedrenderloop.cpp
@@ -767,9 +767,9 @@ void QSGThreadedRenderLoop::animationStopped()
void QSGThreadedRenderLoop::startOrStopAnimationTimer()
{
int exposedWindows = 0;
- Window *theOne = 0;
+ const Window *theOne = 0;
for (int i=0; i<m_windows.size(); ++i) {
- Window &w = m_windows[i];
+ const Window &w = m_windows.at(i);
if (w.window->isVisible() && w.window->isExposed()) {
++exposedWindows;
theOne = &w;
@@ -781,7 +781,7 @@ void QSGThreadedRenderLoop::startOrStopAnimationTimer()
m_animation_timer = 0;
// If animations are running, make sure we keep on animating
if (m_animation_driver->isRunning())
- maybePostPolishRequest(theOne);
+ maybePostPolishRequest(const_cast<Window *>(theOne));
} else if (m_animation_timer == 0 && exposedWindows != 1 && m_animation_driver->isRunning()) {
m_animation_timer = startTimer(qsgrl_animation_interval());
diff --git a/src/quick/scenegraph/qsgwindowsrenderloop.cpp b/src/quick/scenegraph/qsgwindowsrenderloop.cpp
index e4db348ef0..b88d21ce66 100644
--- a/src/quick/scenegraph/qsgwindowsrenderloop.cpp
+++ b/src/quick/scenegraph/qsgwindowsrenderloop.cpp
@@ -234,7 +234,6 @@ void QSGWindowsRenderLoop::windowDestroyed(QQuickWindow *window)
d->cleanupNodesOnShutdown();
if (m_windows.size() == 0) {
d->context->invalidate();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
delete m_gl;
m_gl = 0;
} else if (m_gl && current) {
diff --git a/src/quick/scenegraph/shaders/smoothtexture.vert b/src/quick/scenegraph/shaders/smoothtexture.vert
index 1ce824a68f..900fbc6a72 100644
--- a/src/quick/scenegraph/shaders/smoothtexture.vert
+++ b/src/quick/scenegraph/shaders/smoothtexture.vert
@@ -48,5 +48,8 @@ void main()
bool onEdge = any(notEqual(vertexOffset, vec2(0.)));
bool outerEdge = all(equal(texCoordOffset, vec2(0.)));
- vertexOpacity = onEdge && outerEdge ? 0. : opacity;
+ if (onEdge && outerEdge)
+ vertexOpacity = 0.;
+ else
+ vertexOpacity = opacity;
} \ No newline at end of file
diff --git a/src/quick/util/qquickanimator.cpp b/src/quick/util/qquickanimator.cpp
index 1a355a5eac..61fb7481d9 100644
--- a/src/quick/util/qquickanimator.cpp
+++ b/src/quick/util/qquickanimator.cpp
@@ -293,6 +293,7 @@ QAbstractAnimationJob *QQuickAnimator::transition(QQuickStateActions &actions,
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The XAnimator type animates the x position of an Item.
\l{Animator} types are different from normal Animation types. When
@@ -325,6 +326,7 @@ QQuickAnimatorJob *QQuickXAnimator::createJob() const { return new QQuickXAnimat
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The YAnimator type animates the y position of an Item.
\l{Animator} types are different from normal Animation types. When
@@ -357,6 +359,7 @@ QQuickAnimatorJob *QQuickYAnimator::createJob() const { return new QQuickYAnimat
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The ScaleAnimator type animates the scale factor of an Item.
\l{Animator} types are different from normal Animation types. When
@@ -389,6 +392,7 @@ QQuickAnimatorJob *QQuickScaleAnimator::createJob() const { return new QQuickSca
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The OpacityAnimator type animates the opacity of an Item.
\l{Animator} types are different from normal Animation types. When
@@ -420,6 +424,7 @@ QQuickAnimatorJob *QQuickOpacityAnimator::createJob() const { return new QQuickO
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The RotationAnimator type animates the rotation of an Item.
\l{Animator} types are different from normal Animation types. When
@@ -491,6 +496,7 @@ QQuickRotationAnimator::RotationDirection QQuickRotationAnimator::direction() co
\inqmlmodule QtQuick
\since 5.2
\ingroup qtquick-transitions-animations
+ \inherits Animator
\brief The UniformAnimator type animates a uniform of a ShaderEffect.
\l{Animator} types are different from normal Animation types. When
diff --git a/src/quick/util/qquickanimatorjob.cpp b/src/quick/util/qquickanimatorjob.cpp
index dbd1a662df..8b617e5e3f 100644
--- a/src/quick/util/qquickanimatorjob.cpp
+++ b/src/quick/util/qquickanimatorjob.cpp
@@ -42,6 +42,7 @@
#include <private/qanimationgroupjob_p.h>
#include <qcoreapplication.h>
+#include <qdebug.h>
QT_BEGIN_NAMESPACE
@@ -133,6 +134,13 @@ void QQuickAnimatorProxyJob::updateState(QAbstractAnimationJob::State newState,
}
}
+void QQuickAnimatorProxyJob::debugAnimation(QDebug d) const
+{
+ d << "QuickAnimatorProxyJob("<< hex << (void *) this << dec
+ << "state:" << state() << "duration:" << duration()
+ << "proxying: (" << job() << ')';
+}
+
void QQuickAnimatorProxyJob::windowChanged(QQuickWindow *window)
{
setWindow(window);
@@ -215,6 +223,13 @@ QQuickAnimatorJob::QQuickAnimatorJob()
m_isRenderThreadJob = true;
}
+void QQuickAnimatorJob::debugAnimation(QDebug d) const
+{
+ d << "QuickAnimatorJob(" << hex << (void *) this << dec
+ << ") state:" << state() << "duration:" << duration()
+ << "target:" << m_target << "value:" << m_value;
+}
+
qreal QQuickAnimatorJob::value() const
{
qreal v;
diff --git a/src/quick/util/qquickanimatorjob_p.h b/src/quick/util/qquickanimatorjob_p.h
index 4c0715bd11..34c106e89b 100644
--- a/src/quick/util/qquickanimatorjob_p.h
+++ b/src/quick/util/qquickanimatorjob_p.h
@@ -74,6 +74,7 @@ public:
protected:
void updateCurrentTime(int);
void updateState(QAbstractAnimationJob::State newState, QAbstractAnimationJob::State oldState);
+ void debugAnimation(QDebug d) const Q_DECL_OVERRIDE;
public Q_SLOTS:
void windowChanged(QQuickWindow *window);
@@ -137,6 +138,7 @@ public:
protected:
QQuickAnimatorJob();
+ void debugAnimation(QDebug d) const Q_DECL_OVERRIDE;
QQuickItem *m_target;
QQuickAnimatorController *m_controller;
diff --git a/src/quick/util/qquickstate.cpp b/src/quick/util/qquickstate.cpp
index c35ca46aa8..98d7a76c7e 100644
--- a/src/quick/util/qquickstate.cpp
+++ b/src/quick/util/qquickstate.cpp
@@ -157,6 +157,11 @@ QQuickState::~QQuickState()
Q_D(QQuickState);
if (d->group)
d->group->removeState(this);
+
+ foreach (const QQuickSimpleAction &action, d->revertList) {
+ if (action.binding())
+ action.binding()->destroy();
+ }
}
/*!
diff --git a/src/quickwidgets/qquickwidget.cpp b/src/quickwidgets/qquickwidget.cpp
index 269928e531..29577b856d 100644
--- a/src/quickwidgets/qquickwidget.cpp
+++ b/src/quickwidgets/qquickwidget.cpp
@@ -216,7 +216,7 @@ void QQuickWidgetPrivate::render(bool needsSync)
QOpenGLFramebufferObject::blitFramebuffer(resolvedFbo, rect, fbo, rect);
}
- context->functions()->glFlush();
+ static_cast<QOpenGLExtensions *>(context->functions())->flushShared();
}
void QQuickWidgetPrivate::renderSceneGraph()
@@ -1226,4 +1226,23 @@ void QQuickWidget::setClearColor(const QColor &color)
d->offscreenWindow->setColor(color);
}
+/*!
+ \since 5.5
+
+ Returns the offscreen QQuickWindow which is used by this widget to drive
+ the Qt Quick rendering. This is useful if you want to use QQuickWindow
+ APIs that are not currently exposed by QQuickWidget, for instance
+ connecting to the QQuickWindow::beforeRendering() signal in order
+ to draw native OpenGL content below Qt Quick's own rendering.
+
+ \warning Use the return value of this function with caution. In
+ particular, do not ever attempt to show the QQuickWindow, and be
+ very careful when using other QWindow-only APIs.
+*/
+QQuickWindow *QQuickWidget::quickWindow() const
+{
+ Q_D(const QQuickWidget);
+ return d->offscreenWindow;
+}
+
QT_END_NAMESPACE
diff --git a/src/quickwidgets/qquickwidget.h b/src/quickwidgets/qquickwidget.h
index b961a6eeaf..a8bf03edfb 100644
--- a/src/quickwidgets/qquickwidget.h
+++ b/src/quickwidgets/qquickwidget.h
@@ -90,6 +90,8 @@ public:
void setClearColor(const QColor &color);
+ QQuickWindow *quickWindow() const;
+
public Q_SLOTS:
void setSource(const QUrl&);
void setContent(const QUrl& url, QQmlComponent *component, QObject *item);
diff --git a/tests/auto/auto.pro b/tests/auto/auto.pro
index 0ea9b91c2e..425e88b983 100644
--- a/tests/auto/auto.pro
+++ b/tests/auto/auto.pro
@@ -2,7 +2,6 @@ TEMPLATE=subdirs
SUBDIRS=\
qml \
quick \
- headersclean \
particles \
qmltest \
qmldevtools \
@@ -16,4 +15,3 @@ qmldevtools.CONFIG = host_build
installed_cmake.depends = cmake
-testcocoon: SUBDIRS -= headersclean
diff --git a/tests/auto/headersclean/headersclean.pro b/tests/auto/headersclean/headersclean.pro
deleted file mode 100644
index 2698d67124..0000000000
--- a/tests/auto/headersclean/headersclean.pro
+++ /dev/null
@@ -1,2 +0,0 @@
-QT = qml quick qmltest
-load(qt_headersclean)
diff --git a/tests/auto/particles/qquickcustomparticle/qquickcustomparticle.pro b/tests/auto/particles/qquickcustomparticle/qquickcustomparticle.pro
index 3070d33631..48e7303f86 100644
--- a/tests/auto/particles/qquickcustomparticle/qquickcustomparticle.pro
+++ b/tests/auto/particles/qquickcustomparticle/qquickcustomparticle.pro
@@ -10,6 +10,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private quickparticles-private testlib
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-
-# Skip until fix from qtbase 5.4.0 reached dev.
-win32: CONFIG += insignificant_test
diff --git a/tests/auto/particles/qquicktrailemitter/qquicktrailemitter.pro b/tests/auto/particles/qquicktrailemitter/qquicktrailemitter.pro
index 1f957c23ff..1cb792eff2 100644
--- a/tests/auto/particles/qquicktrailemitter/qquicktrailemitter.pro
+++ b/tests/auto/particles/qquicktrailemitter/qquicktrailemitter.pro
@@ -3,8 +3,6 @@ TARGET = tst_qquicktrailemitter
SOURCES += tst_qquicktrailemitter.cpp
macx:CONFIG -= app_bundle
-win32-msvc2012:CONFIG += insignificant_test # QTBUG-33421
-
include (../../shared/util.pri)
TESTDATA = data/*
diff --git a/tests/auto/qml/debugger/qqmldebugjs/qqmldebugjs.pro b/tests/auto/qml/debugger/qqmldebugjs/qqmldebugjs.pro
index d4ce36dc4a..eb5f17a55d 100644
--- a/tests/auto/qml/debugger/qqmldebugjs/qqmldebugjs.pro
+++ b/tests/auto/qml/debugger/qqmldebugjs/qqmldebugjs.pro
@@ -22,5 +22,3 @@ OTHER_FILES += data/test.qml data/test.js \
data/breakpointRelocation.qml \
data/createComponent.qml
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-
-mac:CONFIG+=insignificant_test # QTBUG-28263
diff --git a/tests/auto/qml/debugger/qqmlprofilerservice/tst_qqmlprofilerservice.cpp b/tests/auto/qml/debugger/qqmlprofilerservice/tst_qqmlprofilerservice.cpp
index d34860ff62..094bf43549 100644
--- a/tests/auto/qml/debugger/qqmlprofilerservice/tst_qqmlprofilerservice.cpp
+++ b/tests/auto/qml/debugger/qqmlprofilerservice/tst_qqmlprofilerservice.cpp
@@ -43,6 +43,9 @@
struct QQmlProfilerData
{
+ QQmlProfilerData(int messageType = 0, int detailType = 0, const QString &detailData = QString())
+ : messageType(messageType), detailType(detailType), detailData(detailData) {}
+
qint64 time;
int messageType;
int detailType;
@@ -174,9 +177,29 @@ private:
QQmlDebugConnection *m_connection;
QQmlProfilerClient *m_client;
+ enum MessageListType {
+ MessageListQML,
+ MessageListJavaScript,
+ MessageListJsHeap,
+ MessageListAsynchronous,
+ MessageListPixmap
+ };
+
+ enum CheckType {
+ CheckMessageType = 1 << 0,
+ CheckDetailType = 1 << 1,
+ CheckLine = 1 << 2,
+ CheckColumn = 1 << 3,
+ CheckDataEndsWith = 1 << 4,
+
+ CheckAll = CheckMessageType | CheckDetailType | CheckLine | CheckColumn | CheckDataEndsWith
+ };
+
void connect(bool block, const QString &testFile);
void checkTraceReceived();
void checkJsHeap();
+ bool verify(MessageListType type, int expectedPosition, const QQmlProfilerData &expected,
+ quint32 checks);
private slots:
void cleanup();
@@ -192,6 +215,8 @@ private slots:
void javascript();
};
+#define VERIFY(type, position, expected, checks) QVERIFY(verify(type, position, expected, checks))
+
void QQmlProfilerClient::messageReceived(const QByteArray &message)
{
QByteArray msg = message;
@@ -355,15 +380,15 @@ void tst_QQmlProfilerService::connect(bool block, const QString &testFile)
void tst_QQmlProfilerService::checkTraceReceived()
{
QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())), "No trace received in time.");
- QVERIFY(m_client->asynchronousMessages.count());
// must start with "StartTrace"
- QCOMPARE(m_client->asynchronousMessages.first().messageType, (int)QQmlProfilerClient::Event);
- QCOMPARE(m_client->asynchronousMessages.first().detailType, (int)QQmlProfilerClient::StartTrace);
+ QQmlProfilerData expected(QQmlProfilerClient::Event, QQmlProfilerClient::StartTrace);
+ VERIFY(MessageListAsynchronous, 0, expected, CheckMessageType | CheckDetailType);
// must end with "EndTrace"
- QCOMPARE(m_client->asynchronousMessages.last().messageType, (int)QQmlProfilerClient::Event);
- QCOMPARE(m_client->asynchronousMessages.last().detailType, (int)QQmlProfilerClient::EndTrace);
+ expected.detailType = QQmlProfilerClient::EndTrace;
+ VERIFY(MessageListAsynchronous, m_client->asynchronousMessages.length() - 1, expected,
+ CheckMessageType | CheckDetailType);
}
void tst_QQmlProfilerService::checkJsHeap()
@@ -375,6 +400,7 @@ void tst_QQmlProfilerService::checkJsHeap()
bool seen_large = false;
qint64 allocated = 0;
qint64 used = 0;
+ qint64 lastTimestamp = -1;
foreach (const QQmlProfilerData &message, m_client->jsHeapMessages) {
switch (message.detailType) {
case QQmlProfilerClient::HeapPage:
@@ -392,6 +418,17 @@ void tst_QQmlProfilerService::checkJsHeap()
break;
}
+ QVERIFY(message.time >= lastTimestamp);
+ // The heap will only be consistent after all events of the same timestamp are processed.
+ if (lastTimestamp == -1) {
+ lastTimestamp = message.time;
+ continue;
+ } else if (message.time == lastTimestamp) {
+ continue;
+ }
+
+ lastTimestamp = message.time;
+
QVERIFY2(used >= 0, QString::fromLatin1("Negative memory usage seen: %1")
.arg(used).toUtf8().constData());
@@ -408,6 +445,68 @@ void tst_QQmlProfilerService::checkJsHeap()
QVERIFY2(seen_large, "No large item seen");
}
+bool tst_QQmlProfilerService::verify(tst_QQmlProfilerService::MessageListType type,
+ int expectedPosition, const QQmlProfilerData &expected,
+ quint32 checks)
+{
+ QList<QQmlProfilerData> *target = 0;
+ switch (type) {
+ case MessageListQML: target = &(m_client->qmlMessages); break;
+ case MessageListJavaScript: target = &(m_client->javascriptMessages); break;
+ case MessageListJsHeap: target = &(m_client->jsHeapMessages); break;
+ case MessageListAsynchronous: target = &(m_client->asynchronousMessages); break;
+ case MessageListPixmap: target = &(m_client->pixmapMessages); break;
+ }
+
+ if (target->length() <= expectedPosition) {
+ qWarning() << "Not enough events. expected position:" << expectedPosition
+ << "length:" << target->length();
+ return false;
+ }
+
+ uint position = expectedPosition;
+ qint64 timestamp = target->at(expectedPosition).time;
+ while (position > 0 && target->at(position - 1).time == timestamp)
+ --position;
+
+ QStringList warnings;
+
+ do {
+ const QQmlProfilerData &actual = target->at(position);
+ if ((checks & CheckMessageType) && actual.messageType != expected.messageType) {
+ warnings << QString::fromLatin1("%1: unexpected messageType. actual: %2 - expected: %3")
+ .arg(position).arg(actual.messageType).arg(expected.messageType);
+ continue;
+ }
+ if ((checks & CheckDetailType) && actual.detailType != expected.detailType) {
+ warnings << QString::fromLatin1("%1: unexpected detailType. actual: %2 - expected: %3")
+ .arg(position).arg(actual.detailType).arg(expected.detailType);
+ continue;
+ }
+ if ((checks & CheckLine) && actual.line != expected.line) {
+ warnings << QString::fromLatin1("%1: unexpected line. actual: %2 - expected: %3")
+ .arg(position).arg(actual.line).arg(expected.line);
+ continue;
+ }
+ if ((checks & CheckColumn) && actual.column != expected.column) {
+ warnings << QString::fromLatin1("%1: unexpected column. actual: %2 - expected: %3")
+ .arg(position).arg(actual.column).arg(expected.column);
+ continue;
+ }
+ if ((checks & CheckDataEndsWith) && !actual.detailData.endsWith(expected.detailData)) {
+ warnings << QString::fromLatin1("%1: unexpected detailData. actual: %2 - expected: %3")
+ .arg(position).arg(actual.detailData).arg(expected.detailData);
+ continue;
+ }
+ return true;
+ } while (target->at(++position).time == timestamp);
+
+ foreach (const QString &message, warnings)
+ qWarning() << message.toLocal8Bit().constData();
+
+ return false;
+}
+
void tst_QQmlProfilerService::cleanup()
{
if (QTest::currentTestFailed()) {
@@ -512,27 +611,26 @@ void tst_QQmlProfilerService::pixmapCacheData()
checkTraceReceived();
checkJsHeap();
- QVERIFY2(m_client->pixmapMessages.count() >= 4,
- QString::number(m_client->pixmapMessages.count()).toUtf8().constData());
+
+ QQmlProfilerData expected(QQmlProfilerClient::PixmapCacheEvent);
// image starting to load
- QCOMPARE(m_client->pixmapMessages[0].messageType, (int)QQmlProfilerClient::PixmapCacheEvent);
- QCOMPARE(m_client->pixmapMessages[0].detailType, (int)QQmlProfilerClient::PixmapLoadingStarted);
+ expected.detailType = QQmlProfilerClient::PixmapLoadingStarted;
+ VERIFY(MessageListPixmap, 0, expected, CheckMessageType | CheckDetailType);
// image size
- QCOMPARE(m_client->pixmapMessages[1].messageType, (int)QQmlProfilerClient::PixmapCacheEvent);
- QCOMPARE(m_client->pixmapMessages[1].detailType, (int)QQmlProfilerClient::PixmapSizeKnown);
- QCOMPARE(m_client->pixmapMessages[1].line, 2); // width
- QCOMPARE(m_client->pixmapMessages[1].column, 2); // height
+ expected.detailType = QQmlProfilerClient::PixmapSizeKnown;
+ expected.line = expected.column = 2; // width and height, in fact
+ VERIFY(MessageListPixmap, 1, expected,
+ CheckMessageType | CheckDetailType | CheckLine | CheckColumn);
// image loaded
- QCOMPARE(m_client->pixmapMessages[2].messageType, (int)QQmlProfilerClient::PixmapCacheEvent);
- QCOMPARE(m_client->pixmapMessages[2].detailType, (int)QQmlProfilerClient::PixmapLoadingFinished);
+ expected.detailType = QQmlProfilerClient::PixmapLoadingFinished;
+ VERIFY(MessageListPixmap, 2, expected, CheckMessageType | CheckDetailType);
// cache size
- QCOMPARE(m_client->pixmapMessages[3].messageType, (int)QQmlProfilerClient::PixmapCacheEvent);
- QCOMPARE(m_client->pixmapMessages[3].detailType, (int)QQmlProfilerClient::PixmapCacheCountChanged);
-
+ expected.detailType = QQmlProfilerClient::PixmapCacheCountChanged;
+ VERIFY(MessageListPixmap, 3, expected, CheckMessageType | CheckDetailType);
}
void tst_QQmlProfilerService::scenegraphData()
@@ -554,19 +652,39 @@ void tst_QQmlProfilerService::scenegraphData()
// there should be a SGPolishAndSync + SGRendererFrame + SGRenderLoopFrame sequence
// (though we can't be sure to get the SGRenderLoopFrame in the threaded renderer)
//
- // since the rendering happens in a different thread, there could be other unrelated events interleaved
- int loopcheck = 0;
+ // since the rendering happens in a different thread, there could be other unrelated events
+ // interleaved. Also, events could carry the same time stamps and be sorted in an unexpected way
+ // if the clocks are acting up.
+ qint64 contextFrameTime = -1;
+ qint64 renderFrameTime = -1;
+
foreach (const QQmlProfilerData &msg, m_client->asynchronousMessages) {
if (msg.messageType == QQmlProfilerClient::SceneGraphFrame) {
- if (loopcheck == 0 && msg.detailType == QQmlProfilerClient::SceneGraphContextFrame)
- loopcheck = 1;
- else if (loopcheck == 1 && msg.detailType == QQmlProfilerClient::SceneGraphRendererFrame)
- loopcheck = 2;
- else if (loopcheck == 2 && msg.detailType == QQmlProfilerClient::SceneGraphRenderLoopFrame)
- loopcheck = 3;
+ if (msg.detailType == QQmlProfilerClient::SceneGraphContextFrame) {
+ contextFrameTime = msg.time;
+ break;
+ }
+ }
+ }
+
+ QVERIFY(contextFrameTime != -1);
+
+ foreach (const QQmlProfilerData &msg, m_client->asynchronousMessages) {
+ if (msg.detailType == QQmlProfilerClient::SceneGraphRendererFrame) {
+ QVERIFY(msg.time >= contextFrameTime);
+ renderFrameTime = msg.time;
+ break;
+ }
+ }
+
+ QVERIFY(renderFrameTime != -1);
+
+ foreach (const QQmlProfilerData &msg, m_client->asynchronousMessages) {
+ if (msg.detailType == QQmlProfilerClient::SceneGraphRenderLoopFrame) {
+ QVERIFY(msg.time >= renderFrameTime);
+ break;
}
}
- QVERIFY(loopcheck >= 2);
}
void tst_QQmlProfilerService::profileOnExit()
@@ -605,22 +723,16 @@ void tst_QQmlProfilerService::signalSourceLocation()
checkTraceReceived();
checkJsHeap();
- QVERIFY2(m_client->qmlMessages.count() >= 16,
- QString::number(m_client->qmlMessages.count()).toUtf8().constData());
-
- QCOMPARE(m_client->qmlMessages[13].messageType, (int)QQmlProfilerClient::RangeLocation);
- QCOMPARE(m_client->qmlMessages[13].detailType, (int)QQmlProfilerClient::HandlingSignal);
- QVERIFY2(m_client->qmlMessages[13].detailData.endsWith("signalSourceLocation.qml"),
- m_client->qmlMessages[13].detailData.toUtf8().constData());
- QCOMPARE(m_client->qmlMessages[13].line, 8);
- QCOMPARE(m_client->qmlMessages[13].column, 28);
-
- QCOMPARE(m_client->qmlMessages[15].messageType, (int)QQmlProfilerClient::RangeLocation);
- QCOMPARE(m_client->qmlMessages[15].detailType, (int)QQmlProfilerClient::HandlingSignal);
- QVERIFY2(m_client->qmlMessages[15].detailData.endsWith("signalSourceLocation.qml"),
- m_client->qmlMessages[15].detailData.toUtf8().constData());
- QCOMPARE(m_client->qmlMessages[15].line, 7);
- QCOMPARE(m_client->qmlMessages[15].column, 21);
+ QQmlProfilerData expected(QQmlProfilerClient::RangeLocation,
+ QQmlProfilerClient::HandlingSignal,
+ QLatin1String("signalSourceLocation.qml"));
+ expected.line = 8;
+ expected.column = 28;
+ VERIFY(MessageListQML, 13, expected, CheckAll);
+
+ expected.line = 7;
+ expected.column = 21;
+ VERIFY(MessageListQML, 15, expected, CheckAll);
}
void tst_QQmlProfilerService::javascript()
@@ -636,26 +748,22 @@ void tst_QQmlProfilerService::javascript()
checkTraceReceived();
checkJsHeap();
- QVERIFY2(m_client->javascriptMessages.count() >= 22,
- QString::number(m_client->javascriptMessages.count()).toUtf8().constData());
-
- QCOMPARE(m_client->javascriptMessages[6].messageType, (int)QQmlProfilerClient::RangeStart);
- QCOMPARE(m_client->javascriptMessages[6].detailType, (int)QQmlProfilerClient::Javascript);
+ QQmlProfilerData expected(QQmlProfilerClient::RangeStart, QQmlProfilerClient::Javascript);
+ VERIFY(MessageListJavaScript, 6, expected, CheckMessageType | CheckDetailType);
- QCOMPARE(m_client->javascriptMessages[7].messageType, (int)QQmlProfilerClient::RangeLocation);
- QCOMPARE(m_client->javascriptMessages[7].detailType, (int)QQmlProfilerClient::Javascript);
- QVERIFY2(m_client->javascriptMessages[7].detailData.endsWith("javascript.qml"),
- m_client->javascriptMessages[7].detailData.toUtf8().constData());
- QCOMPARE(m_client->javascriptMessages[7].line, 4);
- QCOMPARE(m_client->javascriptMessages[7].column, 5);
+ expected.messageType = QQmlProfilerClient::RangeLocation;
+ expected.detailData = QLatin1String("javascript.qml");
+ expected.line = 4;
+ expected.column = 5;
+ VERIFY(MessageListJavaScript, 7, expected, CheckAll);
- QCOMPARE(m_client->javascriptMessages[8].messageType, (int)QQmlProfilerClient::RangeData);
- QCOMPARE(m_client->javascriptMessages[8].detailType, (int)QQmlProfilerClient::Javascript);
- QVERIFY2(m_client->javascriptMessages[8].detailData == "something",
- m_client->javascriptMessages[8].detailData.toUtf8().constData());
+ expected.messageType = QQmlProfilerClient::RangeData;
+ expected.detailData = QLatin1String("something");
+ VERIFY(MessageListJavaScript, 8, expected,
+ CheckMessageType | CheckDetailType | CheckDataEndsWith);
- QCOMPARE(m_client->javascriptMessages[21].messageType, (int)QQmlProfilerClient::RangeEnd);
- QCOMPARE(m_client->javascriptMessages[21].detailType, (int)QQmlProfilerClient::Javascript);
+ expected.messageType = QQmlProfilerClient::RangeEnd;
+ VERIFY(MessageListJavaScript, 21, expected, CheckMessageType | CheckDetailType);
}
QTEST_MAIN(tst_QQmlProfilerService)
diff --git a/tests/auto/qml/debugger/qv4profilerservice/data/console.qml b/tests/auto/qml/debugger/qv4profilerservice/data/console.qml
deleted file mode 100644
index c23c820216..0000000000
--- a/tests/auto/qml/debugger/qv4profilerservice/data/console.qml
+++ /dev/null
@@ -1,14 +0,0 @@
-import QtQuick 2.0
-
-
-Item {
- function f()
- {
- }
-
- Component.onCompleted: {
- console.profile();
- f();
- console.profileEnd();
- }
-}
diff --git a/tests/auto/qml/debugger/qv4profilerservice/data/exit.qml b/tests/auto/qml/debugger/qv4profilerservice/data/exit.qml
deleted file mode 100644
index 604265354c..0000000000
--- a/tests/auto/qml/debugger/qv4profilerservice/data/exit.qml
+++ /dev/null
@@ -1,11 +0,0 @@
-import QtQuick 2.0
-
-Item {
- Timer {
- running: true
- interval: 1
- onTriggered: {
- Qt.quit();
- }
- }
-}
diff --git a/tests/auto/qml/debugger/qv4profilerservice/data/test.qml b/tests/auto/qml/debugger/qv4profilerservice/data/test.qml
deleted file mode 100644
index 9c36e13c5b..0000000000
--- a/tests/auto/qml/debugger/qv4profilerservice/data/test.qml
+++ /dev/null
@@ -1,5 +0,0 @@
-import QtQuick 2.0
-
-Item {
-
-}
diff --git a/tests/auto/qml/debugger/qv4profilerservice/qv4profilerservice.pro b/tests/auto/qml/debugger/qv4profilerservice/qv4profilerservice.pro
deleted file mode 100644
index 459f931f94..0000000000
--- a/tests/auto/qml/debugger/qv4profilerservice/qv4profilerservice.pro
+++ /dev/null
@@ -1,16 +0,0 @@
-CONFIG += testcase
-TARGET = tst_qv4profilerservice
-macx:CONFIG -= app_bundle
-
-SOURCES += tst_qv4profilerservice.cpp
-
-INCLUDEPATH += ../shared
-include(../../../shared/util.pri)
-include(../shared/debugutil.pri)
-
-TESTDATA = data/*
-
-QT += qml testlib gui-private
-
-DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-CONFIG+=insignificant_test
diff --git a/tests/auto/qml/debugger/qv4profilerservice/tst_qv4profilerservice.cpp b/tests/auto/qml/debugger/qv4profilerservice/tst_qv4profilerservice.cpp
deleted file mode 100644
index 47c2ffe74f..0000000000
--- a/tests/auto/qml/debugger/qv4profilerservice/tst_qv4profilerservice.cpp
+++ /dev/null
@@ -1,326 +0,0 @@
-/****************************************************************************
-**
-** Copyright (C) 2015 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
-**
-** This file is part of the test suite of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:LGPL21$
-** Commercial License Usage
-** Licensees holding valid commercial Qt licenses may use this file in
-** accordance with the commercial license agreement provided with the
-** Software or, alternatively, in accordance with the terms contained in
-** a written agreement between you and The Qt Company. For licensing terms
-** and conditions see http://www.qt.io/terms-conditions. For further
-** information use the contact form at http://www.qt.io/contact-us.
-**
-** GNU Lesser General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU Lesser
-** General Public License version 2.1 or version 3 as published by the Free
-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
-** following information to ensure the GNU Lesser General Public License
-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
-**
-** As a special exception, The Qt Company gives you certain additional
-** rights. These rights are described in The Qt Company LGPL Exception
-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
-
-#include <qtest.h>
-#include <QLibraryInfo>
-
-#include "debugutil_p.h"
-#include "qqmldebugclient.h"
-#include "../../../shared/util.h"
-
-#define STR_PORT_FROM "13774"
-#define STR_PORT_TO "13790"
-
-struct QV4ProfilerData
-{
- int messageType;
- QString filename;
- QString functionname;
- int lineNumber;
- double totalTime;
- double selfTime;
- int treeLevel;
-
- QByteArray toByteArray() const;
-};
-
-class QV4ProfilerClient : public QQmlDebugClient
-{
- Q_OBJECT
-
-public:
- enum MessageType {
- V4Entry,
- V4Complete,
- V4SnapshotChunk,
- V4SnapshotComplete,
- V4Started,
-
- V4MaximumMessage
- };
-
- enum ServiceState { NotRunning, Running } serviceState;
-
- QV4ProfilerClient(QQmlDebugConnection *connection)
- : QQmlDebugClient(QLatin1String("V8Profiler"), connection)
- , serviceState(NotRunning)
- {
- }
-
- void startProfiling(const QString &name) {
- QByteArray message;
- QDataStream stream(&message, QIODevice::WriteOnly);
- stream << QByteArray("V8PROFILER") << QByteArray("start") << name;
- sendMessage(message);
- }
-
- void stopProfiling(const QString &name) {
- QByteArray message;
- QDataStream stream(&message, QIODevice::WriteOnly);
- stream << QByteArray("V8PROFILER") << QByteArray("stop") << name;
- sendMessage(message);
- }
-
- void takeSnapshot() {
- QByteArray message;
- QDataStream stream(&message, QIODevice::WriteOnly);
- stream << QByteArray("V8SNAPSHOT") << QByteArray("full");
- sendMessage(message);
- }
-
- void deleteSnapshots() {
- QByteArray message;
- QDataStream stream(&message, QIODevice::WriteOnly);
- stream << QByteArray("V8SNAPSHOT") << QByteArray("delete");
- sendMessage(message);
- }
-
- QList<QV4ProfilerData> traceMessages;
- QList<QByteArray> snapshotMessages;
-
-signals:
- void started();
- void complete();
- void snapshot();
-
-protected:
- void messageReceived(const QByteArray &message);
-};
-
-class tst_QV4ProfilerService : public QQmlDataTest
-{
- Q_OBJECT
-
-public:
- tst_QV4ProfilerService()
- : m_process(0)
- , m_connection(0)
- , m_client(0)
- {
- }
-
-private:
- QQmlDebugProcess *m_process;
- QQmlDebugConnection *m_connection;
- QV4ProfilerClient *m_client;
-
- bool connect(bool block, const QString &testFile, QString *error);
-
-private slots:
- void cleanup();
-
- void blockingConnectWithTraceEnabled();
- void blockingConnectWithTraceDisabled();
- void nonBlockingConnect();
- void snapshot();
- void profileOnExit();
- void console();
-};
-
-void QV4ProfilerClient::messageReceived(const QByteArray &message)
-{
- QByteArray msg = message;
- QDataStream stream(&msg, QIODevice::ReadOnly);
-
- int messageType;
- stream >> messageType;
-
- QVERIFY(messageType >= 0);
- QVERIFY(messageType < QV4ProfilerClient::V4MaximumMessage);
-
- switch (messageType) {
- case QV4ProfilerClient::V4Entry: {
- QCOMPARE(serviceState, Running);
- QV4ProfilerData entry;
- stream >> entry.filename >> entry.functionname >> entry.lineNumber >> entry.totalTime >> entry.selfTime >> entry.treeLevel;
- traceMessages.append(entry);
- break;
- }
- case QV4ProfilerClient::V4Complete:
- QCOMPARE(serviceState, Running);
- serviceState = NotRunning;
- emit complete();
- break;
- case QV4ProfilerClient::V4SnapshotChunk: {
- QByteArray json;
- stream >> json;
- snapshotMessages.append(json);
- break;
- }
- case QV4ProfilerClient::V4SnapshotComplete:
- emit snapshot();
- break;
- case QV4ProfilerClient::V4Started:
- QCOMPARE(serviceState, NotRunning);
- serviceState = Running;
- emit started();
- break;
- default:
- QString failMessage = QString("Unknown message type: %1").arg(messageType);
- QFAIL(qPrintable(failMessage));
- }
-
- QVERIFY(stream.atEnd());
-}
-
-bool tst_QV4ProfilerService::connect(bool block, const QString &testFile,
- QString *error)
-{
- const QString executable = QLibraryInfo::location(QLibraryInfo::BinariesPath) + "/qml";
- QStringList arguments;
-
- if (block)
- arguments << QString("-qmljsdebugger=port:" STR_PORT_FROM "," STR_PORT_TO ",block");
- else
- arguments << QString("-qmljsdebugger=port:" STR_PORT_FROM "," STR_PORT_TO);
-
- arguments << QQmlDataTest::instance()->testFile(testFile);
-
- m_connection = new QQmlDebugConnection();
- m_client = new QV4ProfilerClient(m_connection);
-
- m_process = new QQmlDebugProcess(executable);
- m_process->start(QStringList() << arguments);
- if (!m_process->waitForSessionStart()) {
- *error = QLatin1String("Could not launch application, or did not get 'Waiting for connection'.");
- return false;
- }
-
- m_connection->connectToHost(QLatin1String("127.0.0.1"), m_process->debugPort());
- if (!m_connection->waitForConnected()) {
- *error = QLatin1String("Could not connect to debugger port.");
- return false;
- }
- return true;
-}
-
-void tst_QV4ProfilerService::cleanup()
-{
- if (QTest::currentTestFailed()) {
- qDebug() << "Process State:" << m_process->state();
- qDebug() << "Application Output:" << m_process->output();
- }
- delete m_client;
- delete m_process;
- delete m_connection;
-}
-
-void tst_QV4ProfilerService::blockingConnectWithTraceEnabled()
-{
- QString error;
- if (!connect(true, "test.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->startProfiling("");
- m_client->stopProfiling("");
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())),
- "No trace received in time.");
-}
-
-void tst_QV4ProfilerService::blockingConnectWithTraceDisabled()
-{
- QString error;
- if (!connect(true, "test.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->stopProfiling("");
- QVERIFY2(!QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete()), 1000),
- "Unexpected trace received.");
- m_client->startProfiling("");
- m_client->stopProfiling("");
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())),
- "No trace received in time.");
-}
-
-void tst_QV4ProfilerService::nonBlockingConnect()
-{
- QString error;
- if (!connect(false, "test.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->startProfiling("");
- m_client->stopProfiling("");
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())),
- "No trace received in time.");
-}
-
-void tst_QV4ProfilerService::snapshot()
-{
- QString error;
- if (!connect(false, "test.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->takeSnapshot();
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(snapshot())),
- "No trace received in time.");
-}
-
-void tst_QV4ProfilerService::profileOnExit()
-{
- QString error;
- if (!connect(true, "exit.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->startProfiling("");
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())),
- "No trace received in time.");
-}
-
-void tst_QV4ProfilerService::console()
-{
- QString error;
- if (!connect(true, "console.qml", &error))
- QFAIL(qPrintable(error));
-
- QTRY_COMPARE(m_client->state(), QQmlDebugClient::Enabled);
-
- m_client->stopProfiling("");
-
- QVERIFY2(QQmlDebugTest::waitForSignal(m_client, SIGNAL(complete())),
- "No trace received in time.");
- QVERIFY(!m_client->traceMessages.isEmpty());
-}
-
-QTEST_MAIN(tst_QV4ProfilerService)
-
-#include "tst_qv4profilerservice.moc"
diff --git a/tests/auto/quick/qquickanimations/BLACKLIST b/tests/auto/quick/qquickanimations/BLACKLIST
new file mode 100644
index 0000000000..e45c141d17
--- /dev/null
+++ b/tests/auto/quick/qquickanimations/BLACKLIST
@@ -0,0 +1,40 @@
+# QTBUG-45466 QTBUG-29062
+[simpleProperty]
+osx-10.9 developer-build
+[badTypes]
+windows msvc-2010 32bit developer-build
+[mixedTypes]
+windows msvc-2010 32bit developer-build
+[properties]
+windows msvc-2010 32bit developer-build
+[propertiesTransition]
+windows msvc-2010 32bit developer-build
+[pathTransition]
+windows msvc-2010 32bit developer-build
+[disabledTransition]
+windows msvc-2010 32bit developer-build
+[rotation]
+windows msvc-2010 32bit developer-build
+[startStopSignals]
+windows msvc-2010 32bit developer-build
+[runningTrueBug]
+windows msvc-2010 32bit developer-build
+[nonTransitionBug]
+windows msvc-2010 32bit developer-build
+[registrationBug]
+windows msvc-2010 32bit developer-build
+[alwaysRunToEndRestartBug]
+windows msvc-2010 32bit developer-build
+[loopingBug]
+windows msvc-2010 32bit developer-build
+[pathAnimationInOutBackBug]
+windows msvc-2010 32bit developer-build
+[reparent]
+windows msvc-2012 64bit developer-build
+windows msvc-2010 32bit developer-build
+[simpleAnchor]
+windows msvc-2010 32bit developer-build
+[simplePath]
+windows gcc developer-build
+windows msvc-2010 32bit developer-build
+
diff --git a/tests/auto/quick/qquickanimations/qquickanimations.pro b/tests/auto/quick/qquickanimations/qquickanimations.pro
index f3e1cd082f..dc8f471259 100644
--- a/tests/auto/quick/qquickanimations/qquickanimations.pro
+++ b/tests/auto/quick/qquickanimations/qquickanimations.pro
@@ -1,5 +1,4 @@
CONFIG += testcase
-win32-g++|mac:CONFIG+=insignificant_test # QTBUG-29062
TARGET = tst_qquickanimations
SOURCES += tst_qquickanimations.cpp
diff --git a/tests/auto/quick/qquickflickable/BLACKLIST b/tests/auto/quick/qquickflickable/BLACKLIST
new file mode 100644
index 0000000000..92ed8708de
--- /dev/null
+++ b/tests/auto/quick/qquickflickable/BLACKLIST
@@ -0,0 +1,19 @@
+# QTBUG-36804
+osx-10.10
+[rebound]
+osx-10.10
+[movingAndFlicking:vertical]
+osx-10.10
+[movingAndFlicking:both]
+osx-10.10
+[movingAndFlicking:horizontal]
+osx-10.10
+[stopAtBounds]
+osx-10.10
+windows 32bit developer-build
+[returnToBounds]
+osx
+[pressWhileFlicking]
+osx-10.10
+[flickVelocity]
+osx-10.10
diff --git a/tests/auto/quick/qquickflickable/qquickflickable.pro b/tests/auto/quick/qquickflickable/qquickflickable.pro
index 81b2b1a00c..88dc2fbc2a 100644
--- a/tests/auto/quick/qquickflickable/qquickflickable.pro
+++ b/tests/auto/quick/qquickflickable/qquickflickable.pro
@@ -11,4 +11,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private testlib
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-macx:CONFIG+=insignificant_test
diff --git a/tests/auto/quick/qquickgridview/qquickgridview.pro b/tests/auto/quick/qquickgridview/qquickgridview.pro
index 40b43fa2c0..3b98ed4dea 100644
--- a/tests/auto/quick/qquickgridview/qquickgridview.pro
+++ b/tests/auto/quick/qquickgridview/qquickgridview.pro
@@ -12,7 +12,4 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private testlib
-win32:CONFIG += insignificant_test # QTBUG-33017
-macx:CONFIG += insignificant_test # QTBUG-33017
-
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
diff --git a/tests/auto/quick/qquickitem/data/contains.qml b/tests/auto/quick/qquickitem/data/contains.qml
new file mode 100644
index 0000000000..72fd8bdc91
--- /dev/null
+++ b/tests/auto/quick/qquickitem/data/contains.qml
@@ -0,0 +1,26 @@
+import QtQuick 2.3
+
+Item {
+ id: root
+ width: 300
+ height: 300
+
+ function childContainsViaMapToItem(x, y) {
+ var childLocalPos = root.mapToItem(child, x, y);
+ return child.contains(childLocalPos);
+ }
+
+ function childContainsViaMapFromItem(x, y) {
+ var childLocalPos = child.mapFromItem(root, x, y);
+ return child.contains(childLocalPos);
+ }
+
+ Item {
+ id: child
+ x: 50
+ y: 50
+ width: 50
+ height: 50
+ }
+}
+
diff --git a/tests/auto/quick/qquickitem/tst_qquickitem.cpp b/tests/auto/quick/qquickitem/tst_qquickitem.cpp
index 832cbab971..c79af91747 100644
--- a/tests/auto/quick/qquickitem/tst_qquickitem.cpp
+++ b/tests/auto/quick/qquickitem/tst_qquickitem.cpp
@@ -169,6 +169,9 @@ private slots:
void objectChildTransform();
+ void contains_data();
+ void contains();
+
private:
enum PaintOrderOp {
@@ -1927,6 +1930,48 @@ void tst_qquickitem::objectChildTransform()
// Shouldn't crash.
}
+void tst_qquickitem::contains_data()
+{
+ QTest::addColumn<int>("x");
+ QTest::addColumn<int>("y");
+ QTest::addColumn<bool>("contains");
+
+ QTest::newRow("(0, 0) = false") << 0 << 0 << false;
+ QTest::newRow("(50, 0) = false") << 50 << 0 << false;
+ QTest::newRow("(0, 50) = false") << 0 << 50 << false;
+ QTest::newRow("(50, 50) = true") << 50 << 50 << true;
+ QTest::newRow("(100, 100) = true") << 100 << 100 << true;
+ QTest::newRow("(150, 150) = false") << 150 << 150 << false;
+}
+
+void tst_qquickitem::contains()
+{
+ // Tests that contains works, but also checks that mapToItem/mapFromItem
+ // return the correct type (point or rect, not a JS object with those properties),
+ // as this is a common combination of calls.
+
+ QFETCH(int, x);
+ QFETCH(int, y);
+ QFETCH(bool, contains);
+
+ QQuickView view;
+ view.setSource(testFileUrl("contains.qml"));
+
+ QQuickItem *root = qobject_cast<QQuickItem*>(view.rootObject());
+ QVERIFY(root);
+
+ QVariant result = false;
+ QVERIFY(QMetaObject::invokeMethod(root, "childContainsViaMapToItem",
+ Q_RETURN_ARG(QVariant, result), Q_ARG(QVariant, qreal(x)), Q_ARG(QVariant, qreal(y))));
+ QCOMPARE(result.toBool(), contains);
+
+ result = false;
+ QVERIFY(QMetaObject::invokeMethod(root, "childContainsViaMapFromItem",
+ Q_RETURN_ARG(QVariant, result), Q_ARG(QVariant, qreal(x)), Q_ARG(QVariant, qreal(y))));
+ QCOMPARE(result.toBool(), contains);
+}
+
+
QTEST_MAIN(tst_qquickitem)
#include "tst_qquickitem.moc"
diff --git a/tests/auto/quick/qquickloader/qquickloader.pro b/tests/auto/quick/qquickloader/qquickloader.pro
index 88de3c4c60..567917877c 100644
--- a/tests/auto/quick/qquickloader/qquickloader.pro
+++ b/tests/auto/quick/qquickloader/qquickloader.pro
@@ -14,4 +14,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private network testlib
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-CONFIG+=insignificant_test # QTBUG-30721
diff --git a/tests/auto/quick/qquickpathview/qquickpathview.pro b/tests/auto/quick/qquickpathview/qquickpathview.pro
index 8d729fd7c4..e6cf9a488f 100644
--- a/tests/auto/quick/qquickpathview/qquickpathview.pro
+++ b/tests/auto/quick/qquickpathview/qquickpathview.pro
@@ -12,5 +12,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private testlib
qtHaveModule(widgets): QT += widgets
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-
-macx:CONFIG += insignificant_test # QTBUG-27740
diff --git a/tests/auto/quick/qquickstates/data/revertListMemoryLeak.qml b/tests/auto/quick/qquickstates/data/revertListMemoryLeak.qml
new file mode 100644
index 0000000000..b49487c895
--- /dev/null
+++ b/tests/auto/quick/qquickstates/data/revertListMemoryLeak.qml
@@ -0,0 +1,16 @@
+import QtQuick 2.0
+
+Item {
+ id: rect
+ width: 40;
+ property real boundHeight: 42
+ height: boundHeight;
+
+ states: [
+ State {
+ objectName: "testState"
+ name: "testState"
+ PropertyChanges { target: rect; height: 60; }
+ }
+ ]
+}
diff --git a/tests/auto/quick/qquickstates/tst_qquickstates.cpp b/tests/auto/quick/qquickstates/tst_qquickstates.cpp
index 51fe9b4c96..6c42a7a0ee 100644
--- a/tests/auto/quick/qquickstates/tst_qquickstates.cpp
+++ b/tests/auto/quick/qquickstates/tst_qquickstates.cpp
@@ -141,6 +141,7 @@ private slots:
void avoidFastForward();
void revertListBug();
void QTBUG_38492();
+ void revertListMemoryLeak();
};
void tst_qquickstates::initTestCase()
@@ -1634,6 +1635,30 @@ void tst_qquickstates::QTBUG_38492()
delete item;
}
+void tst_qquickstates::revertListMemoryLeak()
+{
+ QWeakPointer<QQmlAbstractBinding> weakPtr;
+ {
+ QQmlEngine engine;
+
+ QQmlComponent c(&engine, testFileUrl("revertListMemoryLeak.qml"));
+ QQuickItem *item = qobject_cast<QQuickItem *>(c.create());
+ QVERIFY(item);
+ QQuickState *state = item->findChild<QQuickState*>("testState");
+ QVERIFY(state);
+
+ item->setState("testState");
+
+ QQmlAbstractBinding *binding = state->bindingInRevertList(item, "height");
+ QVERIFY(binding);
+ weakPtr = QQmlAbstractBinding::getPointer(binding);
+ QVERIFY(!weakPtr.toStrongRef().isNull());
+
+ delete item;
+ }
+ QVERIFY(weakPtr.toStrongRef().isNull());
+}
+
QTEST_MAIN(tst_qquickstates)
#include "tst_qquickstates.moc"
diff --git a/tests/auto/quick/qquicktext/qquicktext.pro b/tests/auto/quick/qquicktext/qquicktext.pro
index c25a27b745..ee0a9be776 100644
--- a/tests/auto/quick/qquicktext/qquicktext.pro
+++ b/tests/auto/quick/qquicktext/qquicktext.pro
@@ -14,5 +14,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private network testlib
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-
-mac:CONFIG += insignificant_test # QTBUG-27740
diff --git a/tests/auto/quick/qquicktextedit/qquicktextedit.pro b/tests/auto/quick/qquicktextedit/qquicktextedit.pro
index 2386d713a7..2a6d753536 100644
--- a/tests/auto/quick/qquicktextedit/qquicktextedit.pro
+++ b/tests/auto/quick/qquicktextedit/qquicktextedit.pro
@@ -14,6 +14,3 @@ TESTDATA = data/*
QT += core-private gui-private qml-private quick-private network-private testlib
DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0
-
-mac:CONFIG += insignificant_test # QTBUG-27740
-win32:CONFIG += insignificant_test # QTBUG-32540
diff --git a/tests/auto/quick/qquickwindow/BLACKLIST b/tests/auto/quick/qquickwindow/BLACKLIST
index 331f736013..8a19a679a3 100644
--- a/tests/auto/quick/qquickwindow/BLACKLIST
+++ b/tests/auto/quick/qquickwindow/BLACKLIST
@@ -1,2 +1,4 @@
[cursor]
*
+[testWindowVisibilityOrder]
+osx
diff --git a/tests/auto/quickwidgets/qquickwidget/tst_qquickwidget.cpp b/tests/auto/quickwidgets/qquickwidget/tst_qquickwidget.cpp
index 1d9e40011d..3da920ca27 100644
--- a/tests/auto/quickwidgets/qquickwidget/tst_qquickwidget.cpp
+++ b/tests/auto/quickwidgets/qquickwidget/tst_qquickwidget.cpp
@@ -58,6 +58,7 @@ private slots:
void errors();
void engine();
void readback();
+ void renderingSignals();
};
@@ -259,6 +260,38 @@ void tst_qquickwidget::readback()
QCOMPARE(pix, qRgb(255, 0, 0));
}
+void tst_qquickwidget::renderingSignals()
+{
+ QQuickWidget widget;
+ QQuickWindow *window = widget.quickWindow();
+ QVERIFY(window);
+
+ QSignalSpy beforeRenderingSpy(window, &QQuickWindow::beforeRendering);
+ QSignalSpy beforeSyncSpy(window, &QQuickWindow::beforeSynchronizing);
+ QSignalSpy afterRenderingSpy(window, &QQuickWindow::afterRendering);
+
+ QVERIFY(beforeRenderingSpy.isValid());
+ QVERIFY(beforeSyncSpy.isValid());
+ QVERIFY(afterRenderingSpy.isValid());
+
+ QCOMPARE(beforeRenderingSpy.size(), 0);
+ QCOMPARE(beforeSyncSpy.size(), 0);
+ QCOMPARE(afterRenderingSpy.size(), 0);
+
+ widget.setSource(testFileUrl("rectangle.qml"));
+
+ QCOMPARE(beforeRenderingSpy.size(), 0);
+ QCOMPARE(beforeSyncSpy.size(), 0);
+ QCOMPARE(afterRenderingSpy.size(), 0);
+
+ widget.show();
+ QVERIFY(QTest::qWaitForWindowExposed(&widget, 5000));
+
+ QTRY_VERIFY(beforeRenderingSpy.size() > 0);
+ QTRY_VERIFY(beforeSyncSpy.size() > 0);
+ QTRY_VERIFY(afterRenderingSpy.size() > 0);
+}
+
QTEST_MAIN(tst_qquickwidget)
#include "tst_qquickwidget.moc"
diff --git a/tests/manual/scenegraph_lancelot/data/text/textedit_table.qml b/tests/manual/scenegraph_lancelot/data/text/textedit_table.qml
new file mode 100644
index 0000000000..b16472eca6
--- /dev/null
+++ b/tests/manual/scenegraph_lancelot/data/text/textedit_table.qml
@@ -0,0 +1,21 @@
+import QtQuick 2.0
+
+Item {
+ width: 320
+ height: 480
+
+ TextEdit {
+ anchors.fill: parent
+ verticalAlignment: Text.AlignBottom
+ font.family: "Arial"
+ font.pixelSize: 16
+ textFormat: Text.RichText
+ text: "A table: <table border=2>"
+ + "<tr><th>Header 1</th><th>Header 2</th></tr>"
+ + "<tr><td>Cell 1</td><td>Cell 2</td></tr>"
+ + "<tr><td>Cell 3</td><td>Cell 4</td></tr>"
+ + "<tr><td colspan=2>Cell 5</td></tr>"
+ + "<tr><td rowspan=2>Cell 6</td><td>Cell 7</tr>"
+ + "<tr><td>Cell 8</td></tr>"
+ }
+}