Bug 1140578 - Prevent resampling moves across non-move touch events. r=mchang

This commit is contained in:
Kartikaya Gupta 2015-03-09 12:46:04 -04:00
Родитель e288f1cc73
Коммит 8449555fb0
2 изменённых файлов: 38 добавлений и 1 удалений

Просмотреть файл

@ -64,6 +64,7 @@ GeckoTouchDispatcher::GetInstance()
GeckoTouchDispatcher::GeckoTouchDispatcher()
: mTouchQueueLock("GeckoTouchDispatcher::mTouchQueueLock")
, mHavePendingTouchMoves(false)
, mInflightNonMoveEvents(0)
, mTouchEventsFiltered(false)
{
// Since GeckoTouchDispatcher is initialized when input is initialized
@ -112,6 +113,16 @@ GeckoTouchDispatcher::NotifyTouch(MultiTouchInput& aTouch, TimeStamp aEventTime)
if (aTouch.mType == MultiTouchInput::MULTITOUCH_MOVE) {
MutexAutoLock lock(mTouchQueueLock);
if (mInflightNonMoveEvents > 0) {
// If we have any pending non-move events, we shouldn't resample the
// move events because we might end up dispatching events out of order.
// Instead, fall back to a non-resampling in-order dispatch until we're
// done processing the non-move events.
layers::APZThreadUtils::RunOnControllerThread(NewRunnableMethod(
this, &GeckoTouchDispatcher::DispatchTouchEvent, aTouch));
return;
}
mTouchMoveEvents.push_back(aTouch);
mHavePendingTouchMoves = true;
if (mResamplingEnabled) {
@ -121,8 +132,32 @@ GeckoTouchDispatcher::NotifyTouch(MultiTouchInput& aTouch, TimeStamp aEventTime)
layers::APZThreadUtils::RunOnControllerThread(NewRunnableMethod(
this, &GeckoTouchDispatcher::DispatchTouchMoveEvents, TimeStamp::Now()));
} else {
if (mResamplingEnabled) {
MutexAutoLock lock(mTouchQueueLock);
mInflightNonMoveEvents++;
}
layers::APZThreadUtils::RunOnControllerThread(NewRunnableMethod(
this, &GeckoTouchDispatcher::DispatchTouchEvent, aTouch));
this, &GeckoTouchDispatcher::DispatchTouchNonMoveEvent, aTouch));
}
}
void
GeckoTouchDispatcher::DispatchTouchNonMoveEvent(MultiTouchInput aInput)
{
layers::APZThreadUtils::AssertOnControllerThread();
if (mResamplingEnabled) {
// Flush pending touch move events, if there are any
// (DispatchTouchMoveEvents will check the mHavePendingTouchMoves flag and
// bail out if there's nothing to be done).
NotifyVsync(TimeStamp::Now());
}
DispatchTouchEvent(aInput);
if (mResamplingEnabled) {
MutexAutoLock lock(mTouchQueueLock);
mInflightNonMoveEvents--;
MOZ_ASSERT(mInflightNonMoveEvents >= 0);
}
}

Просмотреть файл

@ -49,6 +49,7 @@ public:
static GeckoTouchDispatcher* GetInstance();
void NotifyTouch(MultiTouchInput& aTouch, TimeStamp aEventTime);
void DispatchTouchEvent(MultiTouchInput aMultiTouch);
void DispatchTouchNonMoveEvent(MultiTouchInput aInput);
void DispatchTouchMoveEvents(TimeStamp aVsyncTime);
void NotifyVsync(TimeStamp aVsyncTimestamp);
void SetCompositorVsyncObserver(layers::CompositorVsyncObserver* aObserver);
@ -65,6 +66,7 @@ private:
Mutex mTouchQueueLock;
std::vector<MultiTouchInput> mTouchMoveEvents;
bool mHavePendingTouchMoves;
int mInflightNonMoveEvents;
// end stuff protected by mTouchQueueLock
bool mResamplingEnabled;