Make flushWindowSystemEvents return ev. accepted
authorMorten Johan Sørvig <morten.sorvig@theqtcompany.com>
Wed, 29 Apr 2015 10:34:16 +0000 (12:34 +0200)
committerMorten Johan Sørvig <morten.sorvig@theqtcompany.com>
Thu, 27 Aug 2015 21:58:24 +0000 (21:58 +0000)
flushWindowSystemEvents() now returns whether the
most recent event added to the queue was accepted
by Qt or not.

Use QAtomicInt to store the accepted state in order
to avoid a data race on it between the Gui thread
and the event poster thread.

Change-Id: I6c111fdaecda5c514307ca0749a54075fe8e872f
Reviewed-by: Jørgen Lind <jorgen.lind@theqtcompany.com>
src/gui/kernel/qwindowsysteminterface.cpp
src/gui/kernel/qwindowsysteminterface.h
src/gui/kernel/qwindowsysteminterface_p.h

index 88cf2da..01f4be6 100644 (file)
@@ -49,6 +49,7 @@ QElapsedTimer QWindowSystemInterfacePrivate::eventTime;
 bool QWindowSystemInterfacePrivate::synchronousWindowSystemEvents = false;
 QWaitCondition QWindowSystemInterfacePrivate::eventsFlushed;
 QMutex QWindowSystemInterfacePrivate::flushEventMutex;
+QAtomicInt QWindowSystemInterfacePrivate::eventAccepted;
 QWindowSystemEventHandler *QWindowSystemInterfacePrivate::eventHandler;
 
 //------------------------------------------------------------
@@ -618,17 +619,21 @@ void QWindowSystemInterface::deferredFlushWindowSystemEvents(QEventLoop::Process
     QWindowSystemInterfacePrivate::eventsFlushed.wakeOne();
 }
 
-void QWindowSystemInterface::flushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags)
+/*!
+    Make Qt Gui process all events on the event queue immediately. Return the
+    accepted state for the last event on the queue.
+*/
+bool QWindowSystemInterface::flushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags)
 {
     const int count = QWindowSystemInterfacePrivate::windowSystemEventQueue.count();
     if (!count)
-        return;
+        return false;
     if (!QGuiApplication::instance()) {
         qWarning().nospace()
             << "QWindowSystemInterface::flushWindowSystemEvents() invoked after "
                "QGuiApplication destruction, discarding " << count << " events.";
         QWindowSystemInterfacePrivate::windowSystemEventQueue.clear();
-        return;
+        return false;
     }
     if (QThread::currentThread() != QGuiApplication::instance()->thread()) {
         QMutexLocker locker(&QWindowSystemInterfacePrivate::flushEventMutex);
@@ -638,6 +643,7 @@ void QWindowSystemInterface::flushWindowSystemEvents(QEventLoop::ProcessEventsFl
     } else {
         sendWindowSystemEvents(flags);
     }
+    return QWindowSystemInterfacePrivate::eventAccepted.load() > 0;
 }
 
 bool QWindowSystemInterface::sendWindowSystemEvents(QEventLoop::ProcessEventsFlags flags)
@@ -659,6 +665,13 @@ bool QWindowSystemInterface::sendWindowSystemEvents(QEventLoop::ProcessEventsFla
             nevents++;
             QGuiApplicationPrivate::processWindowSystemEvent(event);
         }
+
+        // Record the accepted state for the processed event
+        // (excluding flush events). This state can then be
+        // returned by flushWindowSystemEvents().
+        if (event->type != QWindowSystemInterfacePrivate::FlushEvents)
+            QWindowSystemInterfacePrivate::eventAccepted.store(event->eventAccepted);
+
         delete event;
     }
 
index ace1a4f..3e0b788 100644 (file)
@@ -213,7 +213,7 @@ public:
     // For event dispatcher implementations
     static bool sendWindowSystemEvents(QEventLoop::ProcessEventsFlags flags);
     static void setSynchronousWindowSystemEvents(bool enable);
-    static void flushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags = QEventLoop::AllEvents);
+    static bool flushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags = QEventLoop::AllEvents);
     static void deferredFlushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags);
     static int windowSystemEventsQueued();
 };
index cc0ca6b..430800f 100644 (file)
@@ -51,6 +51,7 @@
 #include <QMutex>
 #include <QList>
 #include <QWaitCondition>
+#include <QAtomicInt>
 
 QT_BEGIN_NAMESPACE
 
@@ -488,6 +489,7 @@ public:
 
     static QWaitCondition eventsFlushed;
     static QMutex flushEventMutex;
+    static QAtomicInt eventAccepted;
 
     static QList<QTouchEvent::TouchPoint>
         fromNativeTouchPoints(const QList<QWindowSystemInterface::TouchPoint> &points,