summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--doc/src/declarative/focus.qdoc13
-rw-r--r--doc/src/declarative/globalobject.qdoc2
-rw-r--r--doc/src/declarative/qtprogrammers.qdoc2
-rw-r--r--examples/declarative/webview/content/Mapping/Map.qml20
-rwxr-xr-xexamples/declarative/webview/content/Mapping/map.html47
-rw-r--r--examples/declarative/webview/googleMaps.qml31
-rw-r--r--src/declarative/graphicsitems/qmlgraphicsborderimage.cpp2
-rw-r--r--src/declarative/graphicsitems/qmlgraphicsimage.cpp2
-rw-r--r--src/declarative/graphicsitems/qmlgraphicsitem.cpp7
-rw-r--r--src/declarative/graphicsitems/qmlgraphicsitem.h3
-rw-r--r--src/declarative/graphicsitems/qmlgraphicswebview.cpp9
-rw-r--r--src/declarative/qml/qmlengine.cpp15
-rw-r--r--src/declarative/qml/qmlsqldatabase.cpp7
-rw-r--r--src/declarative/util/qmlanimation.cpp50
-rw-r--r--src/declarative/util/qmlanimation_p.h2
-rw-r--r--src/declarative/util/qmlanimation_p_p.h2
-rw-r--r--src/declarative/util/qmllistmodel.cpp22
-rw-r--r--tests/auto/declarative/animations/tst_animations.cpp105
-rw-r--r--tests/auto/declarative/qmlengine/tst_qmlengine.cpp8
-rw-r--r--tests/auto/declarative/qmlgraphicsgridview/tst_qmlgraphicsgridview.cpp36
-rw-r--r--tests/auto/declarative/qmlgraphicslistview/data/listview.qml1
-rw-r--r--tests/auto/declarative/qmlgraphicslistview/tst_qmlgraphicslistview.cpp34
-rw-r--r--tests/auto/declarative/qmllistmodel/tst_qmllistmodel.cpp18
-rw-r--r--tests/auto/declarative/sql/data/2-selection-bindnames.js24
-rw-r--r--tests/auto/declarative/sql/data/6-iteration-efficient.js6
-rw-r--r--tests/auto/declarative/sql/tst_sql.cpp7
26 files changed, 402 insertions, 73 deletions
diff --git a/doc/src/declarative/focus.qdoc b/doc/src/declarative/focus.qdoc
index 6eca667..8061a7c 100644
--- a/doc/src/declarative/focus.qdoc
+++ b/doc/src/declarative/focus.qdoc
@@ -75,12 +75,12 @@ Item {
\endlist
-See also the \l {Keys}{Keys attached property} and {KeyNavigation}{KeyNavigation attached property}.
+See also the \l {Keys}{Keys attached property} and \l {KeyNavigation}{KeyNavigation attached property}.
\section1 Querying the Active Focus Item
Whether or not an \l Item has \e {active focus} can be queried through the
-read-only property \c {Item::focus}. For example, here we have a \l Text
+property \c {Item::focus}. For example, here we have a \l Text
element whose text is determined by whether or not it has \e {active focus}.
\code
@@ -191,10 +191,11 @@ This problem is fundamentally one of visibility. The \c {MyWidget}
components each set their \c {keyHandler} Items as focused as that is all they can
do - they don't know how they are going to be used, but they do know that when
they're in use their \c {keyHandler} element is what needs focus. Likewise
-the code that uses the \c {MyWidget}'s sets the second \c {MyWidget} as
-focused because, while it doesn't know exactly how the \c {MyWidget} is
-implemented, it knows that it wants the second one to be focused. No one piece
-of code knows everything about the other, which is exactly how it should be.
+the code that uses the two \c {MyWidgets} sets the second \c {MyWidget} as
+focused. While it doesn't know exactly how the \c {MyWidget} is
+implemented, it knows that it wants the second one to be focused. This allows us
+to achieve encapsulation, allowing each widget to focus on it's appropriate behaviour
+itself.
To solve this problem - allowing components to care about what they know about
and ignore everything else - the QML items introduce a concept known as a
diff --git a/doc/src/declarative/globalobject.qdoc b/doc/src/declarative/globalobject.qdoc
index 3cf1ca3..dc08c28 100644
--- a/doc/src/declarative/globalobject.qdoc
+++ b/doc/src/declarative/globalobject.qdoc
@@ -126,8 +126,6 @@ This function attempts to open the specified \c target url in an external applic
\section3 Qt.md5(data)
This function returns a hex string of the md5 hash of \c data.
-\endlist
-
\section1 Dynamic Object Creation
The following functions on the global object allow you to dynamically create QML
items from files or strings.
diff --git a/doc/src/declarative/qtprogrammers.qdoc b/doc/src/declarative/qtprogrammers.qdoc
index 6892005..7b1ab44 100644
--- a/doc/src/declarative/qtprogrammers.qdoc
+++ b/doc/src/declarative/qtprogrammers.qdoc
@@ -130,8 +130,6 @@ As an example, imagine you decided to make a generic tab widget item to be used
through your application suite wherever information is in such quantity that it
needs to be divided up into pages.
-To do this in QML, ... \todo example of container definition.
-
A significant difference in the parenting concept with QML compare to QWidgets
is that while child items are positioned relative to their parents,
there is no requirement that they be wholy contained ("clipped") to
diff --git a/examples/declarative/webview/content/Mapping/Map.qml b/examples/declarative/webview/content/Mapping/Map.qml
new file mode 100644
index 0000000..9bde031
--- /dev/null
+++ b/examples/declarative/webview/content/Mapping/Map.qml
@@ -0,0 +1,20 @@
+import Qt 4.6
+
+Item {
+ id: page
+ property real latitude: -34.397
+ property real longitude: 150.644
+ property string address: ""
+ WebView {
+ id: map
+ anchors.fill: parent
+ url: "map.html"
+ javaScriptWindowObjects: Object {
+ WebView.windowObjectName: "qml"
+ property real lat: page.latitude
+ property real lng: page.longitude
+ property string address: page.address
+ onAddressChanged: {map.evaluateJavaScript("goToAddress()")}
+ }
+ }
+}
diff --git a/examples/declarative/webview/content/Mapping/map.html b/examples/declarative/webview/content/Mapping/map.html
new file mode 100755
index 0000000..8afa21c
--- /dev/null
+++ b/examples/declarative/webview/content/Mapping/map.html
@@ -0,0 +1,47 @@
+<html>
+<head>
+<meta name="viewport" content="initial-scale=1.0, user-scalable=no" />
+<script type="text/javascript" src="http://maps.google.com/maps/api/js?sensor=false"></script>
+<script type="text/javascript">
+ var geocoder
+ var map
+ function goToLatLng(latlng,bounds) {
+ if (map) {
+ map.setCenter(latlng)
+ map.fitBounds(bounds)
+ } else {
+ var myOptions = {
+ zoom: 8,
+ center: latlng,
+ mapTypeId: google.maps.MapTypeId.ROADMAP
+ };
+ map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
+ }
+ }
+ function initialize() {
+ geocoder = new google.maps.Geocoder();
+ if (window.qml.address) {
+ goToAddress()
+ } else {
+ goToLatLng(new google.maps.LatLng(window.qml.lat,window.qml.lng));
+ }
+ }
+ function goToAddress() {
+ if (geocoder) {
+ var req = {
+ address: window.qml.address,
+ }
+ if (map)
+ req.bounds = map.getBounds()
+ geocoder.geocode(req, function(results, status) {
+ if (status == google.maps.GeocoderStatus.OK)
+ goToLatLng(results[0].geometry.location,results[0].geometry.bounds);
+ });
+ }
+ }
+</script>
+</head>
+<body onload="initialize()" leftmargin="0px" topmargin="0px" marginwidth="0px" marginheight="0px">
+ <div id="map_canvas" style="width:100%; height:100%"></div>
+</body>
+</html>
diff --git a/examples/declarative/webview/googleMaps.qml b/examples/declarative/webview/googleMaps.qml
new file mode 100644
index 0000000..b5b13bb
--- /dev/null
+++ b/examples/declarative/webview/googleMaps.qml
@@ -0,0 +1,31 @@
+// This example demonstrates how Web services such as Google Maps can be
+// abstracted as QML types. Here we have a "Mapping" module with a "Map"
+// type. The Map type has an address property. Setting that property moves
+// the map. The underlying implementation uses WebView and the Google Maps
+// API, but users from QML don't need to understand the implementation in
+// order to create a Map.
+
+import Qt 4.6
+import "content/Mapping"
+
+Map {
+ id: map
+ width: 300
+ height: 300
+ address: "Paris"
+ Rectangle {
+ color: "white"
+ width: input.width + 20
+ height: input.height + 4
+ radius: 5
+ anchors.bottom: parent.bottom
+ anchors.bottomMargin: 5
+ x: 70
+ TextInput {
+ id: input
+ text: map.address
+ anchors.centerIn: parent
+ Keys.onReturnPressed: map.address = input.text
+ }
+ }
+}
diff --git a/src/declarative/graphicsitems/qmlgraphicsborderimage.cpp b/src/declarative/graphicsitems/qmlgraphicsborderimage.cpp
index 04e79f9..e1039f4 100644
--- a/src/declarative/graphicsitems/qmlgraphicsborderimage.cpp
+++ b/src/declarative/graphicsitems/qmlgraphicsborderimage.cpp
@@ -58,8 +58,6 @@ QML_DEFINE_TYPE(Qt,4,6,BorderImage,QmlGraphicsBorderImage)
\snippet snippets/declarative/border-image.qml 0
\image BorderImage.png
-
- \sa examples/declarative/border-image
*/
/*!
diff --git a/src/declarative/graphicsitems/qmlgraphicsimage.cpp b/src/declarative/graphicsitems/qmlgraphicsimage.cpp
index 89b50a1..42fd910 100644
--- a/src/declarative/graphicsitems/qmlgraphicsimage.cpp
+++ b/src/declarative/graphicsitems/qmlgraphicsimage.cpp
@@ -182,8 +182,6 @@ void QmlGraphicsImagePrivate::setPixmap(const QPixmap &pixmap)
\endlist
\image declarative-image_fillMode.gif
- \sa examples/declarative/fillmode
- \sa examples/declarative/aspectratio
*/
QmlGraphicsImage::FillMode QmlGraphicsImage::fillMode() const
{
diff --git a/src/declarative/graphicsitems/qmlgraphicsitem.cpp b/src/declarative/graphicsitems/qmlgraphicsitem.cpp
index ca45f62..fb6afb1 100644
--- a/src/declarative/graphicsitems/qmlgraphicsitem.cpp
+++ b/src/declarative/graphicsitems/qmlgraphicsitem.cpp
@@ -1428,6 +1428,11 @@ QmlGraphicsKeysAttached *QmlGraphicsKeysAttached::qmlAttachedProperties(QObject
*/
/*!
+ \fn void QmlGraphicsItem::childrenChanged()
+ \internal
+*/
+
+/*!
\fn void QmlGraphicsItem::focusChanged()
\internal
*/
@@ -2692,6 +2697,8 @@ QVariant QmlGraphicsItem::itemChange(GraphicsItemChange change,
{
if (change == ItemParentHasChanged) {
emit parentChanged();
+ } else if (change == ItemChildAddedChange || change == ItemChildRemovedChange) {
+ emit childrenChanged();
}
return QGraphicsItem::itemChange(change, value);
diff --git a/src/declarative/graphicsitems/qmlgraphicsitem.h b/src/declarative/graphicsitems/qmlgraphicsitem.h
index 2ac43b5..11d6e2e 100644
--- a/src/declarative/graphicsitems/qmlgraphicsitem.h
+++ b/src/declarative/graphicsitems/qmlgraphicsitem.h
@@ -69,7 +69,7 @@ class Q_DECLARATIVE_EXPORT QmlGraphicsItem : public QGraphicsObject, public QmlP
Q_PROPERTY(QmlGraphicsItem * parent READ parentItem WRITE setParentItem NOTIFY parentChanged DESIGNABLE false FINAL)
Q_PROPERTY(QmlList<QObject *> *data READ data DESIGNABLE false)
- Q_PROPERTY(QmlList<QmlGraphicsItem *>* children READ fxChildren DESIGNABLE false)
+ Q_PROPERTY(QmlList<QmlGraphicsItem *>* children READ fxChildren DESIGNABLE false NOTIFY childrenChanged)
Q_PROPERTY(QmlList<QObject *>* resources READ resources DESIGNABLE false)
Q_PROPERTY(QmlList<QmlState *>* states READ states DESIGNABLE false)
Q_PROPERTY(QmlList<QmlTransition *>* transitions READ transitions DESIGNABLE false)
@@ -160,6 +160,7 @@ public:
Q_SIGNALS:
void widthChanged();
void heightChanged();
+ void childrenChanged();
void childrenRectChanged();
void baselineOffsetChanged();
void stateChanged(const QString &);
diff --git a/src/declarative/graphicsitems/qmlgraphicswebview.cpp b/src/declarative/graphicsitems/qmlgraphicswebview.cpp
index 00fdd6d..c8bb504 100644
--- a/src/declarative/graphicsitems/qmlgraphicswebview.cpp
+++ b/src/declarative/graphicsitems/qmlgraphicswebview.cpp
@@ -368,8 +368,13 @@ void QmlGraphicsWebView::setPreferredHeight(int ih)
}
/*!
- Evaluates the \a scriptSource JavaScript inside the main frame
- context and returns the result of the last executed statement.
+ \qmlmethod bool WebView::evaluateJavaScript(string)
+
+ Evaluates the \a scriptSource JavaScript inside the context of the
+ main web frame, and returns the result of the last executed statement.
+
+ Note that this JavaScript does \e not have any access to QML objects
+ except as made available as windowObjects.
*/
QVariant QmlGraphicsWebView::evaluateJavaScript(const QString &scriptSource)
{
diff --git a/src/declarative/qml/qmlengine.cpp b/src/declarative/qml/qmlengine.cpp
index 9abd216..86472de 100644
--- a/src/declarative/qml/qmlengine.cpp
+++ b/src/declarative/qml/qmlengine.cpp
@@ -107,11 +107,6 @@ struct StaticQtMetaObject : public QObject
{ return &static_cast<StaticQtMetaObject*> (0)->staticQtMetaObject; }
};
-static QString userLocalDataPath(const QString& app)
-{
- return QDesktopServices::storageLocation(QDesktopServices::DataLocation) + QLatin1String("/") + app;
-}
-
QmlEnginePrivate::QmlEnginePrivate(QmlEngine *e)
: rootContext(0), currentExpression(0),
isDebugging(false), contextClass(0), objectClass(0), valueTypeClass(0), globalClass(0),
@@ -125,7 +120,9 @@ QmlEnginePrivate::QmlEnginePrivate(QmlEngine *e)
scriptEngine.newQMetaObject(StaticQtMetaObject::get());
scriptEngine.globalObject().setProperty(QLatin1String("Qt"), qtObject);
- offlineStoragePath = userLocalDataPath(QLatin1String("QML/OfflineStorage"));
+ offlineStoragePath = QDesktopServices::storageLocation(QDesktopServices::DataLocation)
+ + QDir::separator() + QLatin1String("QML")
+ + QDir::separator() + QLatin1String("OfflineStorage");
qt_add_qmlxmlhttprequest(&scriptEngine);
qt_add_qmlsqldatabase(&scriptEngine);
@@ -1256,8 +1253,12 @@ void QmlEngine::addImportPath(const QString& path)
QmlGraphicsWebView and the SQL databases created with openDatabase()
are stored here.
- The default is QML/OfflineStorage/ in the platform-standard
+ The default is QML/OfflineStorage in the platform-standard
user application data directory.
+
+ Note that the path may not currently exist on the filesystem, so
+ callers wanting to \e create new files at this location should create
+ it first - see QDir::mkpath().
*/
void QmlEngine::setOfflineStoragePath(const QString& dir)
{
diff --git a/src/declarative/qml/qmlsqldatabase.cpp b/src/declarative/qml/qmlsqldatabase.cpp
index c7d2e12..6e32fb7 100644
--- a/src/declarative/qml/qmlsqldatabase.cpp
+++ b/src/declarative/qml/qmlsqldatabase.cpp
@@ -248,10 +248,10 @@ static QScriptValue qmlsqldatabase_executeSql(QScriptContext *context, QScriptEn
QSqlQuery query(db);
bool err = false;
if (query.prepare(sql)) {
- if (values.isArray()) {
+ if (values.isObject()) {
for (QScriptValueIterator it(values); it.hasNext();) {
it.next();
- query.addBindValue(it.value().toVariant());
+ query.bindValue(it.name(),it.value().toVariant());
}
} else {
query.bindValue(0,values.toVariant());
@@ -337,7 +337,8 @@ static QScriptValue qmlsqldatabase_open(QScriptContext *context, QScriptEngine *
database = QSqlDatabase::addDatabase(QLatin1String("QSQLITE"), dbid);
}
if (!database.isOpen()) {
- QString basename = QmlEnginePrivate::get(engine)->offlineStoragePath + QLatin1String("/Databases/");
+ QString basename = QmlEnginePrivate::get(engine)->offlineStoragePath
+ + QDir::separator() + QLatin1String("Databases") + QDir::separator();
QDir().mkpath(basename);
basename += dbid;
database.setDatabaseName(basename+QLatin1String(".sqlite"));
diff --git a/src/declarative/util/qmlanimation.cpp b/src/declarative/util/qmlanimation.cpp
index d78f0a1..780bc82 100644
--- a/src/declarative/util/qmlanimation.cpp
+++ b/src/declarative/util/qmlanimation.cpp
@@ -62,7 +62,7 @@
QT_BEGIN_NAMESPACE
-QEasingCurve stringToCurve(const QString &curve)
+static QEasingCurve stringToCurve(const QString &curve, QObject *obj)
{
QEasingCurve easingCurve;
@@ -73,8 +73,7 @@ QEasingCurve stringToCurve(const QString &curve)
if (hasParams) {
QString easeName = curve.trimmed();
if (!easeName.endsWith(QLatin1Char(')'))) {
- qWarning("QEasingCurve: Unmatched perenthesis in easing function '%s'",
- qPrintable(curve));
+ qmlInfo(obj) << obj->tr("Unmatched parenthesis in easing function \"%1\"").arg(curve);
return easingCurve;
}
@@ -83,8 +82,8 @@ QEasingCurve stringToCurve(const QString &curve)
easeName.mid(idx + 1, easeName.length() - 1 - idx - 1);
normalizedCurve = easeName.left(idx);
if (!normalizedCurve.startsWith(QLatin1String("ease"))) {
- qWarning("QEasingCurve: Easing function '%s' must start with 'ease'",
- qPrintable(curve));
+ qmlInfo(obj) << obj->tr("Easing function \"%1\" must start with \"ease\"").arg(curve);
+ return easingCurve;
}
props = prop_str.split(QLatin1Char(','));
@@ -98,9 +97,8 @@ QEasingCurve stringToCurve(const QString &curve)
int value = me.keyToValue(normalizedCurve.toUtf8().constData());
if (value < 0) {
- qWarning("QEasingCurve: Unknown easing curve '%s'",
- qPrintable(curve));
- value = 0;
+ qmlInfo(obj) << obj->tr("Unknown easing curve \"%1\"").arg(curve);
+ return easingCurve;
}
easingCurve.setType((QEasingCurve::Type)value);
@@ -109,9 +107,8 @@ QEasingCurve stringToCurve(const QString &curve)
int sep = str.indexOf(QLatin1Char(':'));
if (sep == -1) {
- qWarning("QEasingCurve: Improperly specified property in easing function '%s'",
- qPrintable(curve));
- return easingCurve;
+ qmlInfo(obj) << obj->tr("Improperly specified parameter in easing function \"%1\"").arg(curve);
+ continue;
}
QString propName = str.left(sep).trimmed();
@@ -119,9 +116,8 @@ QEasingCurve stringToCurve(const QString &curve)
qreal propValue = str.mid(sep + 1).trimmed().toDouble(&isOk);
if (propName.isEmpty() || !isOk) {
- qWarning("QEasingCurve: Improperly specified property in easing function '%s'",
- qPrintable(curve));
- return easingCurve;
+ qmlInfo(obj) << obj->tr("Improperly specified parameter in easing function \"%1\"").arg(curve);
+ continue;
}
if (propName == QLatin1String("amplitude")) {
@@ -130,10 +126,12 @@ QEasingCurve stringToCurve(const QString &curve)
easingCurve.setPeriod(propValue);
} else if (propName == QLatin1String("overshoot")) {
easingCurve.setOvershoot(propValue);
+ } else {
+ qmlInfo(obj) << obj->tr("Unknown easing parameter \"%1\"").arg(propName);
+ continue;
}
}
}
-
return easingCurve;
}
@@ -219,16 +217,14 @@ void QmlAbstractAnimationPrivate::commence()
}
}
-//### make static?
-QmlMetaProperty QmlAbstractAnimationPrivate::createProperty(QObject *obj, const QString &str)
+QmlMetaProperty QmlAbstractAnimationPrivate::createProperty(QObject *obj, const QString &str, QObject *infoObj)
{
- Q_Q(QmlAbstractAnimation);
QmlMetaProperty prop = QmlMetaProperty::createProperty(obj, str);
if (!prop.isValid()) {
- qmlInfo(q) << QmlAbstractAnimation::tr("Cannot animate non-existant property \"%1\"").arg(str);
+ qmlInfo(infoObj) << QmlAbstractAnimation::tr("Cannot animate non-existant property \"%1\"").arg(str);
return QmlMetaProperty();
} else if (!prop.isWritable()) {
- qmlInfo(q) << QmlAbstractAnimation::tr("Cannot animate read-only property \"%1\"").arg(str);
+ qmlInfo(infoObj) << QmlAbstractAnimation::tr("Cannot animate read-only property \"%1\"").arg(str);
return QmlMetaProperty();
}
return prop;
@@ -436,7 +432,7 @@ void QmlAbstractAnimation::setTarget(QObject *o)
d->target = o;
if (d->target && !d->propertyName.isEmpty()) {
- d->userProperty = d->createProperty(d->target, d->propertyName);
+ d->userProperty = d->createProperty(d->target, d->propertyName, this);
} else {
d->userProperty.invalidate();
}
@@ -458,7 +454,7 @@ void QmlAbstractAnimation::setProperty(const QString &n)
d->propertyName = n;
if (d->target && !d->propertyName.isEmpty()) {
- d->userProperty = d->createProperty(d->target, d->propertyName);
+ d->userProperty = d->createProperty(d->target, d->propertyName, this);
} else {
d->userProperty.invalidate();
}
@@ -652,7 +648,7 @@ int QmlPauseAnimation::duration() const
void QmlPauseAnimation::setDuration(int duration)
{
if (duration < 0) {
- qWarning("QmlPauseAnimation: Cannot set a duration of < 0");
+ qmlInfo(this) << tr("Cannot set a duration of < 0");
return;
}
@@ -1029,7 +1025,7 @@ void QmlPropertyAction::transition(QmlStateActions &actions,
if (hasTarget && d->value.isValid()) {
Action myAction;
- myAction.property = d->createProperty(target(), d->propertyName);
+ myAction.property = d->createProperty(target(), d->propertyName, this);
if (myAction.property.isValid()) {
myAction.toValue = d->value;
data->actions << myAction;
@@ -1630,7 +1626,7 @@ int QmlPropertyAnimation::duration() const
void QmlPropertyAnimation::setDuration(int duration)
{
if (duration < 0) {
- qWarning("QmlPropertyAnimation: Cannot set a duration of < 0");
+ qmlInfo(this) << tr("Cannot set a duration of < 0");
return;
}
@@ -1872,7 +1868,7 @@ void QmlPropertyAnimation::setEasing(const QString &e)
return;
d->easing = e;
- d->va->setEasingCurve(stringToCurve(d->easing));
+ d->va->setEasingCurve(stringToCurve(d->easing, this));
emit easingChanged(e);
}
@@ -2114,7 +2110,7 @@ void QmlPropertyAnimation::transition(QmlStateActions &actions,
//an explicit animation has been specified
if (hasTarget && d->toIsDefined) {
Action myAction;
- myAction.property = d->createProperty(target(), d->propertyName);
+ myAction.property = d->createProperty(target(), d->propertyName, this);
if (myAction.property.isValid()) {
if (d->fromIsDefined) {
d->convertVariant(d->from, d->interpolatorType ? d->interpolatorType : myAction.property.propertyType());
diff --git a/src/declarative/util/qmlanimation_p.h b/src/declarative/util/qmlanimation_p.h
index f126dee..87b6703 100644
--- a/src/declarative/util/qmlanimation_p.h
+++ b/src/declarative/util/qmlanimation_p.h
@@ -136,7 +136,7 @@ private Q_SLOTS:
};
class QmlPauseAnimationPrivate;
-class QmlPauseAnimation : public QmlAbstractAnimation
+class Q_AUTOTEST_EXPORT QmlPauseAnimation : public QmlAbstractAnimation
{
Q_OBJECT
Q_DECLARE_PRIVATE(QmlPauseAnimation)
diff --git a/src/declarative/util/qmlanimation_p_p.h b/src/declarative/util/qmlanimation_p_p.h
index e50415f..27c0cd7 100644
--- a/src/declarative/util/qmlanimation_p_p.h
+++ b/src/declarative/util/qmlanimation_p_p.h
@@ -208,7 +208,7 @@ public:
QmlMetaProperty property;
QmlAnimationGroup *group;
- QmlMetaProperty createProperty(QObject *obj, const QString &str);
+ static QmlMetaProperty createProperty(QObject *obj, const QString &str, QObject *infoObj);
};
class QmlPauseAnimationPrivate : public QmlAbstractAnimationPrivate
diff --git a/src/declarative/util/qmllistmodel.cpp b/src/declarative/util/qmllistmodel.cpp
index 9e91147..a3c5c59 100644
--- a/src/declarative/util/qmllistmodel.cpp
+++ b/src/declarative/util/qmllistmodel.cpp
@@ -483,6 +483,10 @@ void QmlListModel::remove(int index)
*/
void QmlListModel::insert(int index, const QScriptValue& valuemap)
{
+ if (!valuemap.isObject() || valuemap.isArray()) {
+ qmlInfo(this) << tr("insert: value is not an object");
+ return;
+ }
if (!_root)
_root = new ModelNode;
if (index >= _root->values.count() || index<0) {
@@ -517,8 +521,10 @@ void QmlListModel::move(int from, int to, int n)
{
if (n==0 || from==to)
return;
- if (from+n > count() || to+n > count() || from < 0 || to < 0)
+ if (from+n > count() || to+n > count() || from < 0 || to < 0 || n < 0) {
qmlInfo(this) << tr("move: out of range");
+ return;
+ }
int origfrom=from; // preserve actual move, so any animations are correct
int origto=to;
int orign=n;
@@ -564,7 +570,7 @@ void QmlListModel::move(int from, int to, int n)
*/
void QmlListModel::append(const QScriptValue& valuemap)
{
- if (!valuemap.isObject()) {
+ if (!valuemap.isObject() || valuemap.isArray()) {
qmlInfo(this) << tr("append: value is not an object");
return;
}
@@ -636,9 +642,11 @@ QScriptValue QmlListModel::get(int index) const
*/
void QmlListModel::set(int index, const QScriptValue& valuemap)
{
- if (!_root)
- _root = new ModelNode;
- if ( index > _root->values.count()) {
+ if (!valuemap.isObject() || valuemap.isArray()) {
+ qmlInfo(this) << tr("set: value is not an object");
+ return;
+ }
+ if ( !_root || index > _root->values.count()) {
qmlInfo(this) << tr("set: index %1 out of range").arg(index);
return;
}
@@ -677,9 +685,7 @@ void QmlListModel::set(int index, const QScriptValue& valuemap)
*/
void QmlListModel::set(int index, const QString& property, const QVariant& value)
{
- if (!_root)
- _root = new ModelNode;
- if ( index >= _root->values.count()) {
+ if ( !_root || index >= _root->values.count()) {
qmlInfo(this) << tr("set: index %1 out of range").arg(index);
return;
}
diff --git a/tests/auto/declarative/animations/tst_animations.cpp b/tests/auto/declarative/animations/tst_animations.cpp
index 2692cb6..2506337 100644
--- a/tests/auto/declarative/animations/tst_animations.cpp
+++ b/tests/auto/declarative/animations/tst_animations.cpp
@@ -57,6 +57,8 @@ private slots:
void simpleNumber();
void simpleColor();
void alwaysRunToEnd();
+ void complete();
+ void resume();
void dotProperty();
void badTypes();
void badProperties();
@@ -64,6 +66,7 @@ private slots:
void properties();
void propertiesTransition();
void easingStringConversion();
+ void invalidDuration();
};
#define QTIMED_COMPARE(lhs, rhs) do { \
@@ -96,6 +99,7 @@ void tst_animations::simpleProperty()
QVERIFY(animation.isRunning());
QVERIFY(animation.isPaused());
animation.setCurrentTime(125);
+ QVERIFY(animation.currentTime() == 125);
QCOMPARE(rect.pos(), QPointF(100,100));
}
@@ -120,6 +124,7 @@ void tst_animations::simpleNumber()
QVERIFY(animation.isRunning());
QVERIFY(animation.isPaused());
animation.setCurrentTime(125);
+ QVERIFY(animation.currentTime() == 125);
QCOMPARE(rect.x(), qreal(100));
}
@@ -144,6 +149,7 @@ void tst_animations::simpleColor()
QVERIFY(animation.isRunning());
QVERIFY(animation.isPaused());
animation.setCurrentTime(125);
+ QVERIFY(animation.currentTime() == 125);
QCOMPARE(rect.color(), QColor::fromRgbF(0.498039, 0, 0.498039, 1));
}
@@ -157,6 +163,8 @@ void tst_animations::alwaysRunToEnd()
animation.setDuration(1000);
animation.setRepeat(true);
animation.setAlwaysRunToEnd(true);
+ QVERIFY(animation.repeat() == true);
+ QVERIFY(animation.alwaysRunToEnd() == true);
animation.start();
QTest::qWait(1500);
animation.stop();
@@ -165,6 +173,54 @@ void tst_animations::alwaysRunToEnd()
QTIMED_COMPARE(rect.x(), qreal(200));
}
+void tst_animations::complete()
+{
+ QmlGraphicsRectangle rect;
+ QmlPropertyAnimation animation;
+ animation.setTarget(&rect);
+ animation.setProperty("x");
+ animation.setFrom(1);
+ animation.setTo(200);
+ animation.setDuration(500);
+ QVERIFY(animation.from() == 1);
+ animation.start();
+ QTest::qWait(50);
+ animation.stop();
+ QVERIFY(rect.x() != qreal(200));
+ animation.start();
+ QTest::qWait(50);
+ QVERIFY(animation.isRunning());
+ animation.complete();
+ QCOMPARE(rect.x(), qreal(200));
+}
+
+void tst_animations::resume()
+{
+ QmlGraphicsRectangle rect;
+ QmlPropertyAnimation animation;
+ animation.setTarget(&rect);
+ animation.setProperty("x");
+ animation.setFrom(10);
+ animation.setTo(200);
+ animation.setDuration(500);
+ QVERIFY(animation.from() == 10);
+
+ animation.start();
+ QTest::qWait(50);
+ animation.pause();
+ qreal x = rect.x();
+ QVERIFY(x != qreal(200));
+ QVERIFY(animation.isRunning());
+ QVERIFY(animation.isPaused());
+
+ animation.resume();
+ QVERIFY(animation.isRunning());
+ QVERIFY(!animation.isPaused());
+ QTest::qWait(50);
+ animation.stop();
+ QVERIFY(rect.x() > x);
+}
+
void tst_animations::dotProperty()
{
QmlGraphicsRectangle rect;
@@ -180,6 +236,7 @@ void tst_animations::dotProperty()
animation.start();
animation.pause();
animation.setCurrentTime(125);
+ QVERIFY(animation.currentTime() == 125);
QCOMPARE(rect.border()->width(), 5);
}
@@ -427,6 +484,7 @@ void tst_animations::easingStringConversion()
{
QmlNumberAnimation *animation = new QmlNumberAnimation;
animation->setEasing("easeInOutQuad");
+ QCOMPARE(animation->easing(),QLatin1String("easeInOutQuad"));
QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve(), QEasingCurve(QEasingCurve::InOutQuad));
animation->setEasing("OutQuad");
@@ -436,9 +494,56 @@ void tst_animations::easingStringConversion()
QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::OutBounce);
QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().amplitude(), qreal(5));
+ animation->setEasing("easeOutElastic(amplitude: 5, period: 3)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::OutElastic);
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().amplitude(), qreal(5));
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().period(), qreal(3));
+
+ animation->setEasing("easeInOutBack(overshoot: 2)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::InOutBack);
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().overshoot(), qreal(2));
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Unmatched parenthesis in easing function \"easeInOutBack(overshoot: 2\"");
+ animation->setEasing("easeInOutBack(overshoot: 2");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::Linear);
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Easing function \"InOutBack(overshoot: 2)\" must start with \"ease\"");
+ animation->setEasing("InOutBack(overshoot: 2)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::Linear);
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Unknown easing curve \"NonExistantEase\"");
+ animation->setEasing("NonExistantEase");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::Linear);
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Improperly specified parameter in easing function \"easeInOutElastic(amplitude 5)\"");
+ animation->setEasing("easeInOutElastic(amplitude 5)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::InOutElastic);
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Improperly specified parameter in easing function \"easeInOutElastic(amplitude: yes)\"");
+ animation->setEasing("easeInOutElastic(amplitude: yes)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::InOutElastic);
+ QVERIFY(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().amplitude() != qreal(5));
+
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlNumberAnimation (unknown location) Unknown easing parameter \"nonexistantproperty\"");
+ animation->setEasing("easeOutQuad(nonexistantproperty: 12)");
+ QCOMPARE(static_cast<QVariantAnimation*>(((QmlAbstractAnimation*)animation)->qtAnimation())->easingCurve().type(), QEasingCurve::OutQuad);
+
delete animation;
}
+void tst_animations::invalidDuration()
+{
+ QmlPropertyAnimation *animation = new QmlPropertyAnimation;
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlPropertyAnimation (unknown location) Cannot set a duration of < 0");
+ animation->setDuration(-1);
+ QCOMPARE(animation->duration(), 250);
+
+ QmlPauseAnimation *pauseAnimation = new QmlPauseAnimation;
+ QTest::ignoreMessage(QtWarningMsg, "QML QmlPauseAnimation (unknown location) Cannot set a duration of < 0");
+ pauseAnimation->setDuration(-1);
+ QCOMPARE(pauseAnimation->duration(), 250);
+}
+
QTEST_MAIN(tst_animations)
#include "tst_animations.moc"
diff --git a/tests/auto/declarative/qmlengine/tst_qmlengine.cpp b/tests/auto/declarative/qmlengine/tst_qmlengine.cpp
index 54f916f..5471691 100644
--- a/tests/auto/declarative/qmlengine/tst_qmlengine.cpp
+++ b/tests/auto/declarative/qmlengine/tst_qmlengine.cpp
@@ -161,10 +161,18 @@ void tst_qmlengine::contextForObject()
void tst_qmlengine::offlineStoragePath()
{
+ // Without these set, QDesktopServices::storageLocation returns
+ // strings with extra "//" at the end. We set them to ignore this problem.
+ qApp->setApplicationName("tst_qmlengine");
+ qApp->setOrganizationName("Nokia");
+ qApp->setOrganizationDomain("nokia.com");
+
QmlEngine engine;
QDir dir(QDesktopServices::storageLocation(QDesktopServices::DataLocation));
+ dir.mkpath("QML");
dir.cd("QML");
+ dir.mkpath("OfflineStorage");
dir.cd("OfflineStorage");
QCOMPARE(engine.offlineStoragePath(), dir.path());
diff --git a/tests/auto/declarative/qmlgraphicsgridview/tst_qmlgraphicsgridview.cpp b/tests/auto/declarative/qmlgraphicsgridview/tst_qmlgraphicsgridview.cpp
index d0b7462..197191e 100644
--- a/tests/auto/declarative/qmlgraphicsgridview/tst_qmlgraphicsgridview.cpp
+++ b/tests/auto/declarative/qmlgraphicsgridview/tst_qmlgraphicsgridview.cpp
@@ -61,8 +61,8 @@ private slots:
void inserted();
void removed();
void moved();
- void currentIndex();
void changeFlow();
+ void currentIndex();
void defaultValues();
void properties();
@@ -310,7 +310,7 @@ void tst_QmlGraphicsGridView::removed()
QmlView *canvas = createView(SRCDIR "/data/gridview.qml");
TestModel model;
- for (int i = 0; i < 30; i++)
+ for (int i = 0; i < 40; i++)
model.addItem("Item" + QString::number(i), "");
QmlContext *ctxt = canvas->rootContext();
@@ -388,6 +388,7 @@ void tst_QmlGraphicsGridView::removed()
// Remove items before visible
gridview->setViewportY(120);
+ QTest::qWait(500);
gridview->setCurrentIndex(10);
// let transitions settle.
@@ -421,6 +422,14 @@ void tst_QmlGraphicsGridView::removed()
QVERIFY(item->y() == (i/3)*60);
}
+ // remove item outside current view.
+ gridview->setCurrentIndex(32);
+ QTest::qWait(500);
+ gridview->setViewportY(240);
+
+ model.removeItem(30);
+ QVERIFY(gridview->currentIndex() == 31);
+
delete canvas;
}
@@ -623,6 +632,29 @@ void tst_QmlGraphicsGridView::currentIndex()
QVERIFY(key.isAccepted());
QCOMPARE(gridview->currentIndex(), 0);
+ gridview->setFlow(QmlGraphicsGridView::TopToBottom);
+
+ key = QKeyEvent(QEvent::KeyPress, Qt::Key_Right, Qt::NoModifier, "", false, 1);
+ QApplication::sendEvent(canvas, &key);
+ QVERIFY(key.isAccepted());
+ QCOMPARE(gridview->currentIndex(), 5);
+
+ key = QKeyEvent(QEvent::KeyPress, Qt::Key_Left, Qt::NoModifier, "", false, 1);
+ QApplication::sendEvent(canvas, &key);
+ QVERIFY(key.isAccepted());
+ QCOMPARE(gridview->currentIndex(), 0);
+
+ key = QKeyEvent(QEvent::KeyPress, Qt::Key_Down, Qt::NoModifier, "", false, 1);
+ QApplication::sendEvent(canvas, &key);
+ QVERIFY(key.isAccepted());
+ QCOMPARE(gridview->currentIndex(), 1);
+
+ key = QKeyEvent(QEvent::KeyPress, Qt::Key_Up, Qt::NoModifier, "", false, 1);
+ QApplication::sendEvent(canvas, &key);
+ QVERIFY(key.isAccepted());
+ QCOMPARE(gridview->currentIndex(), 0);
+
+
// turn off auto highlight
gridview->setHighlightFollowsCurrentItem(false);
QVERIFY(gridview->highlightFollowsCurrentItem() == false);
diff --git a/tests/auto/declarative/qmlgraphicslistview/data/listview.qml b/tests/auto/declarative/qmlgraphicslistview/data/listview.qml
index ec8bb68..b64b399 100644
--- a/tests/auto/declarative/qmlgraphicslistview/data/listview.qml
+++ b/tests/auto/declarative/qmlgraphicslistview/data/listview.qml
@@ -114,5 +114,6 @@ Rectangle {
highlight: testObject.invalidHighlight ? invalidHl : myHighlight
highlightMoveSpeed: 1000
highlightResizeSpeed: 1000
+ cacheBuffer: testObject.cacheBuffer
}
}
diff --git a/tests/auto/declarative/qmlgraphicslistview/tst_qmlgraphicslistview.cpp b/tests/auto/declarative/qmlgraphicslistview/tst_qmlgraphicslistview.cpp
index 7e6dc0d..36f4dc5 100644
--- a/tests/auto/declarative/qmlgraphicslistview/tst_qmlgraphicslistview.cpp
+++ b/tests/auto/declarative/qmlgraphicslistview/tst_qmlgraphicslistview.cpp
@@ -97,10 +97,12 @@ class TestObject : public QObject
Q_PROPERTY(bool error READ error WRITE setError NOTIFY changedError)
Q_PROPERTY(bool animate READ animate NOTIFY changedAnim)
Q_PROPERTY(bool invalidHighlight READ invalidHighlight NOTIFY changedHl)
+ Q_PROPERTY(int cacheBuffer READ cacheBuffer NOTIFY changedCacheBuffer)
public:
TestObject(QObject *parent = 0)
- : QObject(parent), mError(true), mAnimate(false), mInvalidHighlight(false) {}
+ : QObject(parent), mError(true), mAnimate(false), mInvalidHighlight(false)
+ , mCacheBuffer(0) {}
bool error() const { return mError; }
void setError(bool err) { mError = err; emit changedError(); }
@@ -111,15 +113,20 @@ public:
bool invalidHighlight() const { return mInvalidHighlight; }
void setInvalidHighlight(bool invalid) { mInvalidHighlight = invalid; emit changedHl(); }
+ int cacheBuffer() const { return mCacheBuffer; }
+ void setCacheBuffer(int buffer) { mCacheBuffer = buffer; emit changedCacheBuffer(); }
+
signals:
void changedError();
void changedAnim();
void changedHl();
+ void changedCacheBuffer();
public:
bool mError;
bool mAnimate;
bool mInvalidHighlight;
+ int mCacheBuffer;
};
class TestModel : public QListModelInterface
@@ -291,6 +298,7 @@ void tst_QmlGraphicsListView::items()
QMetaObject::invokeMethod(canvas->root(), "checkProperties");
QVERIFY(testObject->error() == false);
+ QVERIFY(listview->highlightItem() != 0);
QCOMPARE(listview->count(), model.count());
QCOMPARE(viewport->childItems().count(), model.count()+1); // assumes all are visible, +1 for the (default) highlight item
@@ -315,6 +323,7 @@ void tst_QmlGraphicsListView::items()
testObject->setInvalidHighlight(true);
QMetaObject::invokeMethod(canvas->root(), "checkProperties");
QVERIFY(testObject->error() == false);
+ QVERIFY(listview->highlightItem() == 0);
// set an empty model and confirm that items are destroyed
T model2;
@@ -566,6 +575,25 @@ void tst_QmlGraphicsListView::removed(bool animated)
QCOMPARE(item->y(),40+i*20.0);
}
+ // remove current item beyond visible items.
+ listview->setCurrentIndex(20);
+ QTest::qWait(500);
+ model.removeItem(20);
+ QTest::qWait(500);
+
+ QCOMPARE(listview->currentIndex(), 20);
+ QVERIFY(listview->currentItem() != 0);
+
+ // remove item before current, but visible
+ listview->setCurrentIndex(8);
+ QTest::qWait(500);
+ QmlGraphicsItem *oldCurrent = listview->currentItem();
+ model.removeItem(6);
+ QTest::qWait(500);
+
+ QCOMPARE(listview->currentIndex(), 7);
+ QVERIFY(listview->currentItem() == oldCurrent);
+
delete canvas;
}
@@ -1006,7 +1034,7 @@ void tst_QmlGraphicsListView::cacheBuffer()
QVERIFY(viewport != 0);
QVERIFY(listview->delegate() != 0);
QVERIFY(listview->model() != 0);
- QVERIFY(listview->highlight() == 0);
+ QVERIFY(listview->highlight() != 0);
// Confirm items positioned correctly
int itemCount = findItems<QmlGraphicsItem>(viewport, "wrapper").count();
@@ -1017,7 +1045,7 @@ void tst_QmlGraphicsListView::cacheBuffer()
QVERIFY(item->y() == i*20);
}
- listview->setCacheBuffer(400);
+ testObject->setCacheBuffer(400);
QVERIFY(listview->cacheBuffer() == 400);
int newItemCount = findItems<QmlGraphicsItem>(viewport, "wrapper").count();
diff --git a/tests/auto/declarative/qmllistmodel/tst_qmllistmodel.cpp b/tests/auto/declarative/qmllistmodel/tst_qmllistmodel.cpp
index 3222d42..80efd94 100644
--- a/tests/auto/declarative/qmllistmodel/tst_qmllistmodel.cpp
+++ b/tests/auto/declarative/qmllistmodel/tst_qmllistmodel.cpp
@@ -64,10 +64,14 @@ void tst_QmlListModel::dynamic_data()
QTest::newRow("count") << "count" << 0 << "";
+ QTest::newRow("get1") << "{get(0)}" << 0 << "QML QmlListModel (unknown location) get: index 0 out of range";
+
QTest::newRow("append1") << "{append({'foo':123});count}" << 1 << "";
QTest::newRow("append2") << "{append({'foo':123,'bar':456});count}" << 1 << "";
QTest::newRow("append3a") << "{append({'foo':123});append({'foo':456});get(0).foo}" << 123 << "";
QTest::newRow("append3b") << "{append({'foo':123});append({'foo':456});get(1).foo}" << 456 << "";
+ QTest::newRow("append4a") << "{append(123)}" << 0 << "QML QmlListModel (unknown location) append: value is not an object";
+ QTest::newRow("append4b") << "{append([1,2,3])}" << 0 << "QML QmlListModel (unknown location) append: value is not an object";
QTest::newRow("clear1") << "{append({'foo':456});clear();count}" << 0 << "";
QTest::newRow("clear2") << "{append({'foo':123});append({'foo':456});clear();count}" << 0 << "";
@@ -78,6 +82,9 @@ void tst_QmlListModel::dynamic_data()
QTest::newRow("remove2b") << "{append({'foo':123});append({'foo':456});remove(0);get(0).foo}" << 456 << "";
QTest::newRow("remove2c") << "{append({'foo':123});append({'foo':456});remove(1);get(0).foo}" << 123 << "";
QTest::newRow("remove3") << "{append({'foo':123});remove(0);get(0).foo}" << 0 << "QML QmlListModel (unknown location) get: index 0 out of range";
+ QTest::newRow("remove4a") << "{remove(0)}" << 0 << "QML QmlListModel (unknown location) remove: index 0 out of range";
+ QTest::newRow("remove4b") << "{append({'foo':123});remove(0);remove(0)}" << 0 << "QML QmlListModel (unknown location) remove: index 0 out of range";
+ QTest::newRow("remove4c") << "{append({'foo':123});remove(1)}" << 0 << "QML QmlListModel (unknown location) remove: index 1 out of range";
QTest::newRow("insert1") << "{insert(0,{'foo':123});count}" << 1 << "";
QTest::newRow("insert2") << "{insert(1,{'foo':123});count}" << 0 << "QML QmlListModel (unknown location) insert: index 1 out of range";
@@ -87,16 +94,23 @@ void tst_QmlListModel::dynamic_data()
QTest::newRow("insert3d") << "{append({'foo':123});insert(0,{'foo':456});get(0).foo}" << 456 << "";
QTest::newRow("insert3e") << "{append({'foo':123});insert(0,{'foo':456});get(1).foo}" << 123 << "";
QTest::newRow("insert4") << "{append({'foo':123});insert(-1,{'foo':456})}" << 0 << "QML QmlListModel (unknown location) insert: index -1 out of range";
+ QTest::newRow("insert5a") << "{insert(0,123)}" << 0 << "QML QmlListModel (unknown location) insert: value is not an object";
+ QTest::newRow("insert5b") << "{insert(0,[1,2,3])}" << 0 << "QML QmlListModel (unknown location) insert: value is not an object";
QTest::newRow("set1") << "{append({'foo':123});set(0,{'foo':456});count}" << 1 << "";
QTest::newRow("set2") << "{append({'foo':123});set(0,{'foo':456});get(0).foo}" << 456 << "";
QTest::newRow("set3a") << "{append({'foo':123,'bar':456});set(0,{'foo':999});get(0).foo}" << 999 << "";
QTest::newRow("set3b") << "{append({'foo':123,'bar':456});set(0,{'foo':999});get(0).bar}" << 456 << "";
+ QTest::newRow("set4a") << "{set(0,{'foo':456})}" << 0 << "QML QmlListModel (unknown location) set: index 0 out of range";
+ QTest::newRow("set5a") << "{append({'foo':123,'bar':456});set(0,123)}" << 0 << "QML QmlListModel (unknown location) set: value is not an object";
+ QTest::newRow("set5b") << "{append({'foo':123,'bar':456});set(0,[1,2,3])}" << 0 << "QML QmlListModel (unknown location) set: value is not an object";
QTest::newRow("setprop1") << "{append({'foo':123});set(0,'foo',456);count}" << 1 << "";
QTest::newRow("setprop2") << "{append({'foo':123});set(0,'foo',456);get(0).foo}" << 456 << "";
QTest::newRow("setprop3a") << "{append({'foo':123,'bar':456});set(0,'foo',999);get(0).foo}" << 999 << "";
QTest::newRow("setprop3b") << "{append({'foo':123,'bar':456});set(0,'foo',999);get(0).bar}" << 456 << "";
+ QTest::newRow("setprop4a") << "{set(0,'foo',456)}" << 0 << "QML QmlListModel (unknown location) set: index 0 out of range";
+ QTest::newRow("setprop4a") << "{append({'foo':123,'bar':456});set(1,'foo',456)}" << 0 << "QML QmlListModel (unknown location) set: index 1 out of range";
QTest::newRow("move1a") << "{append({'foo':123});append({'foo':456});move(0,1,1);count}" << 2 << "";
QTest::newRow("move1b") << "{append({'foo':123});append({'foo':456});move(0,1,1);get(0).foo}" << 456 << "";
@@ -107,6 +121,10 @@ void tst_QmlListModel::dynamic_data()
QTest::newRow("move2b") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(0,1,2);get(0).foo}" << 789 << "";
QTest::newRow("move2c") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(0,1,2);get(1).foo}" << 123 << "";
QTest::newRow("move2d") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(0,1,2);get(2).foo}" << 456 << "";
+ QTest::newRow("move3a") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(1,0,3)}" << 0 << "QML QmlListModel (unknown location) move: out of range";
+ QTest::newRow("move3b") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(1,-1,1)}" << 0 << "QML QmlListModel (unknown location) move: out of range";
+ QTest::newRow("move3c") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(1,0,-1)}" << 0 << "QML QmlListModel (unknown location) move: out of range";
+ QTest::newRow("move3d") << "{append({'foo':123});append({'foo':456});append({'foo':789});move(0,3,1)}" << 0 << "QML QmlListModel (unknown location) move: out of range";
// Structured model
diff --git a/tests/auto/declarative/sql/data/2-selection-bindnames.js b/tests/auto/declarative/sql/data/2-selection-bindnames.js
new file mode 100644
index 0000000..c00acc14
--- /dev/null
+++ b/tests/auto/declarative/sql/data/2-selection-bindnames.js
@@ -0,0 +1,24 @@
+var db = openDatabase("QmlTestDB", "", "Test database from Qt autotests", 1000000);
+var r=0;
+
+db.transaction(
+ function(tx) {
+ tx.executeSql('SELECT * FROM Greeting WHERE salutation=:p2 AND salutee=:p1', {':p1':'world', ':p2':'hello'},
+ function(tx, rs) {
+ if ( rs.rows.length != 4 ) {
+ if (r==0) r = "SELECT RETURNED WRONG VALUE "+rs.rows.length+rs.rows.item(0)+rs.rows.item(1)
+ }
+ },
+ function(tx, error) { if (r==0) r="SELECT FAILED: "+error.message }
+ );
+ },
+ function(tx, error) { if (r==0) r="TRANSACTION FAILED: "+error.message },
+ function(tx, result) { if (r==0) r="passed" }
+);
+
+
+function test()
+{
+ if (r == 0) r = "transaction_not_finished";
+ return r;
+}
diff --git a/tests/auto/declarative/sql/data/6-iteration-efficient.js b/tests/auto/declarative/sql/data/6-iteration-efficient.js
index 2222b8a..6711fb0 100644
--- a/tests/auto/declarative/sql/data/6-iteration-efficient.js
+++ b/tests/auto/declarative/sql/data/6-iteration-efficient.js
@@ -1,12 +1,16 @@
var db = openDatabase("QmlTestDB", "", "Test database from Qt autotests", 1000000);
var r=0;
+var fbefore="FORWARD WRONG"
+var fafter="FORWARD WRONG"
db.transaction(
function(tx) {
tx.executeSql('SELECT * FROM Greeting', [],
function(tx, rs) {
var r1=""
+ if (!rs.rows.forwardOnly) fbefore=""
rs.rows.forwardOnly = true;
+ if (rs.rows.forwardOnly) fafter="";
for(var i=0; rs.rows[i]; ++i) {
r1 += rs.rows[i].salutation + ", " + rs.rows[i].salutee + ";"
}
@@ -17,7 +21,7 @@ db.transaction(
);
},
function(tx, error) { if (r==0) r="TRANSACTION FAILED: "+error.message },
- function(tx, result) { if (r==0) r="passed" }
+ function(tx, result) { if (r==0) r=fbefore+"passed"+fafter }
);
diff --git a/tests/auto/declarative/sql/tst_sql.cpp b/tests/auto/declarative/sql/tst_sql.cpp
index e4f497c..973d7b1 100644
--- a/tests/auto/declarative/sql/tst_sql.cpp
+++ b/tests/auto/declarative/sql/tst_sql.cpp
@@ -139,10 +139,11 @@ void tst_sql::testQml_data()
QTest::newRow("creation") << "data/1-creation.js" << "passed" << 1 << false;
QTest::newRow("selection") << "data/2-selection.js" << "passed" << 1 << false;
+ QTest::newRow("selection-bindnames") << "data/2-selection-bindnames.js" << "passed" << 1 << true; // WebKit somehow breaks named parameters
QTest::newRow("iteration-item-function") << "data/3-iteration-item-function.js" << "passed" << 1 << false;
- QTest::newRow("iteration-index") << "data/4-iteration-index.js" << "passed" << 1 << true;
- QTest::newRow("iteration-iterator") << "data/5-iteration-iterator.js" << "passed" << 1 << true;
- QTest::newRow("iteration-efficient") << "data/6-iteration-efficient.js" << "passed" << 1 << true;
+ QTest::newRow("iteration-index") << "data/4-iteration-index.js" << "passed" << 1 << true; // Some HTML5 documents say to use rows by index, others by item() function
+ QTest::newRow("iteration-iterator") << "data/5-iteration-iterator.js" << "passed" << 1 << true; // As with previous, WebKit doesn't give an array
+ QTest::newRow("iteration-efficient") << "data/6-iteration-efficient.js" << "passed" << 1 << true; // It's very inefficient to find the total number of results, here is a solution
}
void tst_sql::validateAgainstWebkit_data()