Add RTL tests for cc scrolling

Two existing tests are made agnostic of direction, and re-run with RTL enabled.

Bug: 959437
Change-Id: Ie9dd5c92754bd21937cb56967a6d9948f9a28087
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/3597097
Reviewed-by: Rahul Arakeri <arakeri@microsoft.com>
Commit-Queue: Claire Chambers <clchambers@microsoft.com>
Cr-Commit-Position: refs/heads/main@{#999630}
diff --git a/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar-thumb.html b/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar-thumb.html
index 0c9ad8e8..b1d16ec 100644
--- a/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar-thumb.html
+++ b/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar-thumb.html
@@ -45,13 +45,16 @@
   const SCROLL_CORNER = TRACK_WIDTH;
   const SCROLL_DELTA = 50;
 
-  promise_test (async () => {
+  async function testNonScrolls() {
     await waitForCompositorCommit();
     resetScrollOffset(standardDivFast);
 
+    // Direction: rtl changes the x-wise position of the vertical scrollbar
+    const rtl = standardDivFast.style.direction === "rtl";
+
     // Testing the vertical scrollbar thumb.
-    let x = standardRectFast.right - TRACK_WIDTH / 2;
-    let y = standardRectFast.top + (platform == "mac" ? 0 : BUTTON_WIDTH) + 2;
+    const x = rtl ? standardRectFast.left + TRACK_WIDTH / 2 : standardRectFast.right - TRACK_WIDTH / 2;
+    const y = standardRectFast.top + (platform == "mac" ? 0 : BUTTON_WIDTH) + 2;
 
     await mouseMoveTo(x, y);
     await mouseDownAt(x, y);
@@ -64,14 +67,17 @@
     assert_equals(standardDivFast.scrollTop, 0, "Vertical thumb drag beyond the track and back should not cause a scroll.");
 
     await mouseUpAt(x, y);
-  }, "Test thumb drags beyond scrollbar track.");
+  }
 
-  promise_test (async () => {
+  async function testThumbScrolls() {
     await waitForCompositorCommit();
     resetScrollOffset(standardDivFast);
 
+    // Direction: rtl changes the x-wise position of the vertical scrollbar
+    const rtl = standardDivFast.style.direction === "rtl";
+
     // Testing the vertical scrollbar thumb.
-    let x = standardRectFast.right - TRACK_WIDTH / 2;
+    let x = rtl ? standardRectFast.left + TRACK_WIDTH / 2 : standardRectFast.right - TRACK_WIDTH / 2;
     let y = standardRectFast.top + (platform == "mac" ? 0 : BUTTON_WIDTH) + 2;
     let asc_increments = [15, 10, 7, 6, 2];
     let asc_offsets = {linux: [549, 915, 915, 915, 915], win: [361, 601, 770, 915, 915], mac: [211, 351, 450, 534, 563]}[platform];
@@ -103,6 +109,24 @@
 
     // Since the horizontal scrolling is essentially the same codepath as vertical,
     // this need not be tested in the interest of making the test run faster.
-  }, "Test mouse drags in intervals on non-custom composited div scrollbar thumb.");
+  }
+
+  function ltr(test) {
+    return async function () {
+      standardDivFast.style.direction = "ltr";
+      await test();
+    };
+  }
+  function rtl(test) {
+    return async function () {
+      standardDivFast.style.direction = "rtl";
+      await test();
+    };
+  }
+
+  promise_test(ltr(testNonScrolls), "Test thumb drags beyond scrollbar track.");
+  promise_test(ltr(testThumbScrolls), "Test mouse drags in intervals on non-custom composited div scrollbar thumb.");
+  promise_test(rtl(testNonScrolls), "Test thumb drags beyond scrollbar track. (RTL)");
+  promise_test(rtl(testThumbScrolls), "Test mouse drags in intervals on non-custom composited div scrollbar thumb. (RTL)");
 }
 </script>
diff --git a/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar.html b/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar.html
index bb63248..dee2967 100644
--- a/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar.html
+++ b/third_party/blink/web_tests/fast/scrolling/scrollbars/mouse-scrolling-on-div-scrollbar.html
@@ -43,7 +43,7 @@
       "This test assumes that the height and width of 'standardDivFast' are equivalent. If this changes please update SCROLL_AMOUNT to be X/Y specific");
   const SCROLL_AMOUNT = getScrollbarButtonScrollDelta(standardDivFast).y;
 
-  promise_test (async () => {
+  async function testArrows() {
     // Scrollbars on Mac don't have arrows. This test is irrelevant.
     if(navigator.userAgent.includes("Mac OS X"))
       return;
@@ -51,67 +51,120 @@
     await waitForCompositorCommit();
     resetScrollOffset(standardDivFast);
 
+    // For testing on RTL divs, two things are different. The vertical scrollbar is on the opposite side,
+    // including the scroll corner. Horizontal scrolling on RTL starts at 0 for the rightmost position
+    // and counts downwards into the negatives.
+    const rtl = standardDivFast.style.direction === "rtl";
+
     // Click on the Down arrow for standardRectFast.
-    let x = standardRectFast.right - BUTTON_WIDTH / 2;
+    let x = rtl ? standardRectFast.left + BUTTON_WIDTH / 2 : standardRectFast.right - BUTTON_WIDTH / 2;
     let y = standardRectFast.bottom - SCROLL_CORNER - BUTTON_WIDTH / 2;
     await mouseClickOn(x, y);
     await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollTop;});
     assert_equals(standardDivFast.scrollTop, SCROLL_AMOUNT, "Pressing the down arrow didn't scroll.");
 
     // Click on the Up arrow for standardRectFast.
-    x = standardRectFast.right - BUTTON_WIDTH / 2;
+    x = rtl ? standardRectFast.left + BUTTON_WIDTH / 2 : standardRectFast.right - BUTTON_WIDTH / 2;
     y = standardRectFast.top + BUTTON_WIDTH / 2;
     await mouseClickOn(x, y);
     await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollTop;});
     assert_equals(standardDivFast.scrollTop, 0, "Pressing the up arrow didn't scroll.");
 
-    // Click on the Right arrow for standardRectFast.
-    x = standardRectFast.right - SCROLL_CORNER - BUTTON_WIDTH / 2;
-    y = standardRectFast.bottom - BUTTON_WIDTH / 2;
-    await mouseClickOn(x, y);
-    await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
-    assert_equals(standardDivFast.scrollLeft, SCROLL_AMOUNT, "Pressing the right arrow didn't scroll.");
+    async function scrollRight() {
+      // Click on the Right arrow for standardRectFast.
+      x = rtl ? standardRectFast.right - BUTTON_WIDTH / 2 : standardRectFast.right - SCROLL_CORNER - BUTTON_WIDTH / 2;
+      y = standardRectFast.bottom - BUTTON_WIDTH / 2;
+      await mouseClickOn(x, y);
+      await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
+      assert_equals(standardDivFast.scrollLeft, rtl ? 0 : SCROLL_AMOUNT, "Pressing the right arrow didn't scroll.");
+    }
 
-    // Click on the Left arrow for standardRectFast.
-    x = standardRectFast.left + BUTTON_WIDTH / 2;
-    y = standardRectFast.bottom - BUTTON_WIDTH / 2;
-    await mouseClickOn(x, y);
-    await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
-    assert_equals(standardDivFast.scrollLeft, 0, "Pressing the left arrow didn't scroll.");
-  }, "Test mouse click on non-custom composited div scrollbar arrows.");
+    async function scrollLeft() {
+      // Click on the Left arrow for standardRectFast.
+      x = rtl ? standardRectFast.left + SCROLL_CORNER + BUTTON_WIDTH / 2 : standardRectFast.left + BUTTON_WIDTH / 2;
+      y = standardRectFast.bottom - BUTTON_WIDTH / 2;
+      await mouseClickOn(x, y);
+      await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
+      assert_equals(standardDivFast.scrollLeft, rtl ? -SCROLL_AMOUNT : 0, "Pressing the left arrow didn't scroll.");
+    }
 
-  promise_test (async () => {
+    //For RTL, horizontal scrollbar starts on the rightmost position, so we need to scroll left first;
+    if (rtl) {
+      await scrollLeft();
+      await scrollRight();
+    } else {
+      await scrollRight();
+      await scrollLeft();
+    }
+  }; //
+
+  async function testTrackparts() {
     await waitForCompositorCommit();
     resetScrollOffset(standardDivFast);
 
+    // For testing on RTL divs, two things are different. The vertical scrollbar is on the opposite side,
+    // including the scroll corner. Horizontal scrolling on RTL starts at 0 for the rightmost position
+    // and counts downwards into the negatives.
+    const rtl = standardDivFast.style.direction === "rtl";
+
     // Click on the track part just above the down arrow.
     assert_equals(standardDivFast.scrollTop, 0, "Div is not at 0 offset.");
-    let x = standardRectFast.right - BUTTON_WIDTH / 2;
+    let x = rtl ? standardRectFast.left + BUTTON_WIDTH / 2 : standardRectFast.right - BUTTON_WIDTH / 2;
     let y = standardRectFast.bottom - SCROLL_CORNER - BUTTON_WIDTH - 2;
     await mouseClickOn(x, y);
     await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollTop;});
     assert_approx_equals(standardDivFast.scrollTop, 74, 1, "Pressing the down trackpart didn't scroll.");
 
     // Click on the track part just below the up arrow.
-    x = standardRectFast.right - BUTTON_WIDTH / 2;
+    x = rtl ? standardRectFast.left + BUTTON_WIDTH / 2 : standardRectFast.right - BUTTON_WIDTH / 2;
     y = standardRectFast.top + BUTTON_WIDTH + 2;
     await mouseClickOn(x, y);
     await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollTop;});
     assert_equals(standardDivFast.scrollTop, 0, "Pressing the up trackpart didn't scroll.");
 
-    // Click on the track part just to the left of the right arrow.
-    x = standardRectFast.right - SCROLL_CORNER - BUTTON_WIDTH - 2;
-    y = standardRectFast.bottom - BUTTON_WIDTH / 2;
-    await mouseClickOn(x, y);
-    await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
-    assert_approx_equals(standardDivFast.scrollLeft, 74, 1, "Pressing the right trackpart didn't scroll.");
+    async function scrollRight() {
+      // Click on the track part just to the left of the right arrow.
+      x = rtl ? standardRectFast.right - BUTTON_WIDTH - 2 : standardRectFast.right - SCROLL_CORNER - BUTTON_WIDTH - 2;
+      y = standardRectFast.bottom - BUTTON_WIDTH / 2;
+      await mouseClickOn(x, y);
+      await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
+      assert_approx_equals(standardDivFast.scrollLeft, rtl ? 0 : 74, 1, "Pressing the right trackpart didn't scroll.");
+    }
 
-    // Click on the track part just to the right of the left arrow.
-    x = standardRectFast.left + BUTTON_WIDTH + 2;
-    y = standardRectFast.bottom - BUTTON_WIDTH / 2;
-    await mouseClickOn(x, y);
-    await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
-    assert_equals(standardDivFast.scrollLeft, 0, "Pressing the left trackpart didn't scroll.");
-  }, "Test mouse click on non-custom composited div scrollbar empty trackparts.");
+    async function scrollLeft() {
+      // Click on the track part just to the right of the left arrow.
+      x = rtl ? standardRectFast.left + SCROLL_CORNER + BUTTON_WIDTH + 2 : standardRectFast.left + BUTTON_WIDTH + 2;
+      y = standardRectFast.bottom - BUTTON_WIDTH / 2;
+      await mouseClickOn(x, y);
+      await waitForAnimationEndTimeBased(() => {return standardDivFast.scrollLeft;});
+      assert_approx_equals(standardDivFast.scrollLeft, rtl ? -74 : 0, 1, "Pressing the left trackpart didn't scroll.");
+    }
+
+    if (rtl) {
+      await scrollLeft();
+      await scrollRight();
+    } else {
+      await scrollRight();
+      await scrollLeft();
+    }
+  }// "Test mouse click on non-custom composited div scrollbar empty trackparts.");
+
+  function ltr(test) {
+    return async function () {
+      standardDivFast.style.direction = "ltr";
+      await test();
+    };
+  }
+  function rtl(test) {
+    return async function () {
+      standardDivFast.style.direction = "rtl";
+      await test();
+    };
+  }
+
+  promise_test(ltr(testArrows), "Test mouse click on non-custom composited div scrollbar arrows.");
+  promise_test(ltr(testTrackparts), "Test mouse click on non-custom composited div scrollbar empty trackparts.");
+  promise_test(rtl(testArrows), "Test mouse click on non-custom composited div scrollbar arrows. (RTL)");
+  promise_test(rtl(testTrackparts), "Test mouse click on non-custom composited div scrollbar empty trackparts. (RTL)");
 }
 </script>