pointerevent_lostpointercapture_remove_setcapture_node.html (4391B)
1 <!doctype html> 2 <html> 3 <head> 4 <title>Lostpointercapture removing new capture element prevents the new capture</title> 5 <meta name="viewport" content="width=device-width"> 6 <link rel="stylesheet" type="text/css" href="pointerevent_styles.css"> 7 <script src="/resources/testharness.js"></script> 8 <script src="/resources/testharnessreport.js"></script> 9 <script src="/resources/testdriver.js"></script> 10 <script src="/resources/testdriver-actions.js"></script> 11 <script src="/resources/testdriver-vendor.js"></script> 12 <script src="pointerevent_support.js"></script> 13 </head> 14 <body> 15 <input type="button" id="button" value="Set Capture"><br> 16 <div id="target0"></div> 17 <div id="target1"></div> 18 <script type='text/javascript'> 19 "use strict"; 20 21 let target0 = document.getElementById('target0'); 22 let target1 = document.getElementById('target1'); 23 let captureButton = document.getElementById('button'); 24 let targets = [target0, target1, captureButton]; 25 const LOG_EVENT_TYPES = ['pointerover', 'pointerenter', 'pointerdown', 'pointerup', 'pointerout', 'pointerleave', 'gotpointercapture', 'lostpointercapture']; 26 27 promise_test(async (test) => { 28 captureButton.focus(); 29 let events = []; 30 let logEvent = event => events.push(`${event.type}@${event.target.id}`); 31 32 for (const target of targets) { 33 for (const eventType of LOG_EVENT_TYPES) { 34 target.addEventListener(eventType, logEvent); 35 } 36 } 37 38 let finishPromise = getEvent('pointerup', captureButton, test); 39 40 getEvent('pointerdown', captureButton, test).then((event) => { 41 target0.setPointerCapture(event.pointerId); 42 }); 43 // On the first captured move, we'll set capture to target1. 44 getEvent('pointermove', target0, test).then((event) => { 45 target1.setPointerCapture(event.pointerId); 46 }); 47 // But remove the new capture target when we lose capture. 48 getEvent('lostpointercapture', target0, test).then((event) => { 49 target1.remove(); 50 }); 51 getEvent('gotpointercapture', target1, test).then((event) => { 52 assert_unreached("target1 is removed and should never get pointer capture."); 53 }); 54 55 // Inject mouse inputs. 56 // 57 // TODO(crbug.com/40942362): Ideally the action sequence below needs to dispatch 58 // only single a pointermove event between the pointerdown/up pair. Blink needs 59 // an additional pointermove to end the test without a timeout because of a 60 // complicated bug. To make sure the new pointermove does not get coalesced 61 // with the first pointermove, we added a pair of chorded down/up events (which 62 // becomes poitermoves) and removed pointermove logging to maintain Blink's test 63 // coverage without violating the test's goal. 64 const actions = new test_driver.Actions(); 65 actions 66 .pointerMove(0, 0, {origin: captureButton}) 67 .pointerDown() 68 .pointerMove(10, 0, {origin: captureButton}) 69 .pointerDown({button: actions.ButtonType.MIDDLE}) 70 .pointerUp({button: actions.ButtonType.MIDDLE}) 71 .pointerUp() 72 .send(); 73 74 await finishPromise; 75 76 assert_equals(events.join(", "), [ 77 // Pointer down on button 78 "pointerover@button", "pointerenter@button", "pointerdown@button", 79 // Captured by target0 80 "pointerout@button", "pointerleave@button", "pointerover@target0", "pointerenter@target0", "gotpointercapture@target0", 81 // Captured by target1, losing capture on target0 which removes target1. 82 "lostpointercapture@target0", "pointerout@target0", "pointerleave@target0", 83 // Uncaptured pointer re-enters button and is lifted. 84 "pointerover@button", "pointerenter@button", "pointerup@button" 85 ].join(", ")); 86 }, "setPointerCapture target removed by lostpointercapture"); 87 </script> 88 </body> 89 </html>