summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/tests/infrastructure/testdriver/actions
diff options
context:
space:
mode:
Diffstat (limited to 'testing/web-platform/tests/infrastructure/testdriver/actions')
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/actionsWithKeyPressed.html66
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/crossOrigin.sub.html21
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/elementPosition.html43
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/elementTiming.html69
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/eventOrder.html61
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/iframe.html35
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/iframeChild.html2
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/mouseClickCount.html54
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiDevice.html36
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPoints.html68
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseFirstPoint.html56
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseSecondPoint.html69
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsSimultaneousMove.html58
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsTwoTouchStarts.html58
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsWithPause.html67
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/pause.html19
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEventProperties.html70
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEvents.html158
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/popup.html25
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/support/actions.html34
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/textEditCommands.html61
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/touchEvents.js11
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/touchPointerEventProperties.html71
-rw-r--r--testing/web-platform/tests/infrastructure/testdriver/actions/wheelScroll.html44
24 files changed, 1256 insertions, 0 deletions
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/actionsWithKeyPressed.html b/testing/web-platform/tests/infrastructure/testdriver/actions/actionsWithKeyPressed.html
new file mode 100644
index 0000000000..3e0795b14a
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/actionsWithKeyPressed.html
@@ -0,0 +1,66 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: actions with key pressed</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test1, div#test2 {
+ position: fixed;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+div#test2 {
+ position: fixed;
+ top: 100px;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: green;
+}
+</style>
+
+<div id="test1">
+</div>
+
+<div id="test2">
+</div>
+
+<script>
+let keys = [];
+
+promise_test(async t => {
+ let test1 = document.getElementById("test1");
+ let test2 = document.getElementById("test2");
+ document.getElementById("test1").addEventListener("click",
+ e => {keys.push(e.getModifierState("Shift"))});
+ document.getElementById("test2").addEventListener("click",
+ e => {keys.push(e.getModifierState("Shift"))});
+
+ let actions = new test_driver.Actions()
+ .keyDown("\uE008")
+ .addTick()
+ .pointerMove(0, 0, {origin: test1})
+ .pointerDown()
+ .pointerUp()
+ .pointerMove(0, 0, {origin: test2})
+ .pointerDown()
+ .pointerUp()
+ .addTick()
+ .keyUp("\uE008")
+ .addTick()
+ .pointerMove(0, 0, {origin: test1})
+ .pointerDown()
+ .pointerUp();
+
+ await actions.send();
+ assert_array_equals(keys, [true, true, false]);
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/crossOrigin.sub.html b/testing/web-platform/tests/infrastructure/testdriver/actions/crossOrigin.sub.html
new file mode 100644
index 0000000000..3f6f3a77f3
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/crossOrigin.sub.html
@@ -0,0 +1,21 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>Actions in cross-origin iframe</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<iframe
+ src="https://{{host}}:{{ports[https][1]}}/infrastructure/testdriver/actions/support/actions.html?parent"></iframe>
+
+<script>
+setup({single_test: true});
+addEventListener("message", (msg) => {
+ if (msg.data === "PASS") {
+ done();
+ } else if (msg.data === "FAIL") {
+ assert_unreached("actions failed")
+ }
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/elementPosition.html b/testing/web-platform/tests/infrastructure/testdriver/actions/elementPosition.html
new file mode 100644
index 0000000000..145852e7b5
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/elementPosition.html
@@ -0,0 +1,43 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: element position</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test {
+ position: fixed;
+ left: -100px;
+ top: -25px;
+ width: 200px;
+ height: 75px;
+ background-color:blue;
+}
+</style>
+
+<div id="test">
+</div>
+
+<script>
+let events = [];
+
+async_test(t => {
+ let test = document.getElementById("test");
+ test.addEventListener("click", e => {
+ events.push(e.clientX);
+ events.push(e.clientY)
+ });
+
+ let div = document.getElementById("test");
+ let actions = new test_driver.Actions()
+ .pointerMove(0, 0, {origin: test})
+ .pointerDown()
+ .pointerUp()
+ .send()
+ .then(t.step_func_done(() => assert_array_equals(events, [50, 25])))
+ .catch(e => t.step_func(() => assert_unreached("Actions sequence failed " + e)));
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/elementTiming.html b/testing/web-platform/tests/infrastructure/testdriver/actions/elementTiming.html
new file mode 100644
index 0000000000..33731e9299
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/elementTiming.html
@@ -0,0 +1,69 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: element timing</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test1, div#test2 {
+ position: fixed;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+div#test2 {
+ display: none;
+ left: -100px;
+ background-color: green;
+}
+</style>
+
+<div id="test1">
+</div>
+
+<div id="test2">
+</div>
+
+<script>
+let events = [];
+
+promise_test(async t => {
+ let test1 = document.getElementById("test1");
+ let test2 = document.getElementById("test2");
+ test1.addEventListener("click",
+ () => {
+ test2.style.display = "block";
+ test2.style.top = "100px";
+ test2.style.left = "0"
+ });
+ test2.addEventListener("click",
+ e => {
+ events.push(e.clientX);
+ events.push(e.clientY);
+ });
+
+ const waitCondition = new Promise((resolve, reject)=>{setTimeout(resolve, 5000);});
+ const test1ClickWatcher = new EventWatcher(t, test1, ["click"], ()=>waitCondition);
+ const test2ClickWatcher = new EventWatcher(t, test2, ["click"], ()=>waitCondition);
+ let waitForClicks = Promise.all([test1ClickWatcher.wait_for(["click"]), test2ClickWatcher.wait_for(["click"])]);
+
+ await new test_driver.Actions()
+ .pointerMove(0, 0, {origin: test1})
+ .pointerDown()
+ .pointerUp()
+ .send();
+ await new test_driver.Actions()
+ .pointerMove(0, 0, {origin: test2})
+ .pointerDown()
+ .pointerUp()
+ .send();
+ await waitForClicks;
+ assert_array_equals(events, [50, 150])
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/eventOrder.html b/testing/web-platform/tests/infrastructure/testdriver/actions/eventOrder.html
new file mode 100644
index 0000000000..1fed285a27
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/eventOrder.html
@@ -0,0 +1,61 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: event order</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<button id="a">Button a</button>
+<button id="b">Button b</button>
+<input id="text-input">
+
+<script>
+// Pointer 1 is added before Pointer 2 so it comes first in the list of sources
+// Therefore its actions happen first
+let events = [];
+
+promise_test(() => {
+ Array.prototype.forEach.call(document.getElementsByTagName("button"),
+ (x) => x.addEventListener("mousedown", () => {events.push(x.id)}));
+
+ let button_a = document.getElementById("a");
+ let button_b = document.getElementById("b");
+ return new test_driver.Actions()
+ .addPointer("pointer1")
+ .addPointer("pointer2")
+ .pointerMove(0, 0, {origin: button_a, sourceName: "pointer1"})
+ .pointerMove(0, 0, {origin: button_b, sourceName: "pointer2"})
+ .pointerDown({sourceName: "pointer2"})
+ .pointerDown({sourceName: "pointer1"})
+ .pointerUp({sourceName: "pointer2"})
+ .pointerUp({sourceName: "pointer1"})
+ .send()
+ .then(() => assert_array_equals(events, ["a", "b"]));
+});
+
+// This test uses a large number of keyboard sources to force race conditions
+// in implementations which incorrectly dispatch events. Despite belonging to
+// the same "tick," each action's initial event should be dispatched in series.
+promise_test(() => {
+ const input = document.getElementById("text-input");
+ const actions = new test_driver.Actions();
+ const code_for_a = "a".charCodeAt(0);
+ const keys = Array.from(Array(26))
+ .map((_, index) => ({
+ sourceName: "keyboard" + index,
+ code: String.fromCharCode(code_for_a + index)
+ }));
+
+ keys.forEach(({sourceName}) => actions.addKeyboard(sourceName));
+ keys.forEach(({code, sourceName}) => actions.keyDown(code, {sourceName}));
+ keys.forEach(({code, sourceName}) => actions.keyUp(code,{sourceName}));
+
+ return test_driver.click(input)
+ .then(() => actions.send())
+ .then(() => {
+ assert_equals(input.value, "abcdefghijklmnopqrstuvwxyz");
+ });
+}, "indivisible actions on the same track dispatch events in series");
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/iframe.html b/testing/web-platform/tests/infrastructure/testdriver/actions/iframe.html
new file mode 100644
index 0000000000..6c64d6f49a
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/iframe.html
@@ -0,0 +1,35 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions on a document in an iframe</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+
+<iframe src="iframeChild.html"></iframe>
+
+<script>
+setup({single_test: true});
+addEventListener("load", async () => {
+ let input = frames[0].document.getElementsByTagName("input")[0];
+ await new test_driver.Actions()
+ .pointerMove(0, 0, {origin: input})
+ .pointerDown()
+ .pointerUp()
+ .send();
+ await new test_driver.Actions()
+ .setContext(frames[0])
+ .keyDown("P")
+ .keyUp("P")
+ .keyDown("A")
+ .keyUp("A")
+ .keyDown("S")
+ .keyUp("S")
+ .keyDown("S")
+ .keyUp("S")
+ .send();
+ assert_equals(input.value, "PASS");
+ done();
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/iframeChild.html b/testing/web-platform/tests/infrastructure/testdriver/actions/iframeChild.html
new file mode 100644
index 0000000000..a46c54a7b7
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/iframeChild.html
@@ -0,0 +1,2 @@
+<!doctype html>
+<input type=text>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/mouseClickCount.html b/testing/web-platform/tests/infrastructure/testdriver/actions/mouseClickCount.html
new file mode 100644
index 0000000000..4f02088c5a
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/mouseClickCount.html
@@ -0,0 +1,54 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: test the mouse click counts at different cases</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test {
+ position: fixed;
+ touch-action: none;
+ top: 5px;
+ left: 5px;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+</style>
+
+<div id="test">
+</div>
+
+<script>
+let clickCountList = [];
+
+async_test(t => {
+ let test = document.getElementById("test");
+ test.addEventListener("click", e => {
+ clickCountList.push(e.detail);
+ });
+
+ let div = document.getElementById("test");
+ var actions = new test_driver.Actions();
+ actions.pointerMove(0, 0, {origin: test})
+ .pointerDown()
+ .pointerUp()
+ .pointerDown()
+ .pointerUp()
+ .pointerMove(15, 15, {origin: test})
+ .pointerDown()
+ .pointerUp()
+ .pointerDown()
+ .pointerUp()
+ .pointerDown()
+ .pointerUp()
+ .send()
+ .then(t.step_func_done(() => {
+ let expectedClickCountList = [1, 2, 1, 2, 3];
+ assert_array_equals(clickCountList, expectedClickCountList);
+ })).catch(e => t.step_func(() => assert_unreached("Actions sequence failed " + e)));
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiDevice.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiDevice.html
new file mode 100644
index 0000000000..6bc0fa218d
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiDevice.html
@@ -0,0 +1,36 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: multiple devices</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<input type="text" id="text"></input>
+
+<script>
+async_test(t => {
+ let text_box = document.getElementById("text");
+ let actions = new test_driver.Actions()
+ .pointerMove(0, 0, {origin: text_box})
+ .pointerDown()
+ .pointerUp()
+ .addTick()
+ .keyDown("p")
+ .keyUp("p")
+ .keyDown("a")
+ .keyUp("a")
+ .keyDown("s")
+ .keyUp("s")
+ .keyDown("s")
+ .keyUp("s");
+
+ actions.send()
+ .then(() => {
+ assert_equals(text_box.value, "pass");
+ t.done();
+ })
+ .catch(t.unreached_func("Actions sequence failed"));
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPoints.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPoints.html
new file mode 100644
index 0000000000..64aa429631
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPoints.html
@@ -0,0 +1,68 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with one moving one pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="touchEvents.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+promise_test(async t => {
+ const test1 = document.getElementById("test1");
+
+ const events = [];
+ addPointerEventListeners(t, test1, events);
+
+ const actions = new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerDown({sourceName: "touchPointer2"})
+ .pointerMove(0, 10, {origin: test1, sourceName: "touchPointer1"})
+ .pointerUp({sourceName: "touchPointer1"})
+ .pointerUp({sourceName: "touchPointer2"});
+
+ await actions.send()
+
+ eventEquals(events[0], {type: "pointerdown", pointerId: 2, clientX: 50, clientY: 50});
+ eventEquals(events[1], {type: "pointerdown", pointerId: 3, clientX: 60, clientY: 50});
+ // Allow one or two pointermove events
+ let index = 3;
+ const moveEvents = [events[2]];
+ if (events[3].type === "pointermove") {
+ index += 1;
+ moveEvents.push(events[3]);
+ }
+ for (const event of moveEvents) {
+ if (event.pointerId === 2) {
+ eventEquals(event, {type: "pointermove", clientX: 50, clientY: 60});
+ } else {
+ eventEquals(event, {type: "pointermove", pointerId: 3, clientX: 60, clientY: 50});
+ }
+ }
+ let remainingEvents = events.slice(index);
+ assert_equals(remainingEvents.length, 2);
+ eventEquals(remainingEvents[0], {type: "pointerup", pointerId: 2, clientX: 50, clientY: 60});
+ eventEquals(remainingEvents[1], {type: "pointerup", pointerId: 3, clientX: 60, clientY: 50});
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseFirstPoint.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseFirstPoint.html
new file mode 100644
index 0000000000..41027beb67
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseFirstPoint.html
@@ -0,0 +1,56 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with one moving one pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="touchEvents.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+promise_test(async t => {
+ let test1 = document.getElementById("test1");
+ const events = [];
+ addPointerEventListeners(t, test1, events);
+
+ await new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerDown({sourceName: "touchPointer2"})
+ .pointerUp({sourceName: "touchPointer1"})
+ .pointerMove(10, 10, {origin: test1, sourceName: "touchPointer2"})
+ .pointerUp({sourceName: "touchPointer2"})
+ .send();
+
+ const expected = [{type: "pointerdown", pointerId: 2, clientX: 50, clientY: 50},
+ {type: "pointerdown", pointerId: 3, clientX: 60, clientY: 50},
+ {type: "pointerup", pointerId: 2},
+ {type: "pointermove", pointerId: 3, clientX: 60, clientY:60},
+ {type: "pointerup", pointerId: 3}];
+
+ assert_equals(events.length, expected.length, "Expected number of events");
+ for (let i=0; i<expected.length; i++) {
+ eventEquals(events[i], expected[i]);
+ }
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseSecondPoint.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseSecondPoint.html
new file mode 100644
index 0000000000..58a2263f5b
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsReleaseSecondPoint.html
@@ -0,0 +1,69 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with one moving one pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="touchEvents.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+promise_test(async t => {
+ let test1 = document.getElementById("test1");
+
+ const events = [];
+ addPointerEventListeners(t, test1, events);
+
+ await new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerDown({sourceName: "touchPointer2"})
+ .pointerMove(10, 10, {origin: test1, sourceName: "touchPointer1"})
+ .addTick()
+ .pointerUp({sourceName: "touchPointer2"})
+ .addTick()
+ .pointerUp({sourceName: "touchPointer1"})
+ .send();
+
+ eventEquals(events[0], {type: "pointerdown", pointerId: 2, clientX: 50, clientY: 50});
+ eventEquals(events[1], {type: "pointerdown", pointerId: 3, clientX: 60, clientY: 50});
+ // Allow one or two pointermove events
+ let index = 3;
+ const moveEvents = [events[2]];
+ if (events[3].type === "pointermove") {
+ index += 1;
+ moveEvents.push(events[3]);
+ }
+ for (const event of moveEvents) {
+ if (event.pointerId === 2) {
+ eventEquals(event, {type: "pointermove", clientX: 60, clientY: 60});
+ } else {
+ eventEquals(event, {type: "pointermove", pointerId: 3, clientX: 60, clientY: 50});
+ }
+ }
+ let remainingEvents = events.slice(index);
+ assert_equals(remainingEvents.length, 2);
+ eventEquals(remainingEvents[0], {type: "pointerup", pointerId: 3, clientX: 60, clientY: 50});
+ eventEquals(remainingEvents[1], {type: "pointerup", pointerId: 2, clientX: 60, clientY: 60});
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsSimultaneousMove.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsSimultaneousMove.html
new file mode 100644
index 0000000000..5be5b44896
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsSimultaneousMove.html
@@ -0,0 +1,58 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with both moving</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="touchEvents.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+promise_test(async t => {
+ let test1 = document.getElementById("test1");
+
+ const events = [];
+ addPointerEventListeners(t, test1, events);
+
+ await new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerDown({sourceName: "touchPointer2"})
+ .pointerMove(0, 10, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 10, {origin: test1, sourceName: "touchPointer2"})
+ .pointerUp({sourceName: "touchPointer1"})
+ .pointerUp({sourceName: "touchPointer2"})
+ .send();
+
+ const expected = [{type: "pointerdown", pointerId: 2, clientX: 50, clientY: 50},
+ {type: "pointerdown", pointerId: 3, clientX: 60, clientY: 50},
+ {type: "pointermove", pointerId: 2, clientX: 50, clientY: 60},
+ {type: "pointermove", pointerId: 3, clientX: 60, clientY: 60},
+ {type: "pointerup", pointerId: 2, clientX: 50, clientY: 60},
+ {type: "pointerup", pointerId: 3, clientX: 60, clientY: 60}];
+ assert_equals(events.length, expected.length);
+ for (let i=0; i<expected.length; i++) {
+ eventEquals(events[i], expected[i]);
+ }
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsTwoTouchStarts.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsTwoTouchStarts.html
new file mode 100644
index 0000000000..06f48ebc38
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsTwoTouchStarts.html
@@ -0,0 +1,58 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with one moving one pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+let event_type = [];
+let event_id = [];
+
+promise_test(async t => {
+ const test1 = document.getElementById("test1");
+ const handleEvent = e => {
+ event_type.push(e.type);
+ event_id.push(e.pointerId);
+ }
+ test1.addEventListener("pointerdown", handleEvent);
+ test1.addEventListener("pointerup", handleEvent);
+ test1.addEventListener("pointermove", handleEvent);
+
+ let actions = new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerMove(0, 5, {origin: test1, sourceName: "touchPointer1"})
+ .addTick()
+ .pointerDown({sourceName: "touchPointer2"})
+ .addTick()
+ .pointerUp({sourceName: "touchPointer1"})
+ .pointerUp({sourceName: "touchPointer2"});
+
+ await actions.send()
+
+ assert_array_equals(event_type, ["pointerdown", "pointermove", "pointerdown", "pointerup", "pointerup"]);
+ assert_array_equals(event_id, [2, 2, 3, 2, 3]);
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsWithPause.html b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsWithPause.html
new file mode 100644
index 0000000000..6b89d74c65
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/multiTouchPointsWithPause.html
@@ -0,0 +1,67 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: two touch points with one moving one pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="touchEvents.js"></script>
+
+<style>
+div#test1{
+ position: fixed;
+ touch-action: none;
+ top: 0;
+ left: 0;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="test1">
+</div>
+
+<script>
+
+promise_test(async t => {
+ const test1 = document.getElementById("test1");
+ const events = [];
+ addPointerEventListeners(t, test1, events);
+ await new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .addPointer("touchPointer2", "touch")
+ .pointerMove(0, 0, {origin: test1, sourceName: "touchPointer1"})
+ .pointerMove(10, 0, {origin: test1, sourceName: "touchPointer2"})
+ .pointerDown({sourceName: "touchPointer1"})
+ .pointerDown({sourceName: "touchPointer2"})
+ .pause(0, "pointer", {sourceName: "touchPointer1"})
+ .pointerMove(0, 10, {origin: test1, sourceName: "touchPointer2"})
+ .pointerUp({sourceName: "touchPointer1"})
+ .pointerUp({sourceName: "touchPointer2"})
+ .send();
+
+ eventEquals(events[0], {type: "pointerdown", pointerId: 2, clientX: 50, clientY: 50});
+ eventEquals(events[1], {type: "pointerdown", pointerId: 3, clientX: 60, clientY: 50});
+ // Allow one or two pointermove events
+ let index = 3;
+ const moveEvents = [events[2]];
+ if (events[3].type === "pointermove") {
+ index += 1;
+ moveEvents.push(events[3]);
+ }
+ for (const event of moveEvents) {
+ if (event.pointerId === 2) {
+ eventEquals(event, {type: "pointermove", clientX: 50, clientY: 50});
+ } else {
+ eventEquals(event, {type: "pointermove", pointerId: 3, clientX: 50, clientY: 60});
+ }
+ }
+ let remainingEvents = events.slice(index);
+ assert_equals(remainingEvents.length, 2);
+ eventEquals(remainingEvents[0], {type: "pointerup", pointerId: 2, clientX: 50, clientY: 50});
+ eventEquals(remainingEvents[1], {type: "pointerup", pointerId: 3, clientX: 50, clientY: 60});
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/pause.html b/testing/web-platform/tests/infrastructure/testdriver/actions/pause.html
new file mode 100644
index 0000000000..ec33c51102
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/pause.html
@@ -0,0 +1,19 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<meta name="timeout" content="long">
+<title>TestDriver actions: pause</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<script>
+promise_test(() => {
+ let t0 = performance.now();
+ return new test_driver.Actions()
+ .addTick(1000)
+ .send()
+ .then(() => assert_greater_than(performance.now() - t0, 1000));
+})
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEventProperties.html b/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEventProperties.html
new file mode 100644
index 0000000000..05f85d299e
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEventProperties.html
@@ -0,0 +1,70 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: pointerevent properties of pen type</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test {
+ position: fixed;
+ touch-action: none;
+ top: 5px;
+ left: 5px;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+</style>
+
+<div id="test">
+</div>
+
+<script>
+let pointerDownEvent;
+let pointerMoveEvent;
+let receivedPointerDown = false;
+
+promise_test(async t => {
+ let test = document.getElementById("test");
+ var eventList = ['pointermove', 'pointerdown'];
+ for (eventType of eventList) {
+ test.addEventListener(eventType, e => {
+ if (e.type == 'pointerdown') {
+ receivedPointerDown = true;
+ pointerDownEvent = e;
+ }
+ if (e.type == 'pointermove' && receivedPointerDown)
+ pointerMoveEvent = e;
+ });
+ }
+
+ let div = document.getElementById("test");
+ await new test_driver.Actions()
+ .addPointer("penPointer1", "pen")
+ .pointerMove(0, 0, {origin: test})
+ .pointerDown({pressure:0.36, tiltX:-72, tiltY:9, twist:86})
+ .pointerMove(15, 0, {origin: test})
+ .pointerUp()
+ .send();
+
+ assert_equals(pointerDownEvent.type, "pointerdown");
+ assert_equals(pointerDownEvent.pointerType, "pen");
+ assert_equals(pointerDownEvent.width, 1);
+ assert_equals(pointerDownEvent.height, 1);
+ assert_equals(Math.round(pointerDownEvent.pressure * 100) / 100, 0.36);
+ assert_equals(pointerDownEvent.tiltX, -72);
+ assert_equals(pointerDownEvent.tiltY, 9);
+ assert_equals(pointerDownEvent.twist, 86);
+ assert_equals(pointerMoveEvent.type, "pointermove");
+ assert_equals(pointerMoveEvent.pointerType, "pen");
+ assert_equals(pointerMoveEvent.width, 1);
+ assert_equals(pointerMoveEvent.height, 1);
+ assert_equals(Math.round(pointerMoveEvent.pressure * 100) / 100, 0.5);
+ assert_equals(pointerMoveEvent.tiltX, 0);
+ assert_equals(pointerMoveEvent.tiltY, 0);
+ assert_equals(pointerMoveEvent.twist, 0);
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEvents.html b/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEvents.html
new file mode 100644
index 0000000000..f885ad501a
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/penPointerEvents.html
@@ -0,0 +1,158 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: pointerevent properties of pen type</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="/pointerevents/pointerevent_support.js"></script>
+
+<style>
+div#test {
+ position: fixed;
+ touch-action: none;
+ top: 5px;
+ left: 5px;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+</style>
+
+<div id="test">
+</div>
+
+<script>
+let eventList = [];
+
+promise_test(async t => {
+ let test = document.getElementById("test");
+ [
+ 'pointerover', 'pointerenter', 'pointermove', 'pointerdown', 'pointerup',
+ 'pointerout', 'pointerleave'
+ ].forEach(eventType => {
+ test.addEventListener(eventType, e => {
+ eventList.push(e);
+ });
+ });
+
+ let div = document.getElementById("test");
+ let actions = new test_driver.Actions()
+ .addPointer("penPointer1", "pen")
+ // Force initial position to be outside the test element
+ .pointerMove(0, 0)
+ // Prevent coalescence of move events.
+ .pointerDown()
+ .pointerUp()
+ // Trigger over and enter events.
+ .pointerMove(10, 10)
+ // Toggle of pen-contact state between each move to prevent coalescence of
+ // move events.
+ .pointerDown()
+ .pointerMove(0, 0, {origin: test})
+ .pointerUp()
+ .pointerMove(15, 0, {origin: test})
+ .pointerDown()
+ .pointerMove(30, 0, {origin: test})
+ .pointerUp()
+ .pointerMove(0, 0);
+ await actions.send()
+
+ const expectedEvents = [
+ {
+ type: 'pointerover',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE
+ },
+ {
+ type: 'pointerenter',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE
+ },
+ { type: 'pointermove',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 10,
+ clientY: 10
+ },
+ {
+ type: 'pointerdown',
+ button: ButtonChange.PEN_CONTACT,
+ buttons: ButtonsBitfield.PEN_CONTACT,
+ clientX: 10,
+ clientY: 10
+ },
+ {
+ type: 'pointermove',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.PEN_CONTACT,
+ clientX: 55,
+ clientY: 55
+ },
+ {
+ type: 'pointerup',
+ button: ButtonChange.PEN_CONTACT,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 55,
+ clientY: 55
+ },
+ {
+ type: 'pointermove',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 70,
+ clientY: 55
+ },
+ {
+ type: 'pointerdown',
+ button: ButtonChange.PEN_CONTACT,
+ buttons: ButtonsBitfield.PEN_CONTACT,
+ clientX: 70,
+ clientY: 55
+ },
+ {
+ type: 'pointermove',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.PEN_CONTACT,
+ clientX: 85,
+ clientY: 55
+ },
+ {
+ type: 'pointerup',
+ button: ButtonChange.PEN_CONTACT,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 85,
+ clientY: 55
+ },
+ {
+ type: 'pointerout',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 0,
+ clientY: 0
+ },
+ {
+ type: 'pointerleave',
+ button: ButtonChange.NONE,
+ buttons: ButtonsBitfield.NONE,
+ clientX: 0,
+ clientY: 0
+ },
+ ];
+
+ for (let i = 0; i < expectedEvents.length; i++) {
+ const expectedValue = expectedEvents[i];
+ const actualValue = eventList[i];
+ assert_true(!!actualValue, `Missing $[i}-th event`);
+ assert_equals(actualValue.pointerType, 'pen', 'Unexpected pointer type');
+ for (key in expectedValue) {
+ assert_equals(actualValue[key], expectedValue[key],
+ `Mismatch in event[${i}].${key}`);
+ }
+ }
+
+ assert_equals(eventList.length, expectedEvents.length,
+ 'Unexpected number of events');
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/popup.html b/testing/web-platform/tests/infrastructure/testdriver/actions/popup.html
new file mode 100644
index 0000000000..62140d6381
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/popup.html
@@ -0,0 +1,25 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>Actions in popup</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<script>
+ promise_test((t) => new Promise((resolve, reject) => {
+ addEventListener("message", (msg) => {
+ if (msg.data === "PASS") {
+ resolve();
+ } else if (msg.data === "FAIL") {
+ reject("actions failed");
+ }
+ });
+ addEventListener("click", (event) => {
+ reject("Test window received click meant for the popup");
+ });
+
+ let popup = window.open("support/actions.html?popup", "_blank");
+ t.add_cleanup(() => popup.close());
+ }), "Actions go to the popup and not the test window");
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/support/actions.html b/testing/web-platform/tests/infrastructure/testdriver/actions/support/actions.html
new file mode 100644
index 0000000000..767368b3ab
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/support/actions.html
@@ -0,0 +1,34 @@
+<!doctype html>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+
+<input type=text>
+<script>
+let input = document.getElementsByTagName("input")[0];
+addEventListener("load", async () => {
+ let searchParams = new URLSearchParams(location.search);
+ let testContext = searchParams.has("parent") ? parent : opener;
+ test_driver.set_test_context(testContext);
+ await new test_driver.Actions()
+ .pointerMove(0, 0, {origin: input})
+ .pointerDown()
+ .pointerUp()
+ .send();
+ await new test_driver.Actions()
+ .keyDown("P")
+ .keyUp("P")
+ .keyDown("A")
+ .keyUp("A")
+ .keyDown("S")
+ .keyUp("S")
+ .keyDown("S")
+ .keyUp("S")
+ .send();
+ if (input.value === "PASS") {
+ test_driver.message_test("PASS", "*");
+ } else {
+ test_driver.message_test("FAIL", "*");
+ }
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/textEditCommands.html b/testing/web-platform/tests/infrastructure/testdriver/actions/textEditCommands.html
new file mode 100644
index 0000000000..0bc533ecb0
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/textEditCommands.html
@@ -0,0 +1,61 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: text edit commands</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div { padding:0px; margin: 0px; }
+</style>
+<body>
+ <div>
+ <input type="text" id="text1" value="Hello World" />
+ <input type="text" id="text2">
+ </div>
+</body>
+<script>
+async_test(t => {
+ let text1 = document.getElementById("text1");
+ let text2 = document.getElementById("text2");
+ text1.addEventListener("click", function() {
+ let text1 = document.getElementById("text1");
+ text1.value="new text";
+ });
+
+ const ctrl_key = "\uE009";
+ const cmd_key = "\uE03D";
+ let edit_command_key = ctrl_key;
+ if(navigator.platform.includes('Mac'))
+ edit_command_key = cmd_key;
+
+ let actions = new test_driver.Actions()
+ .pointerMove(0, 0, {origin: text1})
+ .pointerDown()
+ .pointerUp()
+ .addTick()
+ .keyDown(edit_command_key)
+ .keyDown("a")
+ .keyUp("a")
+ .keyDown("x")
+ .keyUp("x")
+ .keyUp(edit_command_key)
+ .addTick()
+ .pointerMove(0, 0, {origin: text2})
+ .pointerDown()
+ .pointerUp()
+ .keyDown(edit_command_key)
+ .keyDown("v")
+ .keyUp("v")
+ .keyUp(edit_command_key);
+
+ actions.send()
+ .then(t.step_func_done(() => {
+ assert_equals(text1.value, "");
+ assert_equals(text2.value, "new text");
+ }))
+ .catch(e => t.step_func(() => assert_unreached("Actions sequence failed " + e)));
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/touchEvents.js b/testing/web-platform/tests/infrastructure/testdriver/actions/touchEvents.js
new file mode 100644
index 0000000000..c1213b6693
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/touchEvents.js
@@ -0,0 +1,11 @@
+function eventEquals(e, expected) {
+ for (const prop of Object.keys(expected)) {
+ assert_equals(e[prop], expected[prop], `Event ${e.type} pointerId ${e.pointerId} property ${prop}`);
+ }
+}
+
+function addPointerEventListeners(test, target, events) {
+ for (const event of ["pointerup", "pointerdown", "pointermove"]) {
+ target.addEventListener(event, test.step_func(e => events.push(e)));
+ }
+}
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/touchPointerEventProperties.html b/testing/web-platform/tests/infrastructure/testdriver/actions/touchPointerEventProperties.html
new file mode 100644
index 0000000000..085889949e
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/touchPointerEventProperties.html
@@ -0,0 +1,71 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: pointerevent properties of touch type</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+div#test {
+ position: fixed;
+ touch-action: none;
+ top: 5px;
+ left: 5px;
+ width: 100px;
+ height: 100px;
+ background-color: blue;
+}
+</style>
+
+<div id="test">
+</div>
+
+<script>
+let pointerDownEvent;
+let pointerMoveEvent;
+let receivedPointerDown = false;
+
+async_test(t => {
+ let test = document.getElementById("test");
+ var eventList = ['pointermove', 'pointerdown'];
+ for (eventType of eventList) {
+ test.addEventListener(eventType, e => {
+ if (e.type == 'pointerdown') {
+ receivedPointerDown = true;
+ pointerDownEvent = e;
+ }
+ if (e.type == 'pointermove' && receivedPointerDown)
+ pointerMoveEvent = e;
+ });
+ }
+
+ let div = document.getElementById("test");
+ let actions = new test_driver.Actions()
+ .addPointer("touchPointer1", "touch")
+ .pointerMove(0, 0, {origin: test})
+ .pointerDown({width:23, height:31, pressure:0.78})
+ .pointerMove(15, 0, {origin: test, width:39, height:35, pressure:0.91})
+ .pointerUp()
+ .send()
+ .then(t.step_func_done(() => {
+ assert_equals(pointerDownEvent.type, "pointerdown");
+ assert_equals(pointerDownEvent.pointerType, "touch");
+ assert_equals(pointerDownEvent.width, 23);
+ assert_equals(pointerDownEvent.height, 31);
+ assert_equals(Math.round(pointerDownEvent.pressure * 100) / 100, 0.78);
+ assert_equals(pointerDownEvent.tiltX, 0);
+ assert_equals(pointerDownEvent.tiltY, 0);
+ assert_equals(pointerDownEvent.twist, 0);
+ assert_equals(pointerMoveEvent.type, "pointermove");
+ assert_equals(pointerMoveEvent.pointerType, "touch");
+ assert_equals(pointerMoveEvent.width, 39);
+ assert_equals(pointerMoveEvent.height, 35);
+ assert_equals(Math.round(pointerMoveEvent.pressure * 100) / 100, 0.91);
+ assert_equals(pointerMoveEvent.tiltX, 0);
+ assert_equals(pointerMoveEvent.tiltY, 0);
+ assert_equals(pointerMoveEvent.twist, 0);
+ })).catch(e => t.step_func(() => assert_unreached("Actions sequence failed " + e)));
+});
+</script>
diff --git a/testing/web-platform/tests/infrastructure/testdriver/actions/wheelScroll.html b/testing/web-platform/tests/infrastructure/testdriver/actions/wheelScroll.html
new file mode 100644
index 0000000000..0447c17ef9
--- /dev/null
+++ b/testing/web-platform/tests/infrastructure/testdriver/actions/wheelScroll.html
@@ -0,0 +1,44 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+<title>TestDriver actions: wheel scroll</title>
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<script src="/resources/testdriver.js"></script>
+<script src="/resources/testdriver-actions.js"></script>
+<script src="/resources/testdriver-vendor.js"></script>
+
+<style>
+#container {
+ width: 200px;
+ height: 200px;
+ overflow: scroll;
+}
+
+#content {
+ width: 600px;
+ height: 1000px;
+ background-color: blue;
+}
+
+</style>
+
+<div id="container">
+ <div id="content"></div>
+</div>
+
+<script>
+let event_type = [];
+let event_id = [];
+
+promise_test(async t => {
+ let container = document.getElementById("container");
+ container.addEventListener("wheel",
+ e => {event_type.push(e.type);});
+
+ let actions = new test_driver.Actions()
+ .scroll(0, 0, 0, 50, {origin: container});
+
+ await actions.send()
+ assert_array_equals(event_type, ["wheel"]);
+});
+</script>