触摸事件 (旧版)
简介
处理旧版 触摸事件 以响应滑动、捏合和点击等手势的 Web 应用程序,可以通过手动调度 TouchEvent 到页面进行测试。以下示例演示了如何使用 locator.dispatch_event() 并传递 Touch 点作为参数。
模拟平移手势
在下面的示例中,我们模拟了预期会移动地图的平移手势。被测应用程序仅使用触摸点的 clientX/clientY
坐标,因此我们仅初始化这些坐标。在更复杂的场景中,如果您的应用程序需要,您可能还需要设置 pageX/pageY/screenX/screenY
。
- 同步
- 异步
from playwright.sync_api import sync_playwright, expect
def pan(locator, deltaX=0, deltaY=0, steps=5):
bounds = locator.bounding_box()
centerX = bounds['x'] + bounds['width'] / 2
centerY = bounds['y'] + bounds['height'] / 2
touches = [{
'identifier': 0,
'clientX': centerX,
'clientY': centerY,
}]
locator.dispatch_event('touchstart', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
for i in range(1, steps + 1):
touches = [{
'identifier': 0,
'clientX': centerX + deltaX * i / steps,
'clientY': centerY + deltaY * i / steps,
}]
locator.dispatch_event('touchmove', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
locator.dispatch_event('touchend')
def test_pan_gesture_to_move_the_map(page):
page.goto('https://www.google.com/maps/place/@37.4117722,-122.0713234,15z', wait_until='commit')
page.get_by_role('button', name='Keep using web').click()
expect(page.get_by_role('button', name='Keep using web')).not_to_be_visible()
met = page.locator('[data-test-id="met"]')
for _ in range(5):
pan(met, 200, 100)
page.screenshot(path="screenshot.png")
with sync_playwright() as p:
browser = p.chromium.launch()
context = browser.new_context(**p.devices['Pixel 7'])
page = context.new_page()
test_pan_gesture_to_move_the_map(page)
browser.close()
from playwright.async_api import async_playwright, expect
async def pan(locator, deltaX=0, deltaY=0, steps=5):
bounds = await locator.bounding_box()
centerX = bounds['x'] + bounds['width'] / 2
centerY = bounds['y'] + bounds['height'] / 2
touches = [{
'identifier': 0,
'clientX': centerX,
'clientY': centerY,
}]
await locator.dispatch_event('touchstart', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
for i in range(1, steps + 1):
touches = [{
'identifier': 0,
'clientX': centerX + deltaX * i / steps,
'clientY': centerY + deltaY * i / steps,
}]
await locator.dispatch_event('touchmove', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
await locator.dispatch_event('touchend')
async def test_pan_gesture_to_move_the_map(page):
await page.goto('https://www.google.com/maps/place/@37.4117722,-122.0713234,15z', wait_until='commit')
await page.get_by_role('button', name='Keep using web').click()
await expect(page.get_by_role('button', name='Keep using web')).not_to_be_visible()
met = page.locator('[data-test-id="met"]')
for _ in range(5):
await pan(met, 200, 100)
await page.screenshot(path="screenshot.png")
async def main():
async with async_playwright() as p:
browser = await p.chromium.launch()
context = await browser.new_context(**p.devices['Pixel 7'])
page = await context.new_page()
await test_pan_gesture_to_move_the_map(page)
await browser.close()
import asyncio
asyncio.run(main())
模拟捏合手势
在下面的示例中,我们模拟了捏合手势,即两个触摸点彼此靠近移动。预计会缩小地图。被测应用程序仅使用触摸点的 clientX/clientY
坐标,因此我们仅初始化这些坐标。在更复杂的场景中,如果您的应用程序需要,您可能还需要设置 pageX/pageY/screenX/screenY
。
- 同步
- 异步
from playwright.sync_api import sync_playwright, expect
def pinch(locator, arg):
bounds = locator.bounding_box()
centerX = bounds['x'] + bounds['width'] / 2
centerY = bounds['y'] + bounds['height'] / 2
deltaX = arg.get('deltaX', 50)
steps = arg.get('steps', 5)
stepDeltaX = deltaX / (steps + 1)
touches = [
{
'identifier': 0,
'clientX': centerX - (deltaX if arg.get('direction') == 'in' else stepDeltaX),
'clientY': centerY,
},
{
'identifier': 1,
'clientX': centerX + (deltaX if arg.get('direction') == 'in' else stepDeltaX),
'clientY': centerY,
},
]
locator.dispatch_event('touchstart', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
for i in range(1, steps + 1):
offset = deltaX - i * stepDeltaX if arg.get('direction') == 'in' else stepDeltaX * (i + 1)
touches = [
{
'identifier': 0,
'clientX': centerX - offset,
'clientY': centerY,
},
{
'identifier': 1,
'clientX': centerX + offset,
'clientY': centerY,
},
]
locator.dispatch_event('touchmove', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
locator.dispatch_event('touchend', {
'touches': [],
'changedTouches': [],
'targetTouches': []
})
def test_pinch_in_gesture_to_zoom_out_the_map(page):
page.goto('https://www.google.com/maps/place/@37.4117722,-122.0713234,15z', wait_until='commit')
page.get_by_role('button', name='Keep using web').click()
expect(page.get_by_role('button', name='Keep using web')).not_to_be_visible()
met = page.locator('[data-test-id="met"]')
for _ in range(5):
pinch(met, {'deltaX': 40, 'direction': 'in'})
page.screenshot(path="screenshot.png")
with sync_playwright() as p:
browser = p.chromium.launch()
context = browser.new_context(**p.devices['Pixel 7'])
page = context.new_page()
test_pinch_in_gesture_to_zoom_out_the_map(page)
browser.close()
from playwright.async_api import async_playwright, expect
async def pinch(locator, arg):
bounds = await locator.bounding_box()
centerX = bounds['x'] + bounds['width'] / 2
centerY = bounds['y'] + bounds['height'] / 2
deltaX = arg.get('deltaX', 50)
steps = arg.get('steps', 5)
stepDeltaX = deltaX / (steps + 1)
touches = [
{
'identifier': 0,
'clientX': centerX - (deltaX if arg.get('direction') == 'in' else stepDeltaX),
'clientY': centerY,
},
{
'identifier': 1,
'clientX': centerX + (deltaX if arg.get('direction') == 'in' else stepDeltaX),
'clientY': centerY,
},
]
await locator.dispatch_event('touchstart', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
for i in range(1, steps + 1):
offset = deltaX - i * stepDeltaX if arg.get('direction') == 'in' else stepDeltaX * (i + 1)
touches = [
{
'identifier': 0,
'clientX': centerX - offset,
'clientY': centerY,
},
{
'identifier': 1,
'clientX': centerX + offset,
'clientY': centerY,
},
]
await locator.dispatch_event('touchmove', {
'touches': touches,
'changedTouches': touches,
'targetTouches': touches
})
await locator.dispatch_event('touchend', {
'touches': [],
'changedTouches': [],
'targetTouches': []
})
async def test_pinch_in_gesture_to_zoom_out_the_map(page):
await page.goto('https://www.google.com/maps/place/@37.4117722,-122.0713234,15z', wait_until='commit')
await page.get_by_role('button', name='Keep using web').click()
await expect(page.get_by_role('button', name='Keep using web')).not_to_be_visible()
met = page.locator('[data-test-id="met"]')
for _ in range(5):
await pinch(met, {'deltaX': 40, 'direction': 'in'})
await page.screenshot(path="screenshot.png")
async def main():
async with async_playwright() as p:
browser = await p.chromium.launch()
context = await browser.new_context(**p.devices['Pixel 7'])
page = await context.new_page()
await test_pinch_in_gesture_to_zoom_out_the_map(page)
await browser.close()
import asyncio
asyncio.run(main())