gfx/layers/apz/src/Axis.cpp

Sat, 03 Jan 2015 20:18:00 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Sat, 03 Jan 2015 20:18:00 +0100
branch
TOR_BUG_3246
changeset 7
129ffea94266
permissions
-rw-r--r--

Conditionally enable double key logic according to:
private browsing mode or privacy.thirdparty.isolate preference and
implement in GetCookieStringCommon and FindCookie where it counts...
With some reservations of how to convince FindCookie users to test
condition and pass a nullptr when disabling double key logic.

     1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
     2 /* vim: set sw=2 ts=8 et tw=80 : */
     3 /* This Source Code Form is subject to the terms of the Mozilla Public
     4  * License, v. 2.0. If a copy of the MPL was not distributed with this
     5  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     7 #include "Axis.h"
     8 #include <math.h>                       // for fabsf, pow, powf
     9 #include <algorithm>                    // for max
    10 #include "AsyncPanZoomController.h"     // for AsyncPanZoomController
    11 #include "mozilla/layers/APZCTreeManager.h" // for APZCTreeManager
    12 #include "FrameMetrics.h"               // for FrameMetrics
    13 #include "mozilla/Attributes.h"         // for MOZ_FINAL
    14 #include "mozilla/Preferences.h"        // for Preferences
    15 #include "mozilla/gfx/Rect.h"           // for RoundedIn
    16 #include "mozilla/mozalloc.h"           // for operator new
    17 #include "nsMathUtils.h"                // for NS_lround
    18 #include "nsThreadUtils.h"              // for NS_DispatchToMainThread, etc
    19 #include "nscore.h"                     // for NS_IMETHOD
    20 #include "gfxPrefs.h"                   // for the preferences
    22 namespace mozilla {
    23 namespace layers {
    25 Axis::Axis(AsyncPanZoomController* aAsyncPanZoomController)
    26   : mPos(0),
    27     mVelocity(0.0f),
    28     mAxisLocked(false),
    29     mAsyncPanZoomController(aAsyncPanZoomController)
    30 {
    31 }
    33 void Axis::UpdateWithTouchAtDevicePoint(int32_t aPos, const TimeDuration& aTimeDelta) {
    34   float newVelocity = mAxisLocked ? 0 : (mPos - aPos) / aTimeDelta.ToMilliseconds();
    35   if (gfxPrefs::APZMaxVelocity() > 0.0f) {
    36     newVelocity = std::min(newVelocity, gfxPrefs::APZMaxVelocity() * APZCTreeManager::GetDPI());
    37   }
    39   mVelocity = newVelocity;
    40   mPos = aPos;
    42   // Limit queue size pased on pref
    43   mVelocityQueue.AppendElement(mVelocity);
    44   if (mVelocityQueue.Length() > gfxPrefs::APZMaxVelocityQueueSize()) {
    45     mVelocityQueue.RemoveElementAt(0);
    46   }
    47 }
    49 void Axis::StartTouch(int32_t aPos) {
    50   mStartPos = aPos;
    51   mPos = aPos;
    52   mAxisLocked = false;
    53 }
    55 float Axis::AdjustDisplacement(float aDisplacement, float& aOverscrollAmountOut) {
    56   if (mAxisLocked) {
    57     aOverscrollAmountOut = 0;
    58     return 0;
    59   }
    61   float displacement = aDisplacement;
    63   // If this displacement will cause an overscroll, throttle it. Can potentially
    64   // bring it to 0 even if the velocity is high.
    65   if (DisplacementWillOverscroll(displacement) != OVERSCROLL_NONE) {
    66     // No need to have a velocity along this axis anymore; it won't take us
    67     // anywhere, so we're just spinning needlessly.
    68     mVelocity = 0.0f;
    69     aOverscrollAmountOut = DisplacementWillOverscrollAmount(displacement);
    70     displacement -= aOverscrollAmountOut;
    71   }
    72   return displacement;
    73 }
    75 float Axis::PanDistance() {
    76   return fabsf(mPos - mStartPos);
    77 }
    79 float Axis::PanDistance(float aPos) {
    80   return fabsf(aPos - mStartPos);
    81 }
    83 void Axis::EndTouch() {
    84   // Calculate the mean velocity and empty the queue.
    85   int count = mVelocityQueue.Length();
    86   if (count) {
    87     mVelocity = 0;
    88     while (!mVelocityQueue.IsEmpty()) {
    89       mVelocity += mVelocityQueue[0];
    90       mVelocityQueue.RemoveElementAt(0);
    91     }
    92     mVelocity /= count;
    93   }
    94 }
    96 void Axis::CancelTouch() {
    97   mVelocity = 0.0f;
    98   while (!mVelocityQueue.IsEmpty()) {
    99     mVelocityQueue.RemoveElementAt(0);
   100   }
   101 }
   103 bool Axis::Scrollable() {
   104     if (mAxisLocked) {
   105         return false;
   106     }
   107     return GetCompositionLength() < GetPageLength();
   108 }
   110 bool Axis::FlingApplyFrictionOrCancel(const TimeDuration& aDelta) {
   111   if (fabsf(mVelocity) <= gfxPrefs::APZFlingStoppedThreshold()) {
   112     // If the velocity is very low, just set it to 0 and stop the fling,
   113     // otherwise we'll just asymptotically approach 0 and the user won't
   114     // actually see any changes.
   115     mVelocity = 0.0f;
   116     return false;
   117   } else {
   118     mVelocity *= pow(1.0f - gfxPrefs::APZFlingFriction(), float(aDelta.ToMilliseconds()));
   119   }
   120   return true;
   121 }
   123 Axis::Overscroll Axis::GetOverscroll() {
   124   // If the current pan takes the window to the left of or above the current
   125   // page rect.
   126   bool minus = GetOrigin() < GetPageStart();
   127   // If the current pan takes the window to the right of or below the current
   128   // page rect.
   129   bool plus = GetCompositionEnd() > GetPageEnd();
   130   if (minus && plus) {
   131     return OVERSCROLL_BOTH;
   132   }
   133   if (minus) {
   134     return OVERSCROLL_MINUS;
   135   }
   136   if (plus) {
   137     return OVERSCROLL_PLUS;
   138   }
   139   return OVERSCROLL_NONE;
   140 }
   142 float Axis::GetExcess() {
   143   switch (GetOverscroll()) {
   144   case OVERSCROLL_MINUS: return GetOrigin() - GetPageStart();
   145   case OVERSCROLL_PLUS: return GetCompositionEnd() - GetPageEnd();
   146   case OVERSCROLL_BOTH: return (GetCompositionEnd() - GetPageEnd()) +
   147                                (GetPageStart() - GetOrigin());
   148   default: return 0;
   149   }
   150 }
   152 Axis::Overscroll Axis::DisplacementWillOverscroll(float aDisplacement) {
   153   // If the current pan plus a displacement takes the window to the left of or
   154   // above the current page rect.
   155   bool minus = GetOrigin() + aDisplacement < GetPageStart();
   156   // If the current pan plus a displacement takes the window to the right of or
   157   // below the current page rect.
   158   bool plus = GetCompositionEnd() + aDisplacement > GetPageEnd();
   159   if (minus && plus) {
   160     return OVERSCROLL_BOTH;
   161   }
   162   if (minus) {
   163     return OVERSCROLL_MINUS;
   164   }
   165   if (plus) {
   166     return OVERSCROLL_PLUS;
   167   }
   168   return OVERSCROLL_NONE;
   169 }
   171 float Axis::DisplacementWillOverscrollAmount(float aDisplacement) {
   172   switch (DisplacementWillOverscroll(aDisplacement)) {
   173   case OVERSCROLL_MINUS: return (GetOrigin() + aDisplacement) - GetPageStart();
   174   case OVERSCROLL_PLUS: return (GetCompositionEnd() + aDisplacement) - GetPageEnd();
   175   // Don't handle overscrolled in both directions; a displacement can't cause
   176   // this, it must have already been zoomed out too far.
   177   default: return 0;
   178   }
   179 }
   181 float Axis::ScaleWillOverscrollAmount(float aScale, float aFocus) {
   182   float originAfterScale = (GetOrigin() + aFocus) - (aFocus / aScale);
   184   bool both = ScaleWillOverscrollBothSides(aScale);
   185   bool minus = originAfterScale < GetPageStart();
   186   bool plus = (originAfterScale + (GetCompositionLength() / aScale)) > GetPageEnd();
   188   if ((minus && plus) || both) {
   189     // If we ever reach here it's a bug in the client code.
   190     MOZ_ASSERT(false, "In an OVERSCROLL_BOTH condition in ScaleWillOverscrollAmount");
   191     return 0;
   192   }
   193   if (minus) {
   194     return originAfterScale - GetPageStart();
   195   }
   196   if (plus) {
   197     return originAfterScale + (GetCompositionLength() / aScale) - GetPageEnd();
   198   }
   199   return 0;
   200 }
   202 float Axis::GetVelocity() {
   203   return mAxisLocked ? 0 : mVelocity;
   204 }
   206 void Axis::SetVelocity(float aVelocity) {
   207   mVelocity = aVelocity;
   208 }
   210 float Axis::GetCompositionEnd() const {
   211   return GetOrigin() + GetCompositionLength();
   212 }
   214 float Axis::GetPageEnd() const {
   215   return GetPageStart() + GetPageLength();
   216 }
   218 float Axis::GetOrigin() const {
   219   CSSPoint origin = mAsyncPanZoomController->GetFrameMetrics().GetScrollOffset();
   220   return GetPointOffset(origin);
   221 }
   223 float Axis::GetCompositionLength() const {
   224   const FrameMetrics& metrics = mAsyncPanZoomController->GetFrameMetrics();
   225   return GetRectLength(metrics.CalculateCompositedRectInCssPixels());
   226 }
   228 float Axis::GetPageStart() const {
   229   CSSRect pageRect = mAsyncPanZoomController->GetFrameMetrics().mScrollableRect;
   230   return GetRectOffset(pageRect);
   231 }
   233 float Axis::GetPageLength() const {
   234   CSSRect pageRect = mAsyncPanZoomController->GetFrameMetrics().mScrollableRect;
   235   return GetRectLength(pageRect);
   236 }
   238 bool Axis::ScaleWillOverscrollBothSides(float aScale) {
   239   const FrameMetrics& metrics = mAsyncPanZoomController->GetFrameMetrics();
   241   CSSToParentLayerScale scale(metrics.GetZoomToParent().scale * aScale);
   242   CSSRect cssCompositionBounds = metrics.mCompositionBounds / scale;
   244   return GetRectLength(metrics.mScrollableRect) < GetRectLength(cssCompositionBounds);
   245 }
   247 bool Axis::HasRoomToPan() const {
   248   return GetOrigin() > GetPageStart()
   249       || GetCompositionEnd() < GetPageEnd();
   250 }
   253 AxisX::AxisX(AsyncPanZoomController* aAsyncPanZoomController)
   254   : Axis(aAsyncPanZoomController)
   255 {
   257 }
   259 float AxisX::GetPointOffset(const CSSPoint& aPoint) const
   260 {
   261   return aPoint.x;
   262 }
   264 float AxisX::GetRectLength(const CSSRect& aRect) const
   265 {
   266   return aRect.width;
   267 }
   269 float AxisX::GetRectOffset(const CSSRect& aRect) const
   270 {
   271   return aRect.x;
   272 }
   274 AxisY::AxisY(AsyncPanZoomController* aAsyncPanZoomController)
   275   : Axis(aAsyncPanZoomController)
   276 {
   278 }
   280 float AxisY::GetPointOffset(const CSSPoint& aPoint) const
   281 {
   282   return aPoint.y;
   283 }
   285 float AxisY::GetRectLength(const CSSRect& aRect) const
   286 {
   287   return aRect.height;
   288 }
   290 float AxisY::GetRectOffset(const CSSRect& aRect) const
   291 {
   292   return aRect.y;
   293 }
   295 }
   296 }

mercurial