diff options
author | Olivier Goffart <olivier.goffart@nokia.com> | 2011-02-23 11:50:01 (GMT) |
---|---|---|
committer | Olivier Goffart <olivier.goffart@nokia.com> | 2011-02-23 11:50:01 (GMT) |
commit | 5a2f7b97d564e4b8a9619cd7aa1519b4dd084ae8 (patch) | |
tree | 7886477c9d38d8c07008e12abf2eb6e05ed672e3 /src | |
parent | ca7be48b7a150952a9657d1000941fb986e5bb2b (diff) | |
parent | 33f0f832a243ee2cb188fcf27126bde6c6c883b0 (diff) | |
download | Qt-5a2f7b97d564e4b8a9619cd7aa1519b4dd084ae8.zip Qt-5a2f7b97d564e4b8a9619cd7aa1519b4dd084ae8.tar.gz Qt-5a2f7b97d564e4b8a9619cd7aa1519b4dd084ae8.tar.bz2 |
Merge remote-tracking branch 'origin/4.7' into qt-master-from-4.7
Conflicts:
src/gui/kernel/qcocoaview_mac.mm
src/s60installs/bwins/QtGuiu.def
src/s60installs/eabi/QtGuiu.def
src/testlib/qtestcase.cpp
Diffstat (limited to 'src')
56 files changed, 553 insertions, 285 deletions
diff --git a/src/3rdparty/webkit/WebKit/qt/Api/qwebkitglobal.h b/src/3rdparty/webkit/WebKit/qt/Api/qwebkitglobal.h index 63d9e55..2c0bf6d 100644 --- a/src/3rdparty/webkit/WebKit/qt/Api/qwebkitglobal.h +++ b/src/3rdparty/webkit/WebKit/qt/Api/qwebkitglobal.h @@ -22,9 +22,9 @@ #include <QtCore/qglobal.h> -#define QTWEBKIT_VERSION_STR "2.0.1" +#define QTWEBKIT_VERSION_STR "2.0.2" // QTWEBKIT_VERSION is (major << 16) + (minor << 8) + patch. Similar to Qt. -#define QTWEBKIT_VERSION 0x020001 +#define QTWEBKIT_VERSION 0x020002 // Use: #if (QTWEBKIT_VERSION >= QTWEBKIT_VERSION_CHECK(2, 0, 0)). Similar to Qt. #define QTWEBKIT_VERSION_CHECK(major, minor, patch) ((major<<16)|(minor<<8)|(patch)) diff --git a/src/corelib/concurrent/qfutureinterface.cpp b/src/corelib/concurrent/qfutureinterface.cpp index 6256944..627d0c7 100644 --- a/src/corelib/concurrent/qfutureinterface.cpp +++ b/src/corelib/concurrent/qfutureinterface.cpp @@ -421,9 +421,11 @@ bool QFutureInterfaceBase::referenceCountIsOne() const QFutureInterfaceBasePrivate::QFutureInterfaceBasePrivate(QFutureInterfaceBase::State initialState) : refCount(1), m_progressValue(0), m_progressMinimum(0), m_progressMaximum(0), - state(initialState), progressTimeStarted(false), pendingResults(0), + state(initialState), pendingResults(0), manualProgress(false), m_expectedResultCount(0), runnable(0) -{ } +{ + progressTime.invalidate(); +} int QFutureInterfaceBasePrivate::internal_resultCount() const { @@ -455,12 +457,11 @@ bool QFutureInterfaceBasePrivate::internal_updateProgress(int progress, m_progressValue = progress; m_progressText = progressText; - if (progressTimeStarted == true && m_progressValue != m_progressMaximum) // make sure the first and last steps are emitted. + if (progressTime.isValid() && m_progressValue != m_progressMaximum) // make sure the first and last steps are emitted. if (progressTime.elapsed() < (1000 / MaxProgressEmitsPerSecond)) return false; progressTime.start(); - progressTimeStarted = true; return true; } diff --git a/src/corelib/concurrent/qfutureinterface_p.h b/src/corelib/concurrent/qfutureinterface_p.h index 7f93c75..538947e 100644 --- a/src/corelib/concurrent/qfutureinterface_p.h +++ b/src/corelib/concurrent/qfutureinterface_p.h @@ -53,7 +53,7 @@ // We mean it. // -#include <QtCore/qdatetime.h> +#include <QtCore/qelapsedtimer.h> #include <QtCore/qcoreevent.h> #include <QtCore/qlist.h> #include <QtCore/qwaitcondition.h> @@ -137,8 +137,7 @@ public: int m_progressMinimum; int m_progressMaximum; QFutureInterfaceBase::State state; - QTime progressTime; - bool progressTimeStarted; + QElapsedTimer progressTime; QWaitCondition pausedWaitCondition; int pendingResults; QtConcurrent::ResultStoreBase m_results; diff --git a/src/dbus/qdbusdemarshaller.cpp b/src/dbus/qdbusdemarshaller.cpp index 3882edb..6638263 100644 --- a/src/dbus/qdbusdemarshaller.cpp +++ b/src/dbus/qdbusdemarshaller.cpp @@ -176,10 +176,10 @@ QDBusArgument::ElementType QDBusDemarshaller::currentType() case DBUS_TYPE_INVALID: return QDBusArgument::UnknownType; - default: - qWarning("QDBusDemarshaller: Found unknown D-Bus type %d '%c'", - q_dbus_message_iter_get_arg_type(&iterator), - q_dbus_message_iter_get_arg_type(&iterator)); +// default: +// qWarning("QDBusDemarshaller: Found unknown D-Bus type %d '%c'", +// q_dbus_message_iter_get_arg_type(&iterator), +// q_dbus_message_iter_get_arg_type(&iterator)); } return QDBusArgument::UnknownType; } @@ -232,10 +232,15 @@ QVariant QDBusDemarshaller::toVariantInternal() return QVariant::fromValue(duplicate()); default: - qWarning("QDBusDemarshaller: Found unknown D-Bus type %d '%c'", - q_dbus_message_iter_get_arg_type(&iterator), - q_dbus_message_iter_get_arg_type(&iterator)); - return QVariant(); +// qWarning("QDBusDemarshaller: Found unknown D-Bus type %d '%c'", +// q_dbus_message_iter_get_arg_type(&iterator), +// q_dbus_message_iter_get_arg_type(&iterator)); + char *ptr = 0; + ptr += q_dbus_message_iter_get_arg_type(&iterator); + q_dbus_message_iter_next(&iterator); + + // I hope you never dereference this pointer! + return QVariant::fromValue<void *>(ptr); break; }; } diff --git a/src/dbus/qdbusmetaobject.cpp b/src/dbus/qdbusmetaobject.cpp index 6683505..df8bc1d 100644 --- a/src/dbus/qdbusmetaobject.cpp +++ b/src/dbus/qdbusmetaobject.cpp @@ -193,14 +193,19 @@ QDBusMetaObjectGenerator::findType(const QByteArray &signature, QByteArray typeName = annotations.value(annotationName).toLatin1(); // verify that it's a valid one - if (typeName.isEmpty()) - return result; // invalid - - type = QVariant::nameToType(typeName); - if (type == QVariant::UserType) - type = QMetaType::type(typeName); - if (type == QVariant::Invalid || signature != QDBusMetaType::typeToSignature(type)) - return result; // unknown type is invalid too + if (!typeName.isEmpty()) { + // type name found + type = QVariant::nameToType(typeName); + if (type == QVariant::UserType) + type = QMetaType::type(typeName); + } + + if (type == QVariant::Invalid || signature != QDBusMetaType::typeToSignature(type)) { + // type is still unknown or doesn't match back to the signature that it + // was expected to, so synthesize a fake type + type = QMetaType::VoidStar; + typeName = "QDBusRawType<0x" + signature.toHex() + ">*"; + } result.name = typeName; } else if (type == QVariant::Invalid) { diff --git a/src/dbus/qdbusxmlparser.cpp b/src/dbus/qdbusxmlparser.cpp index 1b99ced..3feedde 100644 --- a/src/dbus/qdbusxmlparser.cpp +++ b/src/dbus/qdbusxmlparser.cpp @@ -52,6 +52,13 @@ #ifndef QT_NO_DBUS +//#define QDBUS_PARSER_DEBUG +#ifdef QDBUS_PARSER_DEBUG +# define qDBusParserError qWarning +#else +# define qDBusParserError if (true) {} else qDebug +#endif + QT_BEGIN_NAMESPACE static QDBusIntrospection::Annotations @@ -69,8 +76,8 @@ parseAnnotations(const QDomElement& elem) value = ann.attribute(QLatin1String("value")); if (!QDBusUtil::isValidInterfaceName(name)) { - qWarning("Invalid D-BUS annotation '%s' found while parsing introspection", - qPrintable(name)); + qDBusParserError("Invalid D-BUS annotation '%s' found while parsing introspection", + qPrintable(name)); continue; } @@ -99,9 +106,8 @@ parseArgs(const QDomElement& elem, const QLatin1String& direction, bool acceptEm argData.name = arg.attribute(QLatin1String("name")); // can be empty argData.type = arg.attribute(QLatin1String("type")); if (!QDBusUtil::isValidSingleSignature(argData.type)) { - qWarning("Invalid D-BUS type signature '%s' found while parsing introspection", - qPrintable(argData.type)); - continue; + qDBusParserError("Invalid D-BUS type signature '%s' found while parsing introspection", + qPrintable(argData.type)); } retval << argData; @@ -141,8 +147,8 @@ QDBusXmlParser::interfaces() const if (iface.isNull()) continue; // for whatever reason if (!QDBusUtil::isValidInterfaceName(ifaceName)) { - qWarning("Invalid D-BUS interface name '%s' found while parsing introspection", - qPrintable(ifaceName)); + qDBusParserError("Invalid D-BUS interface name '%s' found while parsing introspection", + qPrintable(ifaceName)); continue; } @@ -166,8 +172,8 @@ QDBusXmlParser::interfaces() const if (method.isNull()) continue; if (!QDBusUtil::isValidMemberName(methodName)) { - qWarning("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", - qPrintable(methodName), qPrintable(ifaceName)); + qDBusParserError("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", + qPrintable(methodName), qPrintable(ifaceName)); continue; } @@ -192,8 +198,8 @@ QDBusXmlParser::interfaces() const if (signal.isNull()) continue; if (!QDBusUtil::isValidMemberName(signalName)) { - qWarning("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", - qPrintable(signalName), qPrintable(ifaceName)); + qDBusParserError("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", + qPrintable(signalName), qPrintable(ifaceName)); continue; } @@ -217,8 +223,8 @@ QDBusXmlParser::interfaces() const if (property.isNull()) continue; if (!QDBusUtil::isValidMemberName(propertyName)) { - qWarning("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", - qPrintable(propertyName), qPrintable(ifaceName)); + qDBusParserError("Invalid D-BUS member name '%s' found in interface '%s' while parsing introspection", + qPrintable(propertyName), qPrintable(ifaceName)); continue; } @@ -231,10 +237,9 @@ QDBusXmlParser::interfaces() const if (!QDBusUtil::isValidSingleSignature(propertyData.type)) { // cannot be! - qWarning("Invalid D-BUS type signature '%s' found in property '%s.%s' while parsing introspection", - qPrintable(propertyData.type), qPrintable(ifaceName), - qPrintable(propertyName)); - continue; + qDBusParserError("Invalid D-BUS type signature '%s' found in property '%s.%s' while parsing introspection", + qPrintable(propertyData.type), qPrintable(ifaceName), + qPrintable(propertyName)); } QString access = property.attribute(QLatin1String("access")); @@ -245,9 +250,9 @@ QDBusXmlParser::interfaces() const else if (access == QLatin1String("readwrite")) propertyData.access = QDBusIntrospection::Property::ReadWrite; else { - qWarning("Invalid D-BUS property access '%s' found in property '%s.%s' while parsing introspection", - qPrintable(access), qPrintable(ifaceName), - qPrintable(propertyName)); + qDBusParserError("Invalid D-BUS property access '%s' found in property '%s.%s' while parsing introspection", + qPrintable(access), qPrintable(ifaceName), + qPrintable(propertyName)); continue; // invalid one! } @@ -286,8 +291,8 @@ QDBusXmlParser::object() const if (obj.isNull()) continue; // for whatever reason if (!QDBusUtil::isValidObjectPath(m_path + QLatin1Char('/') + objName)) { - qWarning("Invalid D-BUS object path '%s/%s' found while parsing introspection", - qPrintable(m_path), qPrintable(objName)); + qDBusParserError("Invalid D-BUS object path '%s/%s' found while parsing introspection", + qPrintable(m_path), qPrintable(objName)); continue; } @@ -301,8 +306,8 @@ QDBusXmlParser::object() const if (iface.isNull()) continue; if (!QDBusUtil::isValidInterfaceName(ifaceName)) { - qWarning("Invalid D-BUS interface name '%s' found while parsing introspection", - qPrintable(ifaceName)); + qDBusParserError("Invalid D-BUS interface name '%s' found while parsing introspection", + qPrintable(ifaceName)); continue; } diff --git a/src/declarative/graphicsitems/qdeclarativeflickable.cpp b/src/declarative/graphicsitems/qdeclarativeflickable.cpp index 0faa296..1f1b39a 100644 --- a/src/declarative/graphicsitems/qdeclarativeflickable.cpp +++ b/src/declarative/graphicsitems/qdeclarativeflickable.cpp @@ -845,7 +845,8 @@ void QDeclarativeFlickable::mousePressEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeFlickable); if (d->interactive) { - d->handleMousePressEvent(event); + if (!d->pressed) + d->handleMousePressEvent(event); event->accept(); } else { QDeclarativeItem::mousePressEvent(event); @@ -910,11 +911,27 @@ void QDeclarativeFlickable::wheelEvent(QGraphicsSceneWheelEvent *event) } } +bool QDeclarativeFlickablePrivate::isOutermostPressDelay() const +{ + Q_Q(const QDeclarativeFlickable); + QDeclarativeItem *item = q->parentItem(); + while (item) { + QDeclarativeFlickable *flick = qobject_cast<QDeclarativeFlickable*>(item); + if (flick && flick->pressDelay() > 0 && flick->isInteractive()) + return false; + item = item->parentItem(); + } + + return true; +} + void QDeclarativeFlickablePrivate::captureDelayedPress(QGraphicsSceneMouseEvent *event) { Q_Q(QDeclarativeFlickable); if (!q->scene() || pressDelay <= 0) return; + if (!isOutermostPressDelay()) + return; delayedPressTarget = q->scene()->mouseGrabberItem(); delayedPressEvent = new QGraphicsSceneMouseEvent(event->type()); delayedPressEvent->setAccepted(false); @@ -970,9 +987,10 @@ void QDeclarativeFlickable::timerEvent(QTimerEvent *event) if (scene()->mouseGrabberItem() == d->delayedPressTarget) d->delayedPressTarget->ungrabMouse(); //Use the event handler that will take care of finding the proper item to propagate the event - QApplication::sendEvent(scene(), d->delayedPressEvent); + QApplication::postEvent(scene(), d->delayedPressEvent); + } else { + delete d->delayedPressEvent; } - delete d->delayedPressEvent; d->delayedPressEvent = 0; } } @@ -1343,6 +1361,22 @@ bool QDeclarativeFlickable::yflick() const return d->flickableDirection & QDeclarativeFlickable::VerticalFlick; } +bool QDeclarativeFlickable::sceneEvent(QEvent *event) +{ + bool rv = QDeclarativeItem::sceneEvent(event); + if (event->type() == QEvent::UngrabMouse) { + Q_D(QDeclarativeFlickable); + if (d->pressed) { + // if our mouse grab has been removed (probably by another Flickable), + // fix our state + d->pressed = false; + d->stealMouse = false; + setKeepMouseGrab(false); + } + } + return rv; +} + bool QDeclarativeFlickable::sendMouseEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeFlickable); @@ -1370,7 +1404,7 @@ bool QDeclarativeFlickable::sendMouseEvent(QGraphicsSceneMouseEvent *event) d->handleMouseMoveEvent(&mouseEvent); break; case QEvent::GraphicsSceneMousePress: - if (d->delayedPressEvent) + if (d->pressed) // we are already pressed - this is a delayed replay return false; d->handleMousePressEvent(&mouseEvent); @@ -1389,6 +1423,8 @@ bool QDeclarativeFlickable::sendMouseEvent(QGraphicsSceneMouseEvent *event) // We send the release scene()->sendEvent(s->mouseGrabberItem(), event); // And the event has been consumed + d->stealMouse = false; + d->pressed = false; return true; } d->handleMouseReleaseEvent(&mouseEvent); @@ -1411,6 +1447,7 @@ bool QDeclarativeFlickable::sendMouseEvent(QGraphicsSceneMouseEvent *event) d->stealMouse = false; d->pressed = false; } + return false; } @@ -1509,6 +1546,9 @@ bool QDeclarativeFlickable::isFlickingVertically() const If the flickable is dragged/flicked before the delay times out the press event will not be delivered. If the button is released within the timeout, both the press and release will be delivered. + + Note that for nested Flickables with pressDelay set, the pressDelay of + inner Flickables is overridden by the outermost Flickable. */ int QDeclarativeFlickable::pressDelay() const { diff --git a/src/declarative/graphicsitems/qdeclarativeflickable_p.h b/src/declarative/graphicsitems/qdeclarativeflickable_p.h index 4fde1d5..a14cc1c 100644 --- a/src/declarative/graphicsitems/qdeclarativeflickable_p.h +++ b/src/declarative/graphicsitems/qdeclarativeflickable_p.h @@ -204,6 +204,7 @@ protected: virtual void viewportMoved(); virtual void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry); + bool sceneEvent(QEvent *event); bool sendMouseEvent(QGraphicsSceneMouseEvent *event); bool xflick() const; diff --git a/src/declarative/graphicsitems/qdeclarativeflickable_p_p.h b/src/declarative/graphicsitems/qdeclarativeflickable_p_p.h index 5ad6ff6..1b6081c 100644 --- a/src/declarative/graphicsitems/qdeclarativeflickable_p_p.h +++ b/src/declarative/graphicsitems/qdeclarativeflickable_p_p.h @@ -118,6 +118,7 @@ public: void updateBeginningEnd(); + bool isOutermostPressDelay() const; void captureDelayedPress(QGraphicsSceneMouseEvent *event); void clearDelayedPress(); diff --git a/src/declarative/graphicsitems/qdeclarativegridview.cpp b/src/declarative/graphicsitems/qdeclarativegridview.cpp index 694130b..6d2285d 100644 --- a/src/declarative/graphicsitems/qdeclarativegridview.cpp +++ b/src/declarative/graphicsitems/qdeclarativegridview.cpp @@ -82,7 +82,7 @@ public: item->setPos(QPointF(row, col)); } } - bool contains(int x, int y) const { + bool contains(qreal x, qreal y) const { return (x >= item->x() && x < item->x() + view->cellWidth() && y >= item->y() && y < item->y() + view->cellHeight()); } @@ -2294,7 +2294,7 @@ void QDeclarativeGridView::positionViewAtEnd() \bold Note: methods should only be called after the Component has completed. */ -int QDeclarativeGridView::indexAt(int x, int y) const +int QDeclarativeGridView::indexAt(qreal x, qreal y) const { Q_D(const QDeclarativeGridView); for (int i = 0; i < d->visibleItems.count(); ++i) { diff --git a/src/declarative/graphicsitems/qdeclarativegridview_p.h b/src/declarative/graphicsitems/qdeclarativegridview_p.h index 248b9ef..e68a9ba 100644 --- a/src/declarative/graphicsitems/qdeclarativegridview_p.h +++ b/src/declarative/graphicsitems/qdeclarativegridview_p.h @@ -158,7 +158,7 @@ public: enum PositionMode { Beginning, Center, End, Visible, Contain }; Q_INVOKABLE void positionViewAtIndex(int index, int mode); - Q_INVOKABLE int indexAt(int x, int y) const; + Q_INVOKABLE int indexAt(qreal x, qreal y) const; Q_INVOKABLE Q_REVISION(1) void positionViewAtBeginning(); Q_INVOKABLE Q_REVISION(1) void positionViewAtEnd(); diff --git a/src/declarative/graphicsitems/qdeclarativeitemsmodule.cpp b/src/declarative/graphicsitems/qdeclarativeitemsmodule.cpp index bc4a2d0..3c8f64e 100644 --- a/src/declarative/graphicsitems/qdeclarativeitemsmodule.cpp +++ b/src/declarative/graphicsitems/qdeclarativeitemsmodule.cpp @@ -180,6 +180,7 @@ void QDeclarativeItemModule::defineModule() qmlRegisterType<QDeclarativePinch>("QtQuick",1,1,"Pinch"); qmlRegisterType<QDeclarativePinchEvent>(); qmlRegisterType<QDeclarativeItem,1>("QtQuick",1,1,"Item"); + qmlRegisterType<QDeclarativeMouseArea,1>("QtQuick",1,1,"MouseArea"); qmlRegisterType<QDeclarativeFlickable,1>("QtQuick",1,1,"Flickable"); qmlRegisterType<QDeclarativeListView,1>("QtQuick",1,1,"ListView"); qmlRegisterType<QDeclarativeGridView,1>("QtQuick",1,1,"GridView"); diff --git a/src/declarative/graphicsitems/qdeclarativelistview.cpp b/src/declarative/graphicsitems/qdeclarativelistview.cpp index a60a4aa..91de5a6 100644 --- a/src/declarative/graphicsitems/qdeclarativelistview.cpp +++ b/src/declarative/graphicsitems/qdeclarativelistview.cpp @@ -148,7 +148,7 @@ public: else item->setWidth(size); } - bool contains(int x, int y) const { + bool contains(qreal x, qreal y) const { return (x >= item->x() && x < item->x() + item->width() && y >= item->y() && y < item->y() + item->height()); } @@ -2732,7 +2732,7 @@ void QDeclarativeListView::positionViewAtEnd() \bold Note: methods should only be called after the Component has completed. */ -int QDeclarativeListView::indexAt(int x, int y) const +int QDeclarativeListView::indexAt(qreal x, qreal y) const { Q_D(const QDeclarativeListView); for (int i = 0; i < d->visibleItems.count(); ++i) { diff --git a/src/declarative/graphicsitems/qdeclarativelistview_p.h b/src/declarative/graphicsitems/qdeclarativelistview_p.h index 10fbf10..265f4bd 100644 --- a/src/declarative/graphicsitems/qdeclarativelistview_p.h +++ b/src/declarative/graphicsitems/qdeclarativelistview_p.h @@ -208,7 +208,7 @@ public: enum PositionMode { Beginning, Center, End, Visible, Contain }; Q_INVOKABLE void positionViewAtIndex(int index, int mode); - Q_INVOKABLE int indexAt(int x, int y) const; + Q_INVOKABLE int indexAt(qreal x, qreal y) const; Q_INVOKABLE Q_REVISION(1) void positionViewAtBeginning(); Q_INVOKABLE Q_REVISION(1) void positionViewAtEnd(); diff --git a/src/declarative/graphicsitems/qdeclarativemousearea.cpp b/src/declarative/graphicsitems/qdeclarativemousearea.cpp index 5b73a29..da11b00 100644 --- a/src/declarative/graphicsitems/qdeclarativemousearea.cpp +++ b/src/declarative/graphicsitems/qdeclarativemousearea.cpp @@ -416,6 +416,40 @@ void QDeclarativeMouseArea::setEnabled(bool a) emit enabledChanged(); } } + +/*! + \qmlproperty bool MouseArea::preventStealing + \since Quick 1.1 + This property holds whether the mouse events may be stolen from this + MouseArea. + + If a MouseArea is placed within an item that filters child mouse + events, such as Flickable, the mouse + events may be stolen from the MouseArea if a gesture is recognized + by the parent element, e.g. a flick gesture. If preventStealing is + set to true, no element will steal the mouse events. + + Note that setting preventStealing to true once an element has started + stealing events will have no effect until the next press event. + + By default this property is false. +*/ +bool QDeclarativeMouseArea::preventStealing() const +{ + Q_D(const QDeclarativeMouseArea); + return d->preventStealing; +} + +void QDeclarativeMouseArea::setPreventStealing(bool prevent) +{ + Q_D(QDeclarativeMouseArea); + if (prevent != d->preventStealing) { + d->preventStealing = prevent; + setKeepMouseGrab(d->preventStealing && d->absorb); + emit preventStealingChanged(); + } +} + /*! \qmlproperty MouseButtons MouseArea::pressedButtons This property holds the mouse buttons currently pressed. @@ -443,7 +477,7 @@ void QDeclarativeMouseArea::mousePressEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeMouseArea); d->moved = false; - d->stealMouse = false; + d->stealMouse = d->preventStealing; if (!d->absorb) QDeclarativeItem::mousePressEvent(event); else { @@ -460,7 +494,7 @@ void QDeclarativeMouseArea::mousePressEvent(QGraphicsSceneMouseEvent *event) // we should only start timer if pressAndHold is connected to. if (d->isPressAndHoldConnected()) d->pressAndHoldTimer.start(PressAndHoldDelay, this); - setKeepMouseGrab(false); + setKeepMouseGrab(d->stealMouse); event->setAccepted(setPressed(true)); } } diff --git a/src/declarative/graphicsitems/qdeclarativemousearea_p.h b/src/declarative/graphicsitems/qdeclarativemousearea_p.h index 937ac78..985f27e 100644 --- a/src/declarative/graphicsitems/qdeclarativemousearea_p.h +++ b/src/declarative/graphicsitems/qdeclarativemousearea_p.h @@ -129,6 +129,7 @@ class Q_AUTOTEST_EXPORT QDeclarativeMouseArea : public QDeclarativeItem Q_PROPERTY(Qt::MouseButtons acceptedButtons READ acceptedButtons WRITE setAcceptedButtons NOTIFY acceptedButtonsChanged) Q_PROPERTY(bool hoverEnabled READ hoverEnabled WRITE setHoverEnabled NOTIFY hoverEnabledChanged) Q_PROPERTY(QDeclarativeDrag *drag READ drag CONSTANT) //### add flicking to QDeclarativeDrag or add a QDeclarativeFlick ??? + Q_PROPERTY(bool preventStealing READ preventStealing WRITE setPreventStealing NOTIFY preventStealingChanged REVISION 1) public: QDeclarativeMouseArea(QDeclarativeItem *parent=0); @@ -153,6 +154,9 @@ public: QDeclarativeDrag *drag(); + bool preventStealing() const; + void setPreventStealing(bool prevent); + Q_SIGNALS: void hoveredChanged(); void pressedChanged(); @@ -161,6 +165,7 @@ Q_SIGNALS: void hoverEnabledChanged(); void positionChanged(QDeclarativeMouseEvent *mouse); void mousePositionChanged(QDeclarativeMouseEvent *mouse); + Q_REVISION(1) void preventStealingChanged(); void pressed(QDeclarativeMouseEvent *mouse); void pressAndHold(QDeclarativeMouseEvent *mouse); diff --git a/src/declarative/graphicsitems/qdeclarativemousearea_p_p.h b/src/declarative/graphicsitems/qdeclarativemousearea_p_p.h index 2a327af..67694fb 100644 --- a/src/declarative/graphicsitems/qdeclarativemousearea_p_p.h +++ b/src/declarative/graphicsitems/qdeclarativemousearea_p_p.h @@ -68,7 +68,7 @@ class QDeclarativeMouseAreaPrivate : public QDeclarativeItemPrivate public: QDeclarativeMouseAreaPrivate() : absorb(true), hovered(false), pressed(false), longPress(false), - moved(false), stealMouse(false), doubleClick(false), drag(0) + moved(false), stealMouse(false), doubleClick(false), preventStealing(false), drag(0) { } @@ -110,6 +110,7 @@ public: bool dragY : 1; bool stealMouse : 1; bool doubleClick : 1; + bool preventStealing : 1; QDeclarativeDrag *drag; QPointF startScene; qreal startX; diff --git a/src/declarative/graphicsitems/qdeclarativetextedit.cpp b/src/declarative/graphicsitems/qdeclarativetextedit.cpp index e2f6265..7f383a6 100644 --- a/src/declarative/graphicsitems/qdeclarativetextedit.cpp +++ b/src/declarative/graphicsitems/qdeclarativetextedit.cpp @@ -977,6 +977,10 @@ void QDeclarativeTextEdit::setSelectByMouse(bool on) if (d->selectByMouse != on) { d->selectByMouse = on; setKeepMouseGrab(on); + if (on) + setTextInteractionFlags(d->control->textInteractionFlags() | Qt::TextSelectableByMouse); + else + setTextInteractionFlags(d->control->textInteractionFlags() & ~Qt::TextSelectableByMouse); emit selectByMouseChanged(on); } } @@ -1029,11 +1033,10 @@ void QDeclarativeTextEdit::setReadOnly(bool r) setFlag(QGraphicsItem::ItemAcceptsInputMethod, !r); Qt::TextInteractionFlags flags = Qt::LinksAccessibleByMouse; - if (r) { + if (d->selectByMouse) flags = flags | Qt::TextSelectableByMouse; - } else { - flags = flags | Qt::TextEditorInteraction; - } + if (!r) + flags = flags | Qt::TextSelectableByKeyboard | Qt::TextEditable; d->control->setTextInteractionFlags(flags); if (!r) d->control->moveCursor(QTextCursor::End); @@ -1125,7 +1128,7 @@ void QDeclarativeTextEdit::keyReleaseEvent(QKeyEvent *event) void QDeclarativeTextEditPrivate::focusChanged(bool hasFocus) { Q_Q(QDeclarativeTextEdit); - q->setCursorVisible(hasFocus); + q->setCursorVisible(hasFocus && scene && scene->hasFocus()); QDeclarativeItemPrivate::focusChanged(hasFocus); } @@ -1251,8 +1254,8 @@ void QDeclarativeTextEdit::mousePressEvent(QGraphicsSceneMouseEvent *event) } } } - if (event->type() != QEvent::GraphicsSceneMouseDoubleClick || d->selectByMouse) - d->control->processEvent(event, QPointF(0, -d->yoff)); + + d->control->processEvent(event, QPointF(0, -d->yoff)); if (!event->isAccepted()) QDeclarativePaintedItem::mousePressEvent(event); } @@ -1287,13 +1290,11 @@ Handles the given mouse \a event. void QDeclarativeTextEdit::mouseDoubleClickEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextEdit); - if (d->selectByMouse) { - d->control->processEvent(event, QPointF(0, -d->yoff)); - if (!event->isAccepted()) - QDeclarativePaintedItem::mouseDoubleClickEvent(event); - } else { + + d->control->processEvent(event, QPointF(0, -d->yoff)); + if (!event->isAccepted()) QDeclarativePaintedItem::mouseDoubleClickEvent(event); - } + } /*! @@ -1303,14 +1304,9 @@ Handles the given mouse \a event. void QDeclarativeTextEdit::mouseMoveEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextEdit); - if (d->selectByMouse) { - d->control->processEvent(event, QPointF(0, -d->yoff)); - if (!event->isAccepted()) - QDeclarativePaintedItem::mouseMoveEvent(event); - event->setAccepted(true); - } else { + d->control->processEvent(event, QPointF(0, -d->yoff)); + if (!event->isAccepted()) QDeclarativePaintedItem::mouseMoveEvent(event); - } } /*! @@ -1409,7 +1405,7 @@ void QDeclarativeTextEditPrivate::init() control = new QTextControl(q); control->setIgnoreUnusedNavigationEvents(true); - control->setTextInteractionFlags(control->textInteractionFlags() | Qt::LinksAccessibleByMouse); + control->setTextInteractionFlags(Qt::LinksAccessibleByMouse | Qt::TextSelectableByKeyboard | Qt::TextEditable); control->setDragEnabled(false); // QTextControl follows the default text color diff --git a/src/declarative/graphicsitems/qdeclarativetextinput.cpp b/src/declarative/graphicsitems/qdeclarativetextinput.cpp index 3c95ab8..78f34db 100644 --- a/src/declarative/graphicsitems/qdeclarativetextinput.cpp +++ b/src/declarative/graphicsitems/qdeclarativetextinput.cpp @@ -51,6 +51,7 @@ #include <QFontMetrics> #include <QPainter> #include <QTextBoundaryFinder> +#include <QInputContext> #include <qstyle.h> #ifndef QT_NO_LINEEDIT @@ -947,7 +948,7 @@ void QDeclarativeTextInputPrivate::focusChanged(bool hasFocus) { Q_Q(QDeclarativeTextInput); focused = hasFocus; - q->setCursorVisible(hasFocus); + q->setCursorVisible(hasFocus && scene && scene->hasFocus()); if(q->echoMode() == QDeclarativeTextInput::PasswordEchoOnEdit && !hasFocus) control->updatePasswordEchoEditing(false);//QLineControl sets it on key events, but doesn't deal with focus events if (!hasFocus) @@ -1002,6 +1003,8 @@ Handles the given mouse \a event. void QDeclarativeTextInput::mouseDoubleClickEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextInput); + if (d->sendMouseEventToInputContext(event, QEvent::MouseButtonDblClick)) + return; if (d->selectByMouse) { int cursor = d->xToPos(event->pos().x()); d->control->selectWordAtPos(cursor); @@ -1014,6 +1017,8 @@ void QDeclarativeTextInput::mouseDoubleClickEvent(QGraphicsSceneMouseEvent *even void QDeclarativeTextInput::mousePressEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextInput); + if (d->sendMouseEventToInputContext(event, QEvent::MouseButtonPress)) + return; if(d->focusOnPress){ bool hadActiveFocus = hasActiveFocus(); forceActiveFocus(); @@ -1041,6 +1046,8 @@ void QDeclarativeTextInput::mousePressEvent(QGraphicsSceneMouseEvent *event) void QDeclarativeTextInput::mouseMoveEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextInput); + if (d->sendMouseEventToInputContext(event, QEvent::MouseMove)) + event->setAccepted(true); if (d->selectByMouse) { if (qAbs(int(event->pos().x() - d->pressPos.x())) > QApplication::startDragDistance()) setKeepMouseGrab(true); @@ -1058,6 +1065,8 @@ Handles the given mouse \a event. void QDeclarativeTextInput::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) { Q_D(QDeclarativeTextInput); + if (d->sendMouseEventToInputContext(event, QEvent::MouseButtonRelease)) + return; if (d->selectByMouse) setKeepMouseGrab(false); if (!d->showInputPanelOnFocus) { // input panel on click @@ -1075,6 +1084,44 @@ void QDeclarativeTextInput::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) QDeclarativePaintedItem::mouseReleaseEvent(event); } +bool QDeclarativeTextInputPrivate::sendMouseEventToInputContext( + QGraphicsSceneMouseEvent *event, QEvent::Type eventType) +{ +#if !defined QT_NO_IM + if (event->widget() && control->composeMode()) { + int tmp_cursor = xToPos(event->pos().x()); + int mousePos = tmp_cursor - control->cursor(); + if (mousePos < 0 || mousePos > control->preeditAreaText().length()) { + mousePos = -1; + // don't send move events outside the preedit area + if (eventType == QEvent::MouseMove) + return true; + } + + QInputContext *qic = event->widget()->inputContext(); + if (qic) { + QMouseEvent mouseEvent( + eventType, + event->widget()->mapFromGlobal(event->screenPos()), + event->screenPos(), + event->button(), + event->buttons(), + event->modifiers()); + // may be causing reset() in some input methods + qic->mouseHandler(mousePos, &mouseEvent); + event->setAccepted(mouseEvent.isAccepted()); + } + if (!control->preeditAreaText().isEmpty()) + return true; + } +#else + Q_UNUSED(event); + Q_UNUSED(eventType) +#endif + + return false; +} + bool QDeclarativeTextInput::sceneEvent(QEvent *event) { bool rv = QDeclarativeItem::sceneEvent(event); @@ -1662,6 +1709,8 @@ void QDeclarativeTextInputPrivate::init() q->connect(QApplication::clipboard(), SIGNAL(dataChanged()), q, SLOT(q_canPasteChanged())); #endif // QT_NO_CLIPBOARD + q->connect(control, SIGNAL(updateMicroFocus()), + q, SLOT(updateMicroFocus())); q->updateSize(); oldValidity = control->hasAcceptableInput(); lastSelectionStart = 0; diff --git a/src/declarative/graphicsitems/qdeclarativetextinput_p_p.h b/src/declarative/graphicsitems/qdeclarativetextinput_p_p.h index f7446b4..ab2838b 100644 --- a/src/declarative/graphicsitems/qdeclarativetextinput_p_p.h +++ b/src/declarative/graphicsitems/qdeclarativetextinput_p_p.h @@ -104,6 +104,7 @@ public: void focusChanged(bool hasFocus); void updateHorizontalScroll(); int calculateTextWidth(); + bool sendMouseEventToInputContext(QGraphicsSceneMouseEvent *event, QEvent::Type eventType); QLineControl* control; diff --git a/src/declarative/qml/qdeclarativecomponent.cpp b/src/declarative/qml/qdeclarativecomponent.cpp index 5840f70..cf40182 100644 --- a/src/declarative/qml/qdeclarativecomponent.cpp +++ b/src/declarative/qml/qdeclarativecomponent.cpp @@ -870,7 +870,6 @@ QObject * QDeclarativeComponentPrivate::begin(QDeclarativeContextData *parentCon state->bindValues = enginePriv->bindValues; state->parserStatus = enginePriv->parserStatus; - state->finalizedParserStatus = enginePriv->finalizedParserStatus; state->componentAttached = enginePriv->componentAttached; if (state->componentAttached) state->componentAttached->prev = &state->componentAttached; @@ -878,7 +877,6 @@ QObject * QDeclarativeComponentPrivate::begin(QDeclarativeContextData *parentCon enginePriv->componentAttached = 0; enginePriv->bindValues.clear(); enginePriv->parserStatus.clear(); - enginePriv->finalizedParserStatus.clear(); state->completePending = true; enginePriv->inProgressCreations++; } @@ -909,7 +907,6 @@ void QDeclarativeComponentPrivate::beginDeferred(QDeclarativeEnginePrivate *engi state->bindValues = enginePriv->bindValues; state->parserStatus = enginePriv->parserStatus; - state->finalizedParserStatus = enginePriv->finalizedParserStatus; state->componentAttached = enginePriv->componentAttached; if (state->componentAttached) state->componentAttached->prev = &state->componentAttached; @@ -917,7 +914,6 @@ void QDeclarativeComponentPrivate::beginDeferred(QDeclarativeEnginePrivate *engi enginePriv->componentAttached = 0; enginePriv->bindValues.clear(); enginePriv->parserStatus.clear(); - enginePriv->finalizedParserStatus.clear(); state->completePending = true; enginePriv->inProgressCreations++; } @@ -955,14 +951,17 @@ void QDeclarativeComponentPrivate::complete(QDeclarativeEnginePrivate *enginePri QDeclarativeEnginePrivate::clear(ps); } - for (int ii = 0; ii < state->finalizedParserStatus.count(); ++ii) { - QPair<QDeclarativeGuard<QObject>, int> status = state->finalizedParserStatus.at(ii); - QObject *obj = status.first; - if (obj) { - void *args[] = { 0 }; - QMetaObject::metacall(obj, QMetaObject::InvokeMetaMethod, - status.second, args); + if (1 == enginePriv->inProgressCreations) { + for (int ii = 0; ii < enginePriv->finalizedParserStatus.count(); ++ii) { + QPair<QDeclarativeGuard<QObject>, int> status = enginePriv->finalizedParserStatus.at(ii); + QObject *obj = status.first; + if (obj) { + void *args[] = { 0 }; + QMetaObject::metacall(obj, QMetaObject::InvokeMetaMethod, + status.second, args); + } } + enginePriv->finalizedParserStatus.clear(); } while (state->componentAttached) { @@ -977,7 +976,6 @@ void QDeclarativeComponentPrivate::complete(QDeclarativeEnginePrivate *enginePri state->bindValues.clear(); state->parserStatus.clear(); - state->finalizedParserStatus.clear(); state->completePending = false; enginePriv->inProgressCreations--; @@ -987,7 +985,6 @@ void QDeclarativeComponentPrivate::complete(QDeclarativeEnginePrivate *enginePri enginePriv->erroredBindings->removeError(); } } - } } diff --git a/src/declarative/qml/qdeclarativecomponent_p.h b/src/declarative/qml/qdeclarativecomponent_p.h index f8bec2b..020c5e0 100644 --- a/src/declarative/qml/qdeclarativecomponent_p.h +++ b/src/declarative/qml/qdeclarativecomponent_p.h @@ -101,7 +101,6 @@ public: ConstructionState() : componentAttached(0), completePending(false) {} QList<QDeclarativeEnginePrivate::SimpleList<QDeclarativeAbstractBinding> > bindValues; QList<QDeclarativeEnginePrivate::SimpleList<QDeclarativeParserStatus> > parserStatus; - QList<QPair<QDeclarativeGuard<QObject>, int> > finalizedParserStatus; QDeclarativeComponentAttached *componentAttached; QList<QDeclarativeError> errors; bool completePending; diff --git a/src/declarative/qml/qdeclarativeenginedebug.cpp b/src/declarative/qml/qdeclarativeenginedebug.cpp index 8c7f3ad..31fd516 100644 --- a/src/declarative/qml/qdeclarativeenginedebug.cpp +++ b/src/declarative/qml/qdeclarativeenginedebug.cpp @@ -167,17 +167,19 @@ QDeclarativeEngineDebugServer::propertyData(QObject *obj, int propIdx) QVariant QDeclarativeEngineDebugServer::valueContents(const QVariant &value) const { int userType = value.userType(); - if (QDeclarativeValueTypeFactory::isValueType(userType)) - return value; - /* - if (QDeclarativeMetaType::isList(userType)) { - int count = QDeclarativeMetaType::listCount(value); + if (value.type() == QVariant::List) { QVariantList contents; - for (int i=0; i<count; i++) - contents << valueContents(QDeclarativeMetaType::listAt(value, i)); + QVariantList list = value.toList(); + int count = list.size(); + for (int i = 0; i < count; i++) + contents << valueContents(list.at(i)); return contents; - } else */ + } + + if (QDeclarativeValueTypeFactory::isValueType(userType)) + return value; + if (QDeclarativeMetaType::isQObject(userType)) { QObject *o = QDeclarativeMetaType::toQObject(value); if (o) { diff --git a/src/declarative/qml/qdeclarativelist.cpp b/src/declarative/qml/qdeclarativelist.cpp index 9598d98..346fee5 100644 --- a/src/declarative/qml/qdeclarativelist.cpp +++ b/src/declarative/qml/qdeclarativelist.cpp @@ -88,6 +88,7 @@ void QDeclarativeListReferencePrivate::release() /*! \class QDeclarativeListReference \since 4.7 +\module QtDeclarative \brief The QDeclarativeListReference class allows the manipulation of QDeclarativeListProperty properties. QDeclarativeListReference allows C++ programs to read from, and assign values to a QML list property in a diff --git a/src/declarative/qml/qdeclarativeobjectscriptclass.cpp b/src/declarative/qml/qdeclarativeobjectscriptclass.cpp index 2aa2059..dc3ecca 100644 --- a/src/declarative/qml/qdeclarativeobjectscriptclass.cpp +++ b/src/declarative/qml/qdeclarativeobjectscriptclass.cpp @@ -368,7 +368,7 @@ void QDeclarativeObjectScriptClass::setProperty(QObject *obj, newBinding = new QDeclarativeBinding(value, obj, evalContext); newBinding->setSourceLocation(ctxtInfo.fileName(), ctxtInfo.functionStartLineNumber()); newBinding->setTarget(QDeclarativePropertyPrivate::restore(*lastData, valueTypeData, obj, evalContext)); - if (newBinding->expression().contains("this")) + if (newBinding->expression().contains(QLatin1String("this"))) newBinding->setEvaluateFlags(newBinding->evaluateFlags() | QDeclarativeBinding::RequiresThisObject); } diff --git a/src/declarative/qml/qdeclarativeproperty.cpp b/src/declarative/qml/qdeclarativeproperty.cpp index 61e3002..0dd0edb 100644 --- a/src/declarative/qml/qdeclarativeproperty.cpp +++ b/src/declarative/qml/qdeclarativeproperty.cpp @@ -427,7 +427,7 @@ bool QDeclarativeProperty::operator==(const QDeclarativeProperty &other) const */ int QDeclarativeProperty::propertyType() const { - return d ? d->propertyType() : QVariant::Invalid; + return d ? d->propertyType() : int(QVariant::Invalid); } bool QDeclarativePropertyPrivate::isValueType() const diff --git a/src/declarative/qml/qdeclarativevaluetypescriptclass.cpp b/src/declarative/qml/qdeclarativevaluetypescriptclass.cpp index 200cc1c..4c312b5 100644 --- a/src/declarative/qml/qdeclarativevaluetypescriptclass.cpp +++ b/src/declarative/qml/qdeclarativevaluetypescriptclass.cpp @@ -184,7 +184,7 @@ void QDeclarativeValueTypeScriptClass::setProperty(Object *obj, const Identifier newBinding->setSourceLocation(ctxtInfo.fileName(), ctxtInfo.functionStartLineNumber()); QDeclarativeProperty prop = QDeclarativePropertyPrivate::restore(cacheData, valueTypeData, ref->object, ctxt); newBinding->setTarget(prop); - if (newBinding->expression().contains("this")) + if (newBinding->expression().contains(QLatin1String("this"))) newBinding->setEvaluateFlags(newBinding->evaluateFlags() | QDeclarativeBinding::RequiresThisObject); } diff --git a/src/declarative/qml/qdeclarativevme.cpp b/src/declarative/qml/qdeclarativevme.cpp index 366c64b..2d551f2 100644 --- a/src/declarative/qml/qdeclarativevme.cpp +++ b/src/declarative/qml/qdeclarativevme.cpp @@ -938,7 +938,6 @@ QObject *QDeclarativeVME::run(QDeclarativeVMEStack<QObject *> &stack, QDeclarativeEnginePrivate::clear(bindValues); QDeclarativeEnginePrivate::clear(parserStatus); - ep->finalizedParserStatus.clear(); return 0; } diff --git a/src/declarative/util/qdeclarativeanimation.cpp b/src/declarative/util/qdeclarativeanimation.cpp index eaf0cfa..dc6d524 100644 --- a/src/declarative/util/qdeclarativeanimation.cpp +++ b/src/declarative/util/qdeclarativeanimation.cpp @@ -182,12 +182,11 @@ void QDeclarativeAbstractAnimation::setRunning(bool r) { Q_D(QDeclarativeAbstractAnimation); if (!d->componentComplete) { - if (d->running && r == d->running) //don't re-register - return; d->running = r; if (r == false) d->avoidPropertyValueSourceStart = true; - else { + else if (!d->registered) { + d->registered = true; QDeclarativeEnginePrivate *engPriv = QDeclarativeEnginePrivate::get(qmlEngine(this)); engPriv->registerFinalizedParserStatusObject(this, this->metaObject()->indexOfSlot("componentFinalized()")); } @@ -204,6 +203,7 @@ void QDeclarativeAbstractAnimation::setRunning(bool r) d->running = r; if (d->running) { + bool supressStart = false; if (d->alwaysRunToEnd && d->loopCount != 1 && qtAnimation()->state() == QAbstractAnimation::Running) { //we've restarted before the final loop finished; restore proper loop count @@ -211,6 +211,7 @@ void QDeclarativeAbstractAnimation::setRunning(bool r) qtAnimation()->setLoopCount(d->loopCount); else qtAnimation()->setLoopCount(qtAnimation()->currentLoop() + d->loopCount); + supressStart = true; //we want the animation to continue, rather than restart } if (!d->connectedTimeLine) { @@ -218,7 +219,8 @@ void QDeclarativeAbstractAnimation::setRunning(bool r) this, SLOT(timelineComplete())); d->connectedTimeLine = true; } - d->commence(); + if (!supressStart) + d->commence(); emit started(); } else { if (d->alwaysRunToEnd) { diff --git a/src/declarative/util/qdeclarativeanimation_p_p.h b/src/declarative/util/qdeclarativeanimation_p_p.h index 15bda3c..048ecb1 100644 --- a/src/declarative/util/qdeclarativeanimation_p_p.h +++ b/src/declarative/util/qdeclarativeanimation_p_p.h @@ -210,7 +210,7 @@ public: : running(false), paused(false), alwaysRunToEnd(false), connectedTimeLine(false), componentComplete(true), avoidPropertyValueSourceStart(false), disableUserControl(false), - loopCount(1), group(0) {} + registered(false), loopCount(1), group(0) {} bool running:1; bool paused:1; @@ -219,6 +219,7 @@ public: bool componentComplete:1; bool avoidPropertyValueSourceStart:1; bool disableUserControl:1; + bool registered:1; int loopCount; diff --git a/src/declarative/util/qdeclarativepropertychanges.cpp b/src/declarative/util/qdeclarativepropertychanges.cpp index ccd122e..9bcb263 100644 --- a/src/declarative/util/qdeclarativepropertychanges.cpp +++ b/src/declarative/util/qdeclarativepropertychanges.cpp @@ -281,7 +281,7 @@ QDeclarativePropertyChangesParser::compile(const QList<QDeclarativeCustomParserP QDeclarativeParser::Variant v = qvariant_cast<QDeclarativeParser::Variant>(data.at(ii).second); QVariant var; bool isScript = v.isScript(); - QDeclarativeBinding::Identifier id; + QDeclarativeBinding::Identifier id = 0; switch(v.type()) { case QDeclarativeParser::Variant::Boolean: var = QVariant(v.asBoolean()); diff --git a/src/declarative/util/qdeclarativespringanimation.cpp b/src/declarative/util/qdeclarativespringanimation.cpp index ec2b083..1212a1c 100644 --- a/src/declarative/util/qdeclarativespringanimation.cpp +++ b/src/declarative/util/qdeclarativespringanimation.cpp @@ -236,7 +236,7 @@ void QDeclarativeSpringAnimationPrivate::updateMode() /*! \qmlclass SpringAnimation QDeclarativeSpringAnimation \ingroup qml-animation-transition - \inherits Animation + \inherits NumberAnimation \since 4.7 \brief The SpringAnimation element allows a property to track a value in a spring-like motion. diff --git a/src/declarative/util/qdeclarativexmllistmodel.cpp b/src/declarative/util/qdeclarativexmllistmodel.cpp index d691f94..d5c7d1b 100644 --- a/src/declarative/util/qdeclarativexmllistmodel.cpp +++ b/src/declarative/util/qdeclarativexmllistmodel.cpp @@ -46,11 +46,9 @@ #include <QDebug> #include <QStringList> -#include <QQueue> +#include <QMap> #include <QApplication> #include <QThread> -#include <QMutex> -#include <QWaitCondition> #include <QXmlQuery> #include <QXmlResultItems> #include <QXmlNodeModelIndex> @@ -58,6 +56,7 @@ #include <QNetworkRequest> #include <QNetworkReply> #include <QTimer> +#include <QMutex> #include <private/qobject_p.h> @@ -147,39 +146,32 @@ struct XmlQueryJob QStringList keyRoleResultsCache; }; -class QDeclarativeXmlQuery : public QThread +class QDeclarativeXmlQuery : public QObject { Q_OBJECT public: QDeclarativeXmlQuery(QObject *parent=0) - : QThread(parent), m_quit(false), m_abortQueryId(-1), m_queryIds(XMLLISTMODEL_CLEAR_ID + 1) { + : QObject(parent), m_queryIds(XMLLISTMODEL_CLEAR_ID + 1) { qRegisterMetaType<QDeclarativeXmlQueryResult>("QDeclarativeXmlQueryResult"); - m_currentJob.queryId = -1; + moveToThread(&m_thread); + m_thread.start(QThread::IdlePriority); } ~QDeclarativeXmlQuery() { - m_mutex.lock(); - m_quit = true; - m_condition.wakeOne(); - m_mutex.unlock(); - - wait(); + if(m_thread.isRunning()) { + m_thread.quit(); + m_thread.wait(); + } } void abort(int id) { - QMutexLocker locker(&m_mutex); - QQueue<XmlQueryJob>::iterator it; - for (it = m_jobs.begin(); it != m_jobs.end(); ++it) { - if ((*it).queryId == id) { - m_jobs.erase(it); - return; - } + QMutexLocker ml(&m_mutex); + if (id != -1) { + m_jobs.remove(id); } - m_abortQueryId = id; } - int doQuery(QString query, QString namespaces, QByteArray data, QList<QDeclarativeXmlListModelRole *> *roleObjects, QStringList keyRoleResultsCache) { - QMutexLocker locker(&m_mutex); + int doQuery(QString query, QString namespaces, QByteArray data, QList<QDeclarativeXmlListModelRole *>* roleObjects, QStringList keyRoleResultsCache) { XmlQueryJob job; job.queryId = m_queryIds; @@ -198,69 +190,69 @@ public: if (roleObjects->at(i)->isKey()) job.keyRoleQueries << job.roleQueries.last(); } - m_jobs.enqueue(job); - m_queryIds++; - if (!isRunning()) - start(QThread::IdlePriority); - else - m_condition.wakeOne(); + { + QMutexLocker ml(&m_mutex); + m_jobs.insert(m_queryIds, job); + m_queryIds++; + if (m_queryIds <= 0) + m_queryIds = 1; + } + + QMetaObject::invokeMethod(this, "processQuery", Qt::QueuedConnection, Q_ARG(int, job.queryId)); return job.queryId; } +private slots: + void processQuery(int queryId) { + XmlQueryJob job; + + { + QMutexLocker ml(&m_mutex); + if (!m_jobs.contains(queryId)) + return; + job = m_jobs.value(queryId); + } + + QDeclarativeXmlQueryResult r; + doQueryJob(&job); + doSubQueryJob(&job); + r.queryId = job.queryId; + r.size = m_size; + r.data = m_modelData; + r.inserted = m_insertedItemRanges; + r.removed = m_removedItemRanges; + r.keyRoleResultsCache = job.keyRoleResultsCache; + + { + QMutexLocker ml(&m_mutex); + if (m_jobs.contains(queryId)) { + emit queryCompleted(r); + m_jobs.remove(queryId); + } + } + } + Q_SIGNALS: void queryCompleted(const QDeclarativeXmlQueryResult &); void error(void*, const QString&); protected: - void run() { - m_mutex.lock(); - - while (!m_quit) { - if (!m_jobs.isEmpty()) - m_currentJob = m_jobs.dequeue(); - m_mutex.unlock(); - - QDeclarativeXmlQueryResult r; - if (m_currentJob.queryId != -1) { - doQueryJob(); - doSubQueryJob(); - r.queryId = m_currentJob.queryId; - r.size = m_size; - r.data = m_modelData; - r.inserted = m_insertedItemRanges; - r.removed = m_removedItemRanges; - r.keyRoleResultsCache = m_currentJob.keyRoleResultsCache; - } - m_mutex.lock(); - if (m_currentJob.queryId != -1 && m_abortQueryId != m_currentJob.queryId) - emit queryCompleted(r); - if (m_jobs.isEmpty() && !m_quit) - m_condition.wait(&m_mutex); - m_currentJob.queryId = -1; - m_abortQueryId = -1; - } - - m_mutex.unlock(); - } private: - void doQueryJob(); - void doSubQueryJob(); - void getValuesOfKeyRoles(QStringList *values, QXmlQuery *query) const; + void doQueryJob(XmlQueryJob* job); + void doSubQueryJob(XmlQueryJob* job); + void getValuesOfKeyRoles(const XmlQueryJob& currentJob, QStringList *values, QXmlQuery *query) const; void addIndexToRangeList(QList<QDeclarativeXmlListRange> *ranges, int index) const; private: QMutex m_mutex; - QWaitCondition m_condition; - QQueue<XmlQueryJob> m_jobs; - XmlQueryJob m_currentJob; - bool m_quit; - int m_abortQueryId; + QThread m_thread; + QMap<int, XmlQueryJob> m_jobs; + int m_queryIds; QString m_prefix; int m_size; - int m_queryIds; QList<QList<QVariant> > m_modelData; QList<QDeclarativeXmlListRange> m_insertedItemRanges; QList<QDeclarativeXmlListRange> m_removedItemRanges; @@ -268,16 +260,16 @@ private: Q_GLOBAL_STATIC(QDeclarativeXmlQuery, globalXmlQuery) -void QDeclarativeXmlQuery::doQueryJob() +void QDeclarativeXmlQuery::doQueryJob(XmlQueryJob* currentJob) { - Q_ASSERT(m_currentJob.queryId != -1); + Q_ASSERT(currentJob->queryId != -1); QString r; QXmlQuery query; - QBuffer buffer(&m_currentJob.data); + QBuffer buffer(¤tJob->data); buffer.open(QIODevice::ReadOnly); query.bindVariable(QLatin1String("src"), &buffer); - query.setQuery(m_currentJob.namespaces + m_currentJob.query); + query.setQuery(currentJob->namespaces + currentJob->query); query.evaluateTo(&r); //always need a single root element @@ -285,9 +277,9 @@ void QDeclarativeXmlQuery::doQueryJob() QBuffer b(&xml); b.open(QIODevice::ReadOnly); - QString namespaces = QLatin1String("declare namespace dummy=\"http://qtsotware.com/dummy\";\n") + m_currentJob.namespaces; + QString namespaces = QLatin1String("declare namespace dummy=\"http://qtsotware.com/dummy\";\n") + currentJob->namespaces; QString prefix = QLatin1String("doc($inputDocument)/dummy:items") + - m_currentJob.query.mid(m_currentJob.query.lastIndexOf(QLatin1Char('/'))); + currentJob->query.mid(currentJob->query.lastIndexOf(QLatin1Char('/'))); //figure out how many items we are dealing with int count = -1; @@ -302,18 +294,16 @@ void QDeclarativeXmlQuery::doQueryJob() count = item.toAtomicValue().toInt(); } - m_currentJob.data = xml; + currentJob->data = xml; m_prefix = namespaces + prefix + QLatin1Char('/'); m_size = 0; if (count > 0) m_size = count; } -void QDeclarativeXmlQuery::getValuesOfKeyRoles(QStringList *values, QXmlQuery *query) const +void QDeclarativeXmlQuery::getValuesOfKeyRoles(const XmlQueryJob& currentJob, QStringList *values, QXmlQuery *query) const { - Q_ASSERT(m_currentJob.queryId != -1); - - const QStringList &keysQueries = m_currentJob.keyRoleQueries; + const QStringList &keysQueries = currentJob.keyRoleQueries; QString keysQuery; if (keysQueries.count() == 1) keysQuery = m_prefix + keysQueries[0]; @@ -341,34 +331,34 @@ void QDeclarativeXmlQuery::addIndexToRangeList(QList<QDeclarativeXmlListRange> * ranges->append(qMakePair(index, 1)); } -void QDeclarativeXmlQuery::doSubQueryJob() +void QDeclarativeXmlQuery::doSubQueryJob(XmlQueryJob* currentJob) { - Q_ASSERT(m_currentJob.queryId != -1); + Q_ASSERT(currentJob->queryId != -1); m_modelData.clear(); - QBuffer b(&m_currentJob.data); + QBuffer b(¤tJob->data); b.open(QIODevice::ReadOnly); QXmlQuery subquery; subquery.bindVariable(QLatin1String("inputDocument"), &b); QStringList keyRoleResults; - getValuesOfKeyRoles(&keyRoleResults, &subquery); + getValuesOfKeyRoles(*currentJob, &keyRoleResults, &subquery); // See if any values of key roles have been inserted or removed. m_insertedItemRanges.clear(); m_removedItemRanges.clear(); - if (m_currentJob.keyRoleResultsCache.isEmpty()) { + if (currentJob->keyRoleResultsCache.isEmpty()) { m_insertedItemRanges << qMakePair(0, m_size); } else { - if (keyRoleResults != m_currentJob.keyRoleResultsCache) { + if (keyRoleResults != currentJob->keyRoleResultsCache) { QStringList temp; - for (int i=0; i<m_currentJob.keyRoleResultsCache.count(); i++) { - if (!keyRoleResults.contains(m_currentJob.keyRoleResultsCache[i])) + for (int i=0; i<currentJob->keyRoleResultsCache.count(); i++) { + if (!keyRoleResults.contains(currentJob->keyRoleResultsCache[i])) addIndexToRangeList(&m_removedItemRanges, i); else - temp << m_currentJob.keyRoleResultsCache[i]; + temp << currentJob->keyRoleResultsCache[i]; } for (int i=0; i<keyRoleResults.count(); i++) { @@ -379,11 +369,11 @@ void QDeclarativeXmlQuery::doSubQueryJob() } } } - m_currentJob.keyRoleResultsCache = keyRoleResults; + currentJob->keyRoleResultsCache = keyRoleResults; // Get the new values for each role. //### we might be able to condense even further (query for everything in one go) - const QStringList &queries = m_currentJob.roleQueries; + const QStringList &queries = currentJob->roleQueries; for (int i = 0; i < queries.size(); ++i) { QList<QVariant> resultList; if (!queries[i].isEmpty()) { @@ -397,7 +387,7 @@ void QDeclarativeXmlQuery::doSubQueryJob() item = resultItems.next(); } } else { - emit error(m_currentJob.roleQueryErrorId.at(i), queries[i]); + emit error(currentJob->roleQueryErrorId.at(i), queries[i]); } } //### should warn here if things have gone wrong. diff --git a/src/gui/itemviews/qtreeview.cpp b/src/gui/itemviews/qtreeview.cpp index d03babb..21c9d3b 100644 --- a/src/gui/itemviews/qtreeview.cpp +++ b/src/gui/itemviews/qtreeview.cpp @@ -2744,6 +2744,7 @@ int QTreeView::indexRowSizeHint(const QModelIndex &index) const int start = -1; int end = -1; + int indexRow = index.row(); int count = d->header->count(); bool emptyHeader = (count == 0); QModelIndex parent = index.parent(); @@ -2780,7 +2781,7 @@ int QTreeView::indexRowSizeHint(const QModelIndex &index) const int logicalColumn = emptyHeader ? column : d->header->logicalIndex(column); if (d->header->isSectionHidden(logicalColumn)) continue; - QModelIndex idx = d->model->index(index.row(), logicalColumn, parent); + QModelIndex idx = d->model->index(indexRow, logicalColumn, parent); if (idx.isValid()) { QWidget *editor = d->editorForIndex(idx).widget.data(); if (editor && d->persistent.contains(editor)) { @@ -3215,14 +3216,14 @@ int QTreeViewPrivate::itemHeight(int item) const if (viewItems.isEmpty()) return 0; const QModelIndex &index = viewItems.at(item).index; + if (!index.isValid()) + return 0; int height = viewItems.at(item).height; - if (height <= 0 && index.isValid()) { + if (height <= 0) { height = q_func()->indexRowSizeHint(index); viewItems[item].height = height; } - if (!index.isValid() || height < 0) - return 0; - return height; + return qMax(height, 0); } diff --git a/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h b/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h index 1c9258a..c4b74c6 100644 --- a/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h +++ b/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h @@ -88,6 +88,8 @@ QT_END_NAMESPACE QWidget *widget = [self QT_MANGLE_NAMESPACE(qt_qwidget)]; if (!widget) return NO; // This should happen only for qt_root_win + if (QApplicationPrivate::isBlockedByModal(widget)) + return NO; bool isToolTip = (widget->windowType() == Qt::ToolTip); bool isPopup = (widget->windowType() == Qt::Popup); @@ -99,6 +101,8 @@ QT_END_NAMESPACE QWidget *widget = [self QT_MANGLE_NAMESPACE(qt_qwidget)]; if (!widget) return NO; // This should happen only for qt_root_win + if ([self isSheet]) + return NO; bool isToolTip = (widget->windowType() == Qt::ToolTip); bool isPopup = (widget->windowType() == Qt::Popup); diff --git a/src/gui/kernel/qcocoaview_mac.mm b/src/gui/kernel/qcocoaview_mac.mm index 3d87a9e..ff2dfe7 100644 --- a/src/gui/kernel/qcocoaview_mac.mm +++ b/src/gui/kernel/qcocoaview_mac.mm @@ -797,7 +797,7 @@ static int qCocoaViewCount = 0; - (BOOL)resignFirstResponder { if (!qwidget) - return NO; + return YES; // Seems like the following test only triggers if this // view is inside a QMacNativeWidget: diff --git a/src/gui/kernel/qt_cocoa_helpers_mac.mm b/src/gui/kernel/qt_cocoa_helpers_mac.mm index c8132e8..98f62ca 100644 --- a/src/gui/kernel/qt_cocoa_helpers_mac.mm +++ b/src/gui/kernel/qt_cocoa_helpers_mac.mm @@ -1627,6 +1627,7 @@ void qt_mac_constructQIconFromIconRef(const IconRef icon, const IconRef overlayI #ifdef QT_MAC_USE_COCOA void qt_mac_menu_collapseSeparators(void */*NSMenu **/ theMenu, bool collapse) { + QMacCocoaAutoReleasePool pool; OSMenuRef menu = static_cast<OSMenuRef>(theMenu); if (collapse) { bool previousIsSeparator = true; // setting to true kills all the separators placed at the top. diff --git a/src/gui/painting/qpaintengine_raster.cpp b/src/gui/painting/qpaintengine_raster.cpp index 5513010..9242fb6 100644 --- a/src/gui/painting/qpaintengine_raster.cpp +++ b/src/gui/painting/qpaintengine_raster.cpp @@ -3716,6 +3716,13 @@ void QRasterPaintEnginePrivate::rasterizeLine_dashed(QLineF line, const bool squareCap = (pen.capStyle() == Qt::SquareCap); const QVector<qreal> pattern = pen.dashPattern(); + qreal patternLength = 0; + for (int i = 0; i < pattern.size(); ++i) + patternLength += pattern.at(i); + + if (patternLength <= 0) + return; + qreal length = line.length(); Q_ASSERT(length > 0); while (length > 0) { diff --git a/src/gui/statemachine/qguistatemachine.cpp b/src/gui/statemachine/qguistatemachine.cpp index eadb8ff..2a0de3c 100644 --- a/src/gui/statemachine/qguistatemachine.cpp +++ b/src/gui/statemachine/qguistatemachine.cpp @@ -404,6 +404,7 @@ static QEvent *cloneEvent(QEvent *e) we2->setButtons(we->buttons()); we2->setModifiers(we->modifiers()); we2->setOrientation(we->orientation()); + we2->setDelta(we->delta()); return we2; } #endif diff --git a/src/gui/text/qtextcontrol.cpp b/src/gui/text/qtextcontrol.cpp index e15c06d..46f1d62 100644 --- a/src/gui/text/qtextcontrol.cpp +++ b/src/gui/text/qtextcontrol.cpp @@ -933,15 +933,18 @@ void QTextControl::processEvent(QEvent *e, const QMatrix &matrix, QWidget *conte break; } case QEvent::MouseMove: { QMouseEvent *ev = static_cast<QMouseEvent *>(e); - d->mouseMoveEvent(ev->buttons(), matrix.map(ev->pos())); + d->mouseMoveEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), + ev->buttons(), ev->globalPos()); break; } case QEvent::MouseButtonRelease: { QMouseEvent *ev = static_cast<QMouseEvent *>(e); - d->mouseReleaseEvent(ev->button(), matrix.map(ev->pos())); + d->mouseReleaseEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), + ev->buttons(), ev->globalPos()); break; } case QEvent::MouseButtonDblClick: { QMouseEvent *ev = static_cast<QMouseEvent *>(e); - d->mouseDoubleClickEvent(e, ev->button(), matrix.map(ev->pos())); + d->mouseDoubleClickEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), + ev->buttons(), ev->globalPos()); break; } case QEvent::InputMethod: d->inputMethodEvent(static_cast<QInputMethodEvent *>(e)); @@ -1001,15 +1004,18 @@ void QTextControl::processEvent(QEvent *e, const QMatrix &matrix, QWidget *conte break; } case QEvent::GraphicsSceneMouseMove: { QGraphicsSceneMouseEvent *ev = static_cast<QGraphicsSceneMouseEvent *>(e); - d->mouseMoveEvent(ev->buttons(), matrix.map(ev->pos())); + d->mouseMoveEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), ev->buttons(), + ev->screenPos()); break; } case QEvent::GraphicsSceneMouseRelease: { QGraphicsSceneMouseEvent *ev = static_cast<QGraphicsSceneMouseEvent *>(e); - d->mouseReleaseEvent(ev->button(), matrix.map(ev->pos())); + d->mouseReleaseEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), ev->buttons(), + ev->screenPos()); break; } case QEvent::GraphicsSceneMouseDoubleClick: { QGraphicsSceneMouseEvent *ev = static_cast<QGraphicsSceneMouseEvent *>(e); - d->mouseDoubleClickEvent(e, ev->button(), matrix.map(ev->pos())); + d->mouseDoubleClickEvent(ev, ev->button(), matrix.map(ev->pos()), ev->modifiers(), ev->buttons(), + ev->screenPos()); break; } case QEvent::GraphicsSceneContextMenu: { QGraphicsSceneContextMenuEvent *ev = static_cast<QGraphicsSceneContextMenuEvent *>(e); @@ -1018,7 +1024,8 @@ void QTextControl::processEvent(QEvent *e, const QMatrix &matrix, QWidget *conte case QEvent::GraphicsSceneHoverMove: { QGraphicsSceneHoverEvent *ev = static_cast<QGraphicsSceneHoverEvent *>(e); - d->mouseMoveEvent(Qt::NoButton, matrix.map(ev->pos())); + d->mouseMoveEvent(ev, Qt::NoButton, matrix.map(ev->pos()), ev->modifiers(),Qt::NoButton, + ev->screenPos()); break; } case QEvent::GraphicsSceneDragEnter: { @@ -1488,6 +1495,11 @@ void QTextControlPrivate::mousePressEvent(QEvent *e, Qt::MouseButton button, con { Q_Q(QTextControl); + if (sendMouseEventToInputContext( + e, QEvent::MouseButtonPress, button, pos, modifiers, buttons, globalPos)) { + return; + } + if (interactionFlags & Qt::LinksAccessibleByMouse) { anchorOnMousePress = q->anchorAt(pos); @@ -1530,22 +1542,7 @@ void QTextControlPrivate::mousePressEvent(QEvent *e, Qt::MouseButton button, con return; } -#if !defined(QT_NO_IM) - QTextLayout *layout = cursor.block().layout(); - if (contextWidget && layout && !layout->preeditAreaText().isEmpty()) { - QInputContext *ctx = inputContext(); - if (ctx) { - QMouseEvent ev(QEvent::MouseButtonPress, contextWidget->mapFromGlobal(globalPos), globalPos, - button, buttons, modifiers); - ctx->mouseHandler(cursorPos - cursor.position(), &ev); - } - if (!layout->preeditAreaText().isEmpty()) { - e->ignore(); - return; - } - } -#endif - if (modifiers == Qt::ShiftModifier) { + if (modifiers == Qt::ShiftModifier && (interactionFlags & Qt::TextSelectableByMouse)) { if (wordSelectionEnabled && !selectedWordOnDoubleClick.hasSelection()) { selectedWordOnDoubleClick = cursor; selectedWordOnDoubleClick.select(QTextCursor::WordUnderCursor); @@ -1590,10 +1587,16 @@ void QTextControlPrivate::mousePressEvent(QEvent *e, Qt::MouseButton button, con hadSelectionOnMousePress = cursor.hasSelection(); } -void QTextControlPrivate::mouseMoveEvent(Qt::MouseButtons buttons, const QPointF &mousePos) +void QTextControlPrivate::mouseMoveEvent(QEvent *e, Qt::MouseButton button, const QPointF &mousePos, Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, const QPoint &globalPos) { Q_Q(QTextControl); + if (sendMouseEventToInputContext( + e, QEvent::MouseMove, button, mousePos, modifiers, buttons, globalPos)) { + return; + } + if (interactionFlags & Qt::LinksAccessibleByMouse) { QString anchor = q->anchorAt(mousePos); if (anchor != highlightedAnchor) { @@ -1623,12 +1626,6 @@ void QTextControlPrivate::mouseMoveEvent(Qt::MouseButtons buttons, const QPointF } const qreal mouseX = qreal(mousePos.x()); -#if !defined(QT_NO_IM) - QTextLayout *layout = cursor.block().layout(); - if (layout && !layout->preeditAreaText().isEmpty()) - return; -#endif - int newCursorPos = q->hitTest(mousePos, Qt::FuzzyHit); if (newCursorPos == -1) return; @@ -1642,7 +1639,7 @@ void QTextControlPrivate::mouseMoveEvent(Qt::MouseButtons buttons, const QPointF extendBlockwiseSelection(newCursorPos); else if (selectedWordOnDoubleClick.hasSelection()) extendWordwiseSelection(newCursorPos, mouseX); - else + else if (interactionFlags & Qt::TextSelectableByMouse) setCursorPosition(newCursorPos, QTextCursor::KeepAnchor); if (interactionFlags & Qt::TextEditable) { @@ -1666,10 +1663,16 @@ void QTextControlPrivate::mouseMoveEvent(Qt::MouseButtons buttons, const QPointF repaintOldAndNewSelection(oldSelection); } -void QTextControlPrivate::mouseReleaseEvent(Qt::MouseButton button, const QPointF &pos) +void QTextControlPrivate::mouseReleaseEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos, Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, const QPoint &globalPos) { Q_Q(QTextControl); + if (sendMouseEventToInputContext( + e, QEvent::MouseButtonRelease, button, pos, modifiers, buttons, globalPos)) { + return; + } + const QTextCursor oldSelection = cursor; const int oldCursorPos = cursor.position(); @@ -1727,19 +1730,21 @@ void QTextControlPrivate::mouseReleaseEvent(Qt::MouseButton button, const QPoint } } -void QTextControlPrivate::mouseDoubleClickEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos) +void QTextControlPrivate::mouseDoubleClickEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos, Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, const QPoint &globalPos) { Q_Q(QTextControl); + + if (sendMouseEventToInputContext( + e, QEvent::MouseButtonDblClick, button, pos, modifiers, buttons, globalPos)) { + return; + } + if (button != Qt::LeftButton || !(interactionFlags & Qt::TextSelectableByMouse)) { e->ignore(); return; } -#if !defined(QT_NO_IM) - QTextLayout *layout = cursor.block().layout(); - if (layout && !layout->preeditAreaText().isEmpty()) - return; -#endif #ifndef QT_NO_DRAGANDDROP mightStartDrag = false; @@ -1768,6 +1773,45 @@ void QTextControlPrivate::mouseDoubleClickEvent(QEvent *e, Qt::MouseButton butto } } +bool QTextControlPrivate::sendMouseEventToInputContext( + QEvent *e, QEvent::Type eventType, Qt::MouseButton button, const QPointF &pos, + Qt::KeyboardModifiers modifiers, Qt::MouseButtons buttons, const QPoint &globalPos) +{ +#if !defined(QT_NO_IM) + Q_Q(QTextControl); + + QTextLayout *layout = cursor.block().layout(); + if (contextWidget && layout && !layout->preeditAreaText().isEmpty()) { + QInputContext *ctx = inputContext(); + int cursorPos = q->hitTest(pos, Qt::FuzzyHit) - cursor.position(); + + if (cursorPos < 0 || cursorPos > layout->preeditAreaText().length()) { + cursorPos = -1; + // don't send move events outside the preedit area + if (eventType == QEvent::MouseMove) + return true; + } + if (ctx) { + QMouseEvent ev(eventType, contextWidget->mapFromGlobal(globalPos), globalPos, + button, buttons, modifiers); + ctx->mouseHandler(cursorPos, &ev); + e->setAccepted(ev.isAccepted()); + } + if (!layout->preeditAreaText().isEmpty()) + return true; + } +#else + Q_UNUSED(e); + Q_UNUSED(eventType); + Q_UNUSED(button); + Q_UNUSED(pos); + Q_UNUSED(modifiers); + Q_UNUSED(buttons); + Q_UNUSED(globalPos); +#endif + return false; +} + void QTextControlPrivate::contextMenuEvent(const QPoint &screenPos, const QPointF &docPos, QWidget *contextWidget) { #ifdef QT_NO_CONTEXTMENU diff --git a/src/gui/text/qtextcontrol_p_p.h b/src/gui/text/qtextcontrol_p_p.h index ecd13ea..94670e2 100644 --- a/src/gui/text/qtextcontrol_p_p.h +++ b/src/gui/text/qtextcontrol_p_p.h @@ -135,9 +135,23 @@ public: Qt::KeyboardModifiers modifiers, Qt::MouseButtons buttons, const QPoint &globalPos); - void mouseMoveEvent(Qt::MouseButtons buttons, const QPointF &pos); - void mouseReleaseEvent(Qt::MouseButton button, const QPointF &pos); - void mouseDoubleClickEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos); + void mouseMoveEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos, + Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, + const QPoint &globalPos); + void mouseReleaseEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos, + Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, + const QPoint &globalPos); + void mouseDoubleClickEvent(QEvent *e, Qt::MouseButton button, const QPointF &pos, + Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, + const QPoint &globalPos); + bool sendMouseEventToInputContext(QEvent *e, QEvent::Type eventType, Qt::MouseButton button, + const QPointF &pos, + Qt::KeyboardModifiers modifiers, + Qt::MouseButtons buttons, + const QPoint &globalPos); void contextMenuEvent(const QPoint &screenPos, const QPointF &docPos, QWidget *contextWidget); void focusEvent(QFocusEvent *e); #ifdef QT_KEYPAD_NAVIGATION diff --git a/src/gui/widgets/qlinecontrol.cpp b/src/gui/widgets/qlinecontrol.cpp index 4b95000..023b9ee 100644 --- a/src/gui/widgets/qlinecontrol.cpp +++ b/src/gui/widgets/qlinecontrol.cpp @@ -456,6 +456,7 @@ void QLineControl::processInputMethodEvent(QInputMethodEvent *event) #ifndef QT_NO_IM setPreeditArea(m_cursor, event->preeditString()); #endif //QT_NO_IM + const int oldPreeditCursor = m_preeditCursor; m_preeditCursor = event->preeditString().length(); m_hideCursor = false; QList<QTextLayout::FormatRange> formats; @@ -479,6 +480,8 @@ void QLineControl::processInputMethodEvent(QInputMethodEvent *event) updateDisplayText(/*force*/ true); if (cursorPositionChanged) emitCursorPositionChanged(); + else if (m_preeditCursor != oldPreeditCursor) + emit updateMicroFocus(); if (isGettingInput) finishChange(priorState); } diff --git a/src/gui/widgets/qlinecontrol_p.h b/src/gui/widgets/qlinecontrol_p.h index bfe50fe..3c505c8 100644 --- a/src/gui/widgets/qlinecontrol_p.h +++ b/src/gui/widgets/qlinecontrol_p.h @@ -425,6 +425,7 @@ Q_SIGNALS: void textEdited(const QString &); void resetInputContext(); + void updateMicroFocus(); void accepted(); void editingFinished(); diff --git a/src/network/access/qnetworkrequest.cpp b/src/network/access/qnetworkrequest.cpp index fc33e8d..8d46003 100644 --- a/src/network/access/qnetworkrequest.cpp +++ b/src/network/access/qnetworkrequest.cpp @@ -529,8 +529,9 @@ QSslConfiguration QNetworkRequest::sslConfiguration() const /*! Sets this network request's SSL configuration to be \a config. The settings that apply are the private key, the local certificate, - the SSL protocol (SSLv2, SSLv3, TLSv1 where applicable) and the - ciphers that the SSL backend is allowed to use. + the SSL protocol (SSLv2, SSLv3, TLSv1 where applicable), the CA + certificates and the ciphers that the SSL backend is allowed to + use. By default, no SSL configuration is set, which allows the backends to choose freely what configuration is best for them. diff --git a/src/network/ssl/qsslsocket_openssl.cpp b/src/network/ssl/qsslsocket_openssl.cpp index 7d21bd3..84e14ff 100644 --- a/src/network/ssl/qsslsocket_openssl.cpp +++ b/src/network/ssl/qsslsocket_openssl.cpp @@ -780,6 +780,7 @@ QList<QSslCertificate> QSslSocketPrivate::systemCaCertificates() systemCerts.append(QSslCertificate::fromData(rawCert, QSsl::Der)); } } + CFRelease(cfCerts); } else { // no detailed error handling here diff --git a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp index 30d6b50..6b37b38 100644 --- a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp +++ b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp @@ -213,6 +213,11 @@ void QNetworkManagerEngine::connectToId(const QString &id) dbusDevicePath = devicePath.path(); break; } + else if (device.deviceType() == DEVICE_TYPE_GSM && + connectionType == QLatin1String("gsm")) { + dbusDevicePath = devicePath.path(); + break; + } } const QString service = connection->connectionInterface()->service(); diff --git a/src/plugins/gfxdrivers/directfb/qdirectfbpixmap.cpp b/src/plugins/gfxdrivers/directfb/qdirectfbpixmap.cpp index 50e0f5f..eaff74a 100644 --- a/src/plugins/gfxdrivers/directfb/qdirectfbpixmap.cpp +++ b/src/plugins/gfxdrivers/directfb/qdirectfbpixmap.cpp @@ -245,10 +245,9 @@ bool QDirectFBPixmapData::fromDataBufferDescription(const DFBDataBufferDescripti QDirectFBPointer<IDirectFBDataBuffer> dataBuffer(dataBufferPtr); IDirectFBImageProvider *providerPtr; - if ((result = dataBuffer->CreateImageProvider(dataBuffer.data(), &providerPtr)) != DFB_OK) { - DirectFBError("QDirectFBPixmapData::fromDataBufferDescription(): Can't create image provider", result); + if ((result = dataBuffer->CreateImageProvider(dataBuffer.data(), &providerPtr)) != DFB_OK) return false; - } + QDirectFBPointer<IDirectFBImageProvider> provider(providerPtr); DFBImageDescription imageDescription; diff --git a/src/plugins/gfxdrivers/directfb/qdirectfbscreen.cpp b/src/plugins/gfxdrivers/directfb/qdirectfbscreen.cpp index 09cc465..ff15078 100644 --- a/src/plugins/gfxdrivers/directfb/qdirectfbscreen.cpp +++ b/src/plugins/gfxdrivers/directfb/qdirectfbscreen.cpp @@ -1285,7 +1285,7 @@ bool QDirectFBScreen::connect(const QString &displaySpec) result = d_ptr->primarySurface->GetSize(d_ptr->primarySurface, &w, &h); #elif (Q_DIRECTFB_VERSION >= 0x010000) IDirectFBSurface *layerSurface; - if (d_ptr->dfbLayer->GetSurface(d_ptr->dfbLayer, &layerSurface) != DFB_OK) { + if (d_ptr->dfbLayer->GetSurface(d_ptr->dfbLayer, &layerSurface) == DFB_OK) { result = layerSurface->GetSize(layerSurface, &w, &h); layerSurface->Release(layerSurface); } diff --git a/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.cpp b/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.cpp index d0056a7..3d8cf50 100644 --- a/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.cpp +++ b/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.cpp @@ -55,7 +55,6 @@ QT_BEGIN_NAMESPACE QDirectFBWindowSurface::QDirectFBWindowSurface(DFBSurfaceFlipFlags flip, QDirectFBScreen *scr) : QDirectFBPaintDevice(scr) - , sibling(0) #ifndef QT_NO_DIRECTFB_WM , dfbWindow(0) #endif @@ -75,7 +74,6 @@ QDirectFBWindowSurface::QDirectFBWindowSurface(DFBSurfaceFlipFlags flip, QDirect QDirectFBWindowSurface::QDirectFBWindowSurface(DFBSurfaceFlipFlags flip, QDirectFBScreen *scr, QWidget *widget) : QWSWindowSurface(widget), QDirectFBPaintDevice(scr) - , sibling(0) #ifndef QT_NO_DIRECTFB_WM , dfbWindow(0) #endif @@ -123,7 +121,7 @@ void QDirectFBWindowSurface::raise() IDirectFBWindow *QDirectFBWindowSurface::directFBWindow() const { - return (dfbWindow ? dfbWindow : (sibling ? sibling->dfbWindow : 0)); + return dfbWindow; } void QDirectFBWindowSurface::createWindow(const QRect &rect) @@ -287,17 +285,40 @@ void QDirectFBWindowSurface::setGeometry(const QRect &rect) QByteArray QDirectFBWindowSurface::permanentState() const { - QByteArray state(sizeof(this), 0); - *reinterpret_cast<const QDirectFBWindowSurface**>(state.data()) = this; + QByteArray state(sizeof(SurfaceFlags) + sizeof(DFBWindowID), 0); + char *ptr = state.data(); + SurfaceFlags flags = surfaceFlags(); + memcpy(ptr, &flags, sizeof(SurfaceFlags)); + ptr += sizeof(SurfaceFlags); + DFBWindowID did = (DFBWindowID)(-1); + if (dfbWindow) + dfbWindow->GetID(dfbWindow, &did); + memcpy(ptr, &did, sizeof(DFBWindowID)); return state; } void QDirectFBWindowSurface::setPermanentState(const QByteArray &state) { - if (state.size() == sizeof(this)) { - sibling = *reinterpret_cast<QDirectFBWindowSurface *const*>(state.constData()); - Q_ASSERT(sibling); - setSurfaceFlags(sibling->surfaceFlags()); + const char *ptr = state.constData(); + IDirectFBDisplayLayer *layer = screen->dfbDisplayLayer(); + SurfaceFlags flags; + memcpy(&flags, ptr, sizeof(SurfaceFlags)); + + setSurfaceFlags(flags); + ptr += sizeof(SurfaceFlags); + DFBWindowID id; + memcpy(&id, ptr, sizeof(DFBWindowID)); + if (dfbSurface) + dfbSurface->Release(dfbSurface); + if (id != (DFBWindowID)-1) { + IDirectFBWindow *dw; + layer->GetWindow(layer, id, &dw); + if (dw->GetSurface(dw, &dfbSurface) != DFB_OK) + dfbSurface = 0; + dw->Release(dw); + } + else { + dfbSurface = 0; } } @@ -406,8 +427,6 @@ void QDirectFBWindowSurface::endPaint(const QRegion &) IDirectFBSurface *QDirectFBWindowSurface::directFBSurface() const { - if (!dfbSurface && sibling && sibling->dfbSurface) - return sibling->dfbSurface; return dfbSurface; } @@ -415,11 +434,8 @@ IDirectFBSurface *QDirectFBWindowSurface::directFBSurface() const IDirectFBSurface *QDirectFBWindowSurface::surfaceForWidget(const QWidget *widget, QRect *rect) const { Q_ASSERT(widget); - if (!dfbSurface) { - if (sibling && (!sibling->sibling || sibling->dfbSurface)) - return sibling->surfaceForWidget(widget, rect); + if (!dfbSurface) return 0; - } QWidget *win = window(); Q_ASSERT(win); if (rect) { diff --git a/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.h b/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.h index f683fc8..75d462b 100644 --- a/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.h +++ b/src/plugins/gfxdrivers/directfb/qdirectfbwindowsurface.h @@ -100,7 +100,6 @@ private: void updateIsOpaque(); void setOpaque(bool opaque); void releaseSurface(); - QDirectFBWindowSurface *sibling; #ifdef QT_DIRECTFB_WM void createWindow(const QRect &rect); diff --git a/src/plugins/imageformats/ico/qicohandler.cpp b/src/plugins/imageformats/ico/qicohandler.cpp index 5aa26d3..701207d 100644 --- a/src/plugins/imageformats/ico/qicohandler.cpp +++ b/src/plugins/imageformats/ico/qicohandler.cpp @@ -559,6 +559,8 @@ QImage ICOReader::iconAt(int index) icoAttrib.ncolors = 0; else // # colors used icoAttrib.ncolors = header.biClrUsed ? header.biClrUsed : 1 << icoAttrib.nbits; + if (icoAttrib.ncolors > 256) //color table can't be more than 256 + return img; icoAttrib.w = iconEntry.bWidth; if (icoAttrib.w == 0) icoAttrib.w = header.biWidth; diff --git a/src/testlib/qbenchmark_p.h b/src/testlib/qbenchmark_p.h index 9a83a1a..ace17db 100644 --- a/src/testlib/qbenchmark_p.h +++ b/src/testlib/qbenchmark_p.h @@ -130,7 +130,7 @@ public: QBenchmarkGlobalData:current is created at the beginning of qExec() and cleared at the end. */ -class QBenchmarkGlobalData +class Q_TESTLIB_EXPORT QBenchmarkGlobalData { public: static QBenchmarkGlobalData *current; @@ -161,7 +161,7 @@ private: created at the beginning of qInvokeTestMethod() and cleared at the end. */ -class QBenchmarkTestMethodData +class Q_TESTLIB_EXPORT QBenchmarkTestMethodData { public: static QBenchmarkTestMethodData *current; diff --git a/src/testlib/qtestcase.cpp b/src/testlib/qtestcase.cpp index 55f5fbe..22d59f9 100644 --- a/src/testlib/qtestcase.cpp +++ b/src/testlib/qtestcase.cpp @@ -1014,6 +1014,10 @@ static bool isValidSlot(const QMetaMethod &sl) return true; } +Q_TESTLIB_EXPORT bool printAvailableFunctions = false; +Q_TESTLIB_EXPORT QStringList testFunctions; +Q_TESTLIB_EXPORT QStringList testTags; + static void qPrintTestSlots() { for (int i = 0; i < QTest::currentTestObject->metaObject()->methodCount(); ++i) { @@ -1034,7 +1038,7 @@ static int qToInt(char *str) return l; } -static void qParseArgs(int argc, char *argv[]) +Q_TESTLIB_EXPORT void qtest_qParseArgs(int argc, char *argv[], bool qml) { const char *testOptions = " options:\n" @@ -1084,8 +1088,12 @@ static void qParseArgs(int argc, char *argv[]) "%s", argv[0], testOptions); exit(0); } else if (strcmp(argv[i], "-functions") == 0) { - qPrintTestSlots(); - exit(0); + if (qml) { + QTest::printAvailableFunctions = true; + } else { + qPrintTestSlots(); + exit(0); + } } else if(strcmp(argv[i], "-xunitxml") == 0){ QTestLog::setLogMode(QTestLog::XunitXML); } else if (strcmp(argv[i], "-xml") == 0) { @@ -1221,6 +1229,32 @@ static void qParseArgs(int argc, char *argv[]) } else if (argv[i][0] == '-') { printf("Unknown option: '%s'\n\n%s", argv[i], testOptions); exit(1); + } else if (qml) { + // We can't check the availability of test functions until + // we load the QML files. So just store the data for now. + int colon = -1; + int offset; + for(offset = 0; *(argv[i]+offset); ++offset) { + if (*(argv[i]+offset) == ':') { + if (*(argv[i]+offset+1) == ':') { + // "::" is used as a test name separator. + // e.g. "ClickTests::test_click:row1". + ++offset; + } else { + colon = offset; + break; + } + } + } + if (colon == -1) { + QTest::testFunctions += QString::fromLatin1(argv[i]); + QTest::testTags += QString(); + } else { + QTest::testFunctions += + QString::fromLatin1(argv[i], colon); + QTest::testTags += + QString::fromLatin1(argv[i] + colon + 1); + } } else { if (!QTest::testFuncs) { QTest::testFuncs = new QTest::TestFunction[512]; @@ -1785,7 +1819,7 @@ int QTest::qExec(QObject *testObject, int argc, char **argv) QTEST_ASSERT(metaObject); QTestResult::setCurrentTestObject(metaObject->className()); - qParseArgs(argc, argv); + qtest_qParseArgs(argc, argv, false); if (QTest::randomOrder) { seedRandom(); } diff --git a/src/testlib/qtestlog_p.h b/src/testlib/qtestlog_p.h index 59282fd..a892d3d 100644 --- a/src/testlib/qtestlog_p.h +++ b/src/testlib/qtestlog_p.h @@ -59,7 +59,7 @@ QT_BEGIN_NAMESPACE class QBenchmarkResult; -class QTestLog +class Q_TESTLIB_EXPORT QTestLog { public: enum LogMode { Plain = 0, XML, LightXML, XunitXML }; diff --git a/src/testlib/qtestresult_p.h b/src/testlib/qtestresult_p.h index 15523f5..7ff120a 100644 --- a/src/testlib/qtestresult_p.h +++ b/src/testlib/qtestresult_p.h @@ -60,7 +60,7 @@ QT_BEGIN_NAMESPACE class QTestResultPrivate; class QTestData; -class QTestResult +class Q_TESTLIB_EXPORT QTestResult { public: enum TestLocation { NoWhere = 0, DataFunc = 1, InitFunc = 2, Func = 3, CleanupFunc = 4 }; diff --git a/src/testlib/qtesttable_p.h b/src/testlib/qtesttable_p.h index d085b57..f835506 100644 --- a/src/testlib/qtesttable_p.h +++ b/src/testlib/qtesttable_p.h @@ -60,7 +60,7 @@ QT_BEGIN_NAMESPACE class QTestData; class QTestTablePrivate; -class QTestTable +class Q_TESTLIB_EXPORT QTestTable { public: QTestTable(); |