Bug 1287576 - Update the touch-behavior notification code to behave like the set-target-apzc notification code. r=botond
authorKartikaya Gupta <kgupta@mozilla.com>
Mon, 25 Jul 2016 20:35:03 -0400
changeset 346640 5adee976c6cc1693a6327abe9cca29a42111a0ce
parent 346639 77c13c4140a4c2f95f97c2288e64ffabd4f8280a
child 346641 6047635058edf8b297698f4b1bb182f0d00bf2f1
push id6389
push userraliiev@mozilla.com
push dateMon, 19 Sep 2016 13:38:22 +0000
treeherdermozilla-beta@01d67bfe6c81 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbotond
bugs1287576
milestone50.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1287576 - Update the touch-behavior notification code to behave like the set-target-apzc notification code. r=botond In particular, this change uses the root frame of the touch target document, so that the correct presShell resolution is used when doing the touch-action hit test. MozReview-Commit-ID: 2bra6PIRqkR
dom/ipc/TabChild.cpp
gfx/layers/apz/util/APZCCallbackHelper.cpp
gfx/layers/apz/util/APZCCallbackHelper.h
gfx/layers/apz/util/TouchActionHelper.cpp
gfx/layers/apz/util/TouchActionHelper.h
widget/nsBaseWidget.cpp
--- a/dom/ipc/TabChild.cpp
+++ b/dom/ipc/TabChild.cpp
@@ -2005,21 +2005,21 @@ TabChild::RecvRealTouchEvent(const Widge
 
   WidgetTouchEvent localEvent(aEvent);
   localEvent.mWidget = mPuppetWidget;
 
   APZCCallbackHelper::ApplyCallbackTransform(localEvent, aGuid,
       mPuppetWidget->GetDefaultScale());
 
   if (localEvent.mMessage == eTouchStart && AsyncPanZoomEnabled()) {
+    nsCOMPtr<nsIDocument> document = GetDocument();
     if (gfxPrefs::TouchActionEnabled()) {
       APZCCallbackHelper::SendSetAllowedTouchBehaviorNotification(mPuppetWidget,
-          localEvent, aInputBlockId, mSetAllowedTouchBehaviorCallback);
+          document, localEvent, aInputBlockId, mSetAllowedTouchBehaviorCallback);
     }
-    nsCOMPtr<nsIDocument> document = GetDocument();
     APZCCallbackHelper::SendSetTargetAPZCNotification(mPuppetWidget, document,
         localEvent, aGuid, aInputBlockId);
   }
 
   // Dispatch event to content (potentially a long-running operation)
   nsEventStatus status = APZCCallbackHelper::DispatchWidgetEvent(localEvent);
 
   if (!AsyncPanZoomEnabled()) {
--- a/gfx/layers/apz/util/APZCCallbackHelper.cpp
+++ b/gfx/layers/apz/util/APZCCallbackHelper.cpp
@@ -773,27 +773,34 @@ APZCCallbackHelper::SendSetTargetAPZCNot
       }
     }
   }
 }
 
 void
 APZCCallbackHelper::SendSetAllowedTouchBehaviorNotification(
         nsIWidget* aWidget,
+        nsIDocument* aDocument,
         const WidgetTouchEvent& aEvent,
         uint64_t aInputBlockId,
         const SetAllowedTouchBehaviorCallback& aCallback)
 {
-  nsTArray<TouchBehaviorFlags> flags;
-  for (uint32_t i = 0; i < aEvent.mTouches.Length(); i++) {
-    flags.AppendElement(
-      TouchActionHelper::GetAllowedTouchBehavior(aWidget,
-        aEvent.mTouches[i]->mRefPoint));
+  if (nsIPresShell* shell = aDocument->GetShell()) {
+    if (nsIFrame* rootFrame = shell->GetRootFrame()) {
+      rootFrame = UpdateRootFrameForTouchTargetDocument(rootFrame);
+
+      nsTArray<TouchBehaviorFlags> flags;
+      for (uint32_t i = 0; i < aEvent.mTouches.Length(); i++) {
+        flags.AppendElement(
+          TouchActionHelper::GetAllowedTouchBehavior(aWidget,
+                rootFrame, aEvent.mTouches[i]->mRefPoint));
+      }
+      aCallback(aInputBlockId, Move(flags));
+    }
   }
-  aCallback(aInputBlockId, Move(flags));
 }
 
 void
 APZCCallbackHelper::NotifyMozMouseScrollEvent(const FrameMetrics::ViewID& aScrollId, const nsString& aEvent)
 {
   nsCOMPtr<nsIContent> targetContent = nsLayoutUtils::FindContentFor(aScrollId);
   if (!targetContent) {
     return;
--- a/gfx/layers/apz/util/APZCCallbackHelper.h
+++ b/gfx/layers/apz/util/APZCCallbackHelper.h
@@ -136,16 +136,17 @@ public:
                                               nsIDocument* aDocument,
                                               const WidgetGUIEvent& aEvent,
                                               const ScrollableLayerGuid& aGuid,
                                               uint64_t aInputBlockId);
 
     /* Figure out the allowed touch behaviors of each touch point in |aEvent|
      * and send that information to the provided callback. */
     static void SendSetAllowedTouchBehaviorNotification(nsIWidget* aWidget,
+                                                        nsIDocument* aDocument,
                                                         const WidgetTouchEvent& aEvent,
                                                         uint64_t aInputBlockId,
                                                         const SetAllowedTouchBehaviorCallback& aCallback);
 
     /* Notify content of a mouse scroll testing event. */
     static void NotifyMozMouseScrollEvent(const FrameMetrics::ViewID& aScrollId, const nsString& aEvent);
 
     /* Notify content that the repaint flush is complete. */
--- a/gfx/layers/apz/util/TouchActionHelper.cpp
+++ b/gfx/layers/apz/util/TouchActionHelper.cpp
@@ -4,17 +4,16 @@
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "TouchActionHelper.h"
 
 #include "mozilla/layers/APZCTreeManager.h"
 #include "nsContainerFrame.h"
 #include "nsIScrollableFrame.h"
 #include "nsLayoutUtils.h"
-#include "nsView.h"
 
 namespace mozilla {
 namespace layers {
 
 void
 TouchActionHelper::UpdateAllowedBehavior(uint32_t aTouchActionValue,
                                          bool aConsiderPanning,
                                          TouchBehaviorFlags& aOutBehavior)
@@ -41,32 +40,26 @@ TouchActionHelper::UpdateAllowedBehavior
     } else if ((aTouchActionValue & NS_STYLE_TOUCH_ACTION_PAN_Y) && !(aTouchActionValue & NS_STYLE_TOUCH_ACTION_PAN_X)) {
       aOutBehavior &= ~AllowedTouchBehavior::HORIZONTAL_PAN;
     }
   }
 }
 
 TouchBehaviorFlags
 TouchActionHelper::GetAllowedTouchBehavior(nsIWidget* aWidget,
+                                           nsIFrame* aRootFrame,
                                            const LayoutDeviceIntPoint& aPoint)
 {
-  nsView *view = nsView::GetViewFor(aWidget);
   TouchBehaviorFlags behavior = AllowedTouchBehavior::VERTICAL_PAN | AllowedTouchBehavior::HORIZONTAL_PAN |
                                 AllowedTouchBehavior::PINCH_ZOOM | AllowedTouchBehavior::DOUBLE_TAP_ZOOM;
 
-  if (!view) {
-    return behavior;
-  }
+  nsPoint relativePoint =
+    nsLayoutUtils::GetEventCoordinatesRelativeTo(aWidget, aPoint, aRootFrame);
 
-  nsIFrame *viewFrame = view->GetFrame();
-
-  nsPoint relativePoint =
-    nsLayoutUtils::GetEventCoordinatesRelativeTo(aWidget, aPoint, viewFrame);
-
-  nsIFrame *target = nsLayoutUtils::GetFrameForPoint(viewFrame, relativePoint, nsLayoutUtils::IGNORE_ROOT_SCROLL_FRAME);
+  nsIFrame *target = nsLayoutUtils::GetFrameForPoint(aRootFrame, relativePoint, nsLayoutUtils::IGNORE_ROOT_SCROLL_FRAME);
   if (!target) {
     return behavior;
   }
   nsIScrollableFrame *nearestScrollableParent = nsLayoutUtils::GetNearestScrollableFrame(target, 0);
   nsIFrame* nearestScrollableFrame = do_QueryFrame(nearestScrollableParent);
 
   // We're walking up the DOM tree until we meet the element with touch behavior and accumulating
   // touch-action restrictions of all elements in this chain.
--- a/gfx/layers/apz/util/TouchActionHelper.h
+++ b/gfx/layers/apz/util/TouchActionHelper.h
@@ -3,16 +3,17 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef __mozilla_layers_TouchActionHelper_h__
 #define __mozilla_layers_TouchActionHelper_h__
 
 #include "mozilla/layers/APZUtils.h" // for TouchBehaviorFlags
 
+class nsIFrame;
 class nsIWidget;
 
 namespace mozilla {
 namespace layers {
 
 /*
  * Helper class to figure out the allowed touch behavior for frames, as per
  * the touch-action spec.
@@ -26,15 +27,16 @@ private:
 
 public:
   /*
    * Performs hit testing on content, finds frame that corresponds to the aPoint and retrieves
    * touch-action css property value from it according the rules specified in the spec:
    * http://www.w3.org/TR/pointerevents/#the-touch-action-css-property.
    */
   static TouchBehaviorFlags GetAllowedTouchBehavior(nsIWidget* aWidget,
+                                                    nsIFrame* aRootFrame,
                                                     const LayoutDeviceIntPoint& aPoint);
 };
 
 } // namespace layers
 } // namespace mozilla
 
 #endif /*__mozilla_layers_TouchActionHelper_h__ */
--- a/widget/nsBaseWidget.cpp
+++ b/widget/nsBaseWidget.cpp
@@ -1116,17 +1116,17 @@ nsBaseWidget::ProcessUntransformedAPZEve
     // EventStateManager did not route the event into the child process.
     // It's safe to communicate to APZ that the event has been processed.
     // TODO: Eventually we'll be able to move the SendSetTargetAPZCNotification
     // call into APZEventState::Process*Event() as well.
     if (WidgetTouchEvent* touchEvent = aEvent->AsTouchEvent()) {
       if (touchEvent->mMessage == eTouchStart) {
         if (gfxPrefs::TouchActionEnabled()) {
           APZCCallbackHelper::SendSetAllowedTouchBehaviorNotification(this,
-              *(original->AsTouchEvent()), aInputBlockId,
+              GetDocument(), *(original->AsTouchEvent()), aInputBlockId,
               mSetAllowedTouchBehaviorCallback);
         }
         APZCCallbackHelper::SendSetTargetAPZCNotification(this, GetDocument(),
             *(original->AsTouchEvent()), aGuid, aInputBlockId);
       }
       mAPZEventState->ProcessTouchEvent(*touchEvent, aGuid, aInputBlockId,
           aApzResponse, status);
     } else if (WidgetWheelEvent* wheelEvent = aEvent->AsWheelEvent()) {