зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1458653 - Don't accelerate a fling if the previous fling animation has slowed down below a velocity threshold. r=botond
This should prevent most cases of unintended fling acceleration. For example, when scrolling paragraph-by-paragraph via a series of short flings, we would often accelerate the next fling even if the previous fling had already slowed down almost to a stop. With this change, we will no longer trigger acceleration in that scenario. This also matches Chrome's behavior. This patch does not add a new pref for the new velocity threshold. Chrome also shares the same velocity threshold for both velocities. Differential Revision: https://phabricator.services.mozilla.com/D95469
This commit is contained in:
Родитель
621c2b0fb7
Коммит
cfbcc7d97b
|
@ -259,8 +259,9 @@ typedef PlatformSpecificStateBase
|
|||
* Units: milliseconds
|
||||
*
|
||||
* \li\b apz.fling_accel_min_velocity
|
||||
* The minimum velocity of the second fling for it to be considered for fling
|
||||
* acceleration.
|
||||
* The minimum velocity of the second fling, and the minimum velocity of the
|
||||
* previous fling animation at the point of interruption, for the new fling to
|
||||
* be considered for fling acceleration.
|
||||
* Units: screen pixels per milliseconds
|
||||
*
|
||||
* \li\b apz.fling_accel_base_mult
|
||||
|
|
|
@ -16,6 +16,7 @@ namespace layers {
|
|||
void FlingAccelerator::Reset() {
|
||||
mPreviousFlingStartTime = SampleTime{};
|
||||
mPreviousFlingStartingVelocity = ParentLayerPoint{};
|
||||
mPreviousFlingCancelVelocity = ParentLayerPoint{};
|
||||
}
|
||||
|
||||
static bool SameDirection(float aVelocity1, float aVelocity2) {
|
||||
|
@ -53,6 +54,8 @@ ParentLayerPoint FlingAccelerator::GetFlingStartingVelocity(
|
|||
}
|
||||
}
|
||||
|
||||
Reset();
|
||||
|
||||
mPreviousFlingStartTime = aNow;
|
||||
mPreviousFlingStartingVelocity = velocity;
|
||||
|
||||
|
@ -81,6 +84,15 @@ bool FlingAccelerator::ShouldAccelerate(
|
|||
return false;
|
||||
}
|
||||
|
||||
if (mPreviousFlingCancelVelocity.Length() <
|
||||
StaticPrefs::apz_fling_accel_min_velocity()) {
|
||||
FLING_LOG(
|
||||
"%p The previous fling animation had slowed down too much when it was "
|
||||
"interrupted (%f), not accelerating.\n",
|
||||
this, float(mPreviousFlingCancelVelocity.Length()));
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -32,6 +32,10 @@ class FlingAccelerator final {
|
|||
ParentLayerPoint GetFlingStartingVelocity(const SampleTime& aNow,
|
||||
const ParentLayerPoint& aVelocity);
|
||||
|
||||
void ObserveFlingCanceled(const ParentLayerPoint& aVelocity) {
|
||||
mPreviousFlingCancelVelocity = aVelocity;
|
||||
}
|
||||
|
||||
protected:
|
||||
bool ShouldAccelerate(const SampleTime& aNow,
|
||||
const ParentLayerPoint& aVelocity) const;
|
||||
|
@ -41,6 +45,9 @@ class FlingAccelerator final {
|
|||
// The time at which the most recent fling started. This is the time when the
|
||||
// finger is lifted at the end of the gesture, as the fling animation starts.
|
||||
SampleTime mPreviousFlingStartTime;
|
||||
// The velocity that the previous fling animation had at the point it was
|
||||
// interrupted.
|
||||
ParentLayerPoint mPreviousFlingCancelVelocity;
|
||||
};
|
||||
|
||||
} // namespace layers
|
||||
|
|
|
@ -183,6 +183,10 @@ class GenericFlingAnimation : public AsyncPanZoomAnimation,
|
|||
return true;
|
||||
}
|
||||
|
||||
void Cancel(CancelAnimationFlags aFlags) override {
|
||||
mApzc.mFlingAccelerator.ObserveFlingCanceled(mApzc.GetVelocityVector());
|
||||
}
|
||||
|
||||
virtual bool HandleScrollOffsetUpdate(
|
||||
const Maybe<CSSPoint>& aRelativeDelta) override {
|
||||
return true;
|
||||
|
|
|
@ -146,3 +146,17 @@ TEST_F(APZCFlingAccelerationTester,
|
|||
{0, 0, 14, 61, 41, 0, 45, 35});
|
||||
CHECK_VELOCITY(Up, 3.2, 4.2);
|
||||
}
|
||||
|
||||
TEST_F(APZCFlingAccelerationTester,
|
||||
ShouldNotAccelerateWhenPreviousFlingHasSlowedDown) {
|
||||
SCOPED_GFX_PREF_INT("apz.fling_accel_interval_ms", 750);
|
||||
|
||||
ExecutePanGesture100Hz(ScreenIntPoint{748, 1046},
|
||||
{0, 9, 15, 23, 31, 30, 0, 34, 31, 29, 28, 24, 24, 11});
|
||||
CHECK_VELOCITY(Up, 2.2, 3.0);
|
||||
ExecuteWait(TimeDuration::FromMilliseconds(498));
|
||||
CHECK_VELOCITY(Up, 0.8, 1.0);
|
||||
ExecutePanGesture100Hz(ScreenIntPoint{745, 1056},
|
||||
{0, 10, 17, 29, 29, 33, 33, 0, 31, 27, 13});
|
||||
CHECK_VELOCITY(Up, 2.3, 2.7);
|
||||
}
|
||||
|
|
|
@ -567,6 +567,12 @@ TEST_F(APZScrollHandoffTester, ScrollgrabFlingAcceleration1) {
|
|||
SCOPED_GFX_PREF_FLOAT("apz.fling_min_velocity_threshold", 0.0f);
|
||||
SCOPED_GFX_VAR(UseWebRender, bool, false);
|
||||
CreateScrollgrabLayerTree(true /* make parent scrollable */);
|
||||
|
||||
// Note: Usually, fling acceleration does not work across handoff, because our
|
||||
// fling acceleration code does not propagate the "fling cancel velocity"
|
||||
// across handoff. However, this test sets apz.fling_min_velocity_threshold to
|
||||
// zero, so the "fling cancel velocity" is allowed to be zero, and fling
|
||||
// acceleration succeeds, almost by accident.
|
||||
TestFlingAcceleration();
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче