tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

TestScrollbarDragging.cpp (3968B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* vim: set ts=8 sts=2 et sw=2 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/. */
      6 
      7 #include "APZCTreeManagerTester.h"
      8 #include "APZTestCommon.h"
      9 #include "InputUtils.h"
     10 
     11 class APZScrollbarDraggingTester : public APZCTreeManagerTester {
     12 public:
     13  APZScrollbarDraggingTester() { CreateMockHitTester(); }
     14 
     15 protected:
     16  UniquePtr<ScopedLayerTreeRegistration> registration;
     17  ScrollableLayerGuid::ViewID scrollId = ScrollableLayerGuid::START_SCROLL_ID;
     18  TestAsyncPanZoomController* apzc = nullptr;
     19 
     20  ParentLayerCoord ScrollY() const {
     21    return apzc
     22        ->GetCurrentAsyncScrollOffset(AsyncPanZoomController::eForEventHandling)
     23        .y;
     24  }
     25 
     26  void QueueHitOnVerticalScrollbar() {
     27    mMockHitTester->QueueScrollbarThumbHitResult(scrollId,
     28                                                 ScrollDirection::eVertical);
     29  }
     30 
     31  void CreateLayerTreeWithVerticalScrollbar() {
     32    // The first child is the scrollable node, the second child is the
     33    // scrollbar.
     34    const char* treeShape = "x(xx)";
     35    LayerIntRect layerVisibleRect[] = {LayerIntRect(0, 0, 100, 100),
     36                                       LayerIntRect(0, 0, 50, 100),
     37                                       LayerIntRect(50, 0, 50, 10)};
     38    CreateScrollData(treeShape, layerVisibleRect);
     39    SetScrollableFrameMetrics(layers[1], scrollId, CSSRect(0, 0, 50, 1000));
     40    registration = MakeUnique<ScopedLayerTreeRegistration>(LayersId{0}, mcc);
     41    layers[2]->SetScrollbarData(ScrollbarData::CreateForThumb(
     42        ScrollDirection::eVertical, 0.1, 0, 10, 10, true, 0, 100, scrollId));
     43    UpdateHitTestingTree();
     44    apzc = ApzcOf(layers[1]);
     45  }
     46 };
     47 
     48 // Test that the scrollable rect shrinking during dragging does not result
     49 // in scrolling out of bounds.
     50 TEST_F(APZScrollbarDraggingTester, ScrollableRectShrinksDuringDragging) {
     51  // Explicitly enable scrollbar dragging. This allows the test to run on
     52  // Android as well.
     53  SCOPED_GFX_PREF_BOOL("apz.drag.enabled", true);
     54 
     55  CreateLayerTreeWithVerticalScrollbar();
     56  EXPECT_EQ(ScrollY(), 0);
     57 
     58  // Start a scrollbar drag at y=5.
     59  QueueHitOnVerticalScrollbar();
     60  auto dragBlockId =
     61      MouseDown(manager, ScreenIntPoint(75, 5), mcc->Time()).mInputBlockId;
     62  manager->StartScrollbarDrag(apzc->GetGuid(),
     63                              AsyncDragMetrics(scrollId, 0, dragBlockId, 5,
     64                                               ScrollDirection::eVertical));
     65 
     66  // Drag the scrollbar down to y=75. (The total height is 100.)
     67  for (int mouseY = 10; mouseY <= 75; mouseY += 5) {
     68    mcc->AdvanceByMillis(10);
     69    // We do a hit test for every mouse event, including mousemoves.
     70    QueueHitOnVerticalScrollbar();
     71    MouseMove(manager, ScreenIntPoint(75, mouseY), mcc->Time());
     72  }
     73 
     74  // We should have scrolled past y>500 at least (total scrollable rect height
     75  // is 1000).
     76  EXPECT_GT(ScrollY(), 500);
     77 
     78  // Shrink the scrollable rect height to 500.
     79  ModifyFrameMetrics(layers[1], [](ScrollMetadata&, FrameMetrics& aMetrics) {
     80    aMetrics.SetScrollableRect(CSSRect(0, 0, 50, 500));
     81  });
     82  UpdateHitTestingTree();
     83 
     84  // Continue the drag to near the bottom, y=95.
     85  // Check that the scroll position never gets out of bounds. (With the
     86  // scrollable rect height now 500, the max vertical scroll position is 400.)
     87  for (int mouseY = 80; mouseY <= 95; mouseY += 5) {
     88    mcc->AdvanceByMillis(10);
     89    QueueHitOnVerticalScrollbar();
     90    MouseMove(manager, ScreenIntPoint(75, mouseY), mcc->Time());
     91    EXPECT_LE(ScrollY(), 400);
     92  }
     93 
     94  // End the drag.
     95  mcc->AdvanceByMillis(10);
     96  QueueHitOnVerticalScrollbar();
     97  MouseUp(manager, ScreenIntPoint(75, 95), mcc->Time());
     98 
     99  // We should end up at the bottom of the new scroll range (and not out of
    100  // bounds).
    101  EXPECT_EQ(ScrollY(), 400);
    102 }