appium2.0+之PointerActions詳解

以下內容在 夜神模擬器 上進行。

一、應用場景

一些針對手勢的操作,比如滑動、長按、拖動等。可以將這些基本手勢組合成一個相對復雜的手勢。

二、使用步驟

  1. 創建觸摸輸入設備(模擬手指操作)

    touch_input = PointerInput(interaction.POINTER_TOUCH, "touch")
    
  2. 創建動作構建器

    action_builder = ActionBuilder(driver, mouse=touch_input)
    
  3. 構建動作
    在這里插入圖片描述

  4. 用perform執行完整動作鏈

    action_builder.perform()
    

三、PointerActions方法詳解

按住Ctrl+左鍵點擊pointer_action,再從跳轉文件Ctrl+左鍵點擊PointerActions,跳轉PointerActions類查看其方法詳細內容

在這里插入圖片描述

在這里插入圖片描述

  • move_to_location(x: int, y: int)

作用:將指針(如手指)移動到屏幕指定坐標(x, y),x:目標位置的 X 坐標(相對于屏幕左上角,單位像素)

  • pointer_down() 按下

pointer_down(self,button=MouseButton.LEFT,width=None,height=None,pressure=None,tangential_pressure=None,tilt_x=None,tilt_y=None,twist=None,altitude_angle=None,azimuth_angle=None,)

對于大多數普通場景(如點擊、滑動),無需復雜參數,僅需指定基礎動作即可:

action.pointer_action.pointer_down()  
  • pointer_up() 抬起

pointer_up(button=MouseButton.LEFT)
  • move_to():基于元素/坐標移動

支持基于元素或坐標的移動,還可通過參數控制移動過程中的觸摸細節(如壓力、角度等):

def move_to(self,element,x=0,y=0,width=None,height=None,pressure=None,tangential_pressure=None,tilt_x=None,tilt_y=None,twist=None,altitude_angle=None,azimuth_angle=None,
)
  1. 基于元素的移動
    以元素為基準,通過 x/y 設定相對偏移(適合元素位置動態變化的場景):

    # 移動到元素的右上角(元素左上角 + 寬偏移,高0)
    element = driver.find_element('id', 'target_btn')
    action.pointer_action.move_to(element=element, x=element.size['width'],  # 相對元素左上角X偏移(等于元素寬度→右上角)y=0  # 相對元素左上角Y偏移0
    )
    
  2. 基于絕對坐標的移動

    action.pointer_action.move_to(x=500, y=300)
    
  3. 結合按下 / 抬起實現滑動
    移動過程中保持按下狀態,實現滑動效果:

    # 從元素A滑動到元素B
    element_a = driver.find_element('id', 'start_point')
    element_b = driver.find_element('id', 'end_point')# 移動到A→按下→移動到B→抬起(完成滑動)
    action.pointer_action.move_to(element=element_a)
    action.pointer_action.pointer_down()  # 按下(開始滑動)
    action.pointer_action.move_to(element=element_b)  # 滑動到B
    action.pointer_action.pointer_up()    # 抬起(結束滑動)
    action.perform()
    
  • move_by 基于當前位置移動

基于相對當前位置移動指針設備,move_by() 是實現連續、精細手勢的核心方法,尤其適合需要模擬人手自然滑動的場景(如滾動列表、拖拽控件等):

def move_by(self,x,y,width=None,height=None,pressure=None,tangential_pressure=None,tilt_x=None,tilt_y=None,twist=None,altitude_angle=None,azimuth_angle=None,
)
  1. 基礎相對移動
# 假設指針當前在(100, 200)位置
action.pointer_action.move_by(x=200, y=100)  # 向右移動200px,向下移動100px→新位置(300, 300)
  1. 按下并連續滑動
    按下并連續滑動(分兩步向上移動):
action.pointer_action.pointer_down()  # 按下(開始滑動)
action.pointer_action.move_by(x=0, y=-300)  # 第一步:向上移動300px(y為負)
action.pointer_action.move_by(x=0, y=-300)  # 第二步:再向上移動300px
action.pointer_action.pointer_up()    # 抬起(結束滑動)
  • move_to_location() 直接移動到屏幕指定絕對坐標位置

def move_to_location(self,x,y,width=None,height=None,pressure=None,tangential_pressure=None,tilt_x=None,tilt_y=None,twist=None,altitude_angle=None,azimuth_angle=None,
)

示例:

# 移動到屏幕(300, 500)位置并點擊
action.pointer_action.move_to_location(x=300, y=500)  # 直接定位到絕對坐標
  • click() 點擊

直接對元素或指定坐標位置執行點擊:

action.pointer_action.click(element)  # 直接點擊元素

若未傳入 element,需先通過 move_to_location() 定位到坐標,再調用 click()

  • context_click()

模擬上下文點擊(通常指鼠標右鍵點擊),主要用于觸發元素的上下文菜單(如桌面端網頁或應用中右鍵點擊元素彈出的菜單)。在移動設備上,此方法通常等效于長按操作(因為移動設備無鼠標右鍵,長按是觸發上下文菜單的常見方式)。

  • click_and_hold() 點擊并按住

常用于拖拽、長按觸發菜單等需要持續按壓的場景:

# 拖拽流程:按住→移動→抬起
action.pointer_action.click_and_hold(element=app_icon)  # 按住圖標
action.pointer_action.move_by(x=200, y=300)  # 向右下方移動
action.pointer_action.release()  # 抬起(釋放圖標)
  • release() 抬起

用于結束之前通過 click_and_hold()pointer_down() 等方法開始的 “按下” 狀態,與 pointer_up 功能基本一致。

  • double_click() 雙擊

double_click(el可選),若無element,則需先定位到目標坐標,再執行雙擊:

# 定位圖片元素并雙擊(如放大圖片)
image = driver.find_element('xpath', '//android.widget.ImageView[@index="0"]')
action.pointer_action.double_click(element=image)  # 雙擊圖片
  • pause(duration: float = 0) 暫停

duration 單位為秒,浮點型。
在動作鏈中插入 pause() 后,Appium 會在執行到該步驟時暫停指定時長,再繼續執行后續動作。主要用于:

  • 模擬長按(按下后暫停一段時間再抬起)。
  • 等待前一個動作生效(如點擊按鈕后等待頁面加載)。
  • 控制手勢速度(如滑動過程中減速)。

示例:

# 分步滑動(每步移動+暫停)
action.pointer_action.move_by(x=0, y=-200)  # 第一步上滑
action.pointer_action.pause(0.3)  # 暫停0.3秒
action.pointer_action.move_by(x=0, y=-200)  # 第二步上滑

四、單點觸控案例

代碼執行前準備

  • 命令行啟動appium服務(版本2.19.0):
appium --address 127.0.0.1 --log-level debug --use-drivers uiautomator2
  • 模擬器打開,命令行adb devices顯示設備已連接
    在這里插入圖片描述

1、點擊/長按wifi設置

#!/usr/bin/env python
# encoding: utf-8
'''
@Author  : 草木零
@Software: PyCharm
@File    : class03_actionBuilder01.py
@Time    : 2025/7/28 17:04
@desc   : 運行多種方法進行 點擊/長按
'''# 案例1:設置里點擊wlan
from time import sleep
from appium import webdriver
from appium.options.android import UiAutomator2Options  # 導入 Android 選項類
from selenium.webdriver.common.actions.action_builder import ActionBuilder
from selenium.webdriver.common.actions.pointer_input import PointerInput
from selenium.webdriver.common.actions import interaction# 手機/模擬器,配置信息
desired_caps = {"platformName": "Android","platformVersion": "7.1.2","deviceName": "127.0.0.1:62001","appPackage": "com.android.settings",# 獲取包名、界面名:adb shell dumpsys window|findstr mCurrentFocus"appActivity": "com.android.settings.Settings","noReset": False
}# 顯式傳入 options 參數(適用于必須使用高版本 Selenium 的場景)
# 將 desired_caps 轉換為 Options 實例
options = UiAutomator2Options().load_capabilities(desired_caps)# 傳入 options 參數
driver = webdriver.Remote(command_executor='http://127.0.0.1:4723',options=options  # 必須傳入 options,替代原來的 desired_capabilities
)# 獲取WLAN元素
wlanEl = driver.find_element('xpath', '//*[@text="WLAN"] ')
# 創建觸摸輸入設備(模擬手指操作)
touch_input = PointerInput(interaction.POINTER_TOUCH, "touch")
# 創建動作構建器
action_builder = ActionBuilder(driver, mouse=touch_input)# 例子1:為展示多一點操作搞的復雜示例
# 獲取元素中心點坐標
# 元素x軸中心點坐標=元素左上角位置坐標x+元素尺寸寬度的一半
x = wlanEl.location['x'] + wlanEl.size['width'] // 2
y = wlanEl.location['y'] + wlanEl.size['height'] // 2
# 執行點擊動作(移動→按下→抬起)
action_builder.pointer_action.move_to_location(x, y) #移動
action_builder.pointer_action.pointer_down() # 左鍵點擊
action_builder.pointer_action.release() #釋放鼠標# 例2:直接一步click點擊即可
# action_builder.pointer_action.click(wlanEl) #例1那些操作只用這一步可完成點擊效果# 例3:長按:按下(pointer_down或者click_and_hold)+暫停+抬起
# action_builder.pointer_action.click_and_hold(wlanEl) #點擊并按住
# action_builder.pointer_action.pause(2) # 暫停2s
# action_builder.pointer_action.pointer_up() #抬起# 執行完整動作鏈
action_builder.perform()driver.quit()

2、滑屏解鎖

位置:模擬器——設置—安全—設置屏幕鎖定——圖案
過程:使用了WEditor找元素位置,如果用Android UIAutomator2模式,和appium不要同時開啟,用Android adb可以和appium同時開啟

在這里插入圖片描述
在這里插入圖片描述

代碼

#!/usr/bin/env python
# encoding: utf-8
'''
@Author  : 草木零
@Software: PyCharm
@File    : class03_actionBuilder02.py
@Time    : 2025/7/29 11:28
@desc   : 手機屏幕圖案解鎖
'''
from time import sleep
from appium import webdriver
from appium.options.android import UiAutomator2Options  # 導入 Android 選項類
from selenium.webdriver.common.actions.action_builder import ActionBuilder
from selenium.webdriver.common.actions.pointer_input import PointerInput
from selenium.webdriver.common.actions import interaction# 手機/模擬器,配置信息
desired_caps = {"platformName": "Android","platformVersion": "7.1.2","deviceName": "127.0.0.1:62001","appPackage": "com.android.settings",# 獲取包名、界面名:adb shell dumpsys window|findstr mCurrentFocus"appActivity": "com.android.settings.ChooseLockPattern","noReset": False
}# 顯式傳入 options 參數(適用于必須使用高版本 Selenium 的場景)
# 將 desired_caps 轉換為 Options 實例
options = UiAutomator2Options().load_capabilities(desired_caps)# 傳入 options 參數
driver = webdriver.Remote(command_executor='http://127.0.0.1:4723',options=options  # 必須傳入 options,替代原來的 desired_capabilities
)# 創建觸摸輸入設備(模擬手指操作)
touch_input = PointerInput(interaction.POINTER_TOUCH, "touch")
# 創建動作構建器
action_builder = ActionBuilder(driver, mouse=touch_input)# 桌面圖案解鎖
window_size = driver.get_window_size() #返回dict格式的當前窗口屏幕尺寸
width = window_size['width']  # 獲取寬度
height = window_size['height']  # 獲取高度
# 各落點位置
startX = width*0.2
startY = height*0.47
midX = width*0.2
midY = height*0.8
endX = width*0.8
endY = height*0.8
action_builder.pointer_action.move_to_location(startX, startY) #移動至起點位置
action_builder.pointer_action.pointer_down()  # 按下
sleep(0.5)  # 按下后短暫停留
action_builder.pointer_action.move_to_location(midX, midY)  # 滑動到中間位置
sleep(0.5)
action_builder.pointer_action.move_to_location(endX, endY)  # 滑動到終點
sleep(0.5)  # 滑動過程
action_builder.pointer_action.pointer_up()  # 抬起
# 執行完整動作鏈
action_builder.perform()
sleep(3)
driver.quit()

效果
在這里插入圖片描述

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/93878.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/93878.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/93878.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Java HTTPS 請求失敗排查與證書導入全過程

文章目錄Java HTTPS 請求失敗排查與證書導入全過程問題背景問題初步分析排查過程查看目標地址證書導入證書驗證證書是否導入成功重啟應用進一步驗證:是否真的是證書問題?1. 瀏覽器訪問2. 抓包工具驗證(如 Charles、Wireshark)補充…

android APT技術

1,背景 對于注解的使用,想必大家都不陌生,它出現在我們的源碼中,以及大部分框架中,比如ButterKnife、Arouter、Retrofit,但它們是有區別的,其中前2個是編譯時注解,最后一個是運行時注…

MySQL 和 PostgreSQL綜合比對分析匯總

面對大數據項目或其它類型項目中,面對關系型數據庫選擇一直是很總要的一點,本文針對MySQL 和 PostgreSQL進行綜合比對分析匯總,內容僅供參考。MySQL 和 PostgreSQL 是兩款主流的開源關系型數據庫(RDBMS),但…

Linux---make和makefile

一、基本概念1.是什么make是一條命令,makefile是一個文件2.對應在vs中按一下f5就能運行代碼,在Linux中make就相當于f5,使用makefile來封裝從而實現我, 想要的功能3.使用①創建makefile文件②編輯makefile解釋:test.exe…

【DAB收音機】DAB收音機協議及其他資料匯總

目錄[ETSI DAB標準協議文檔](https://www.etsi.org/standards)Other DAB資料DAB收音機相關的專利DAB收音機相關的期刊及學位論文DAB開源項目代碼倉庫qt-dab工具welle.io工具dablin工具【eti廣播工具】?? 項目對比與選型建議Other 收音機資料Other資料ETSI DAB標準協議文檔 官…

RabbitMQ的特點和消息可靠性保障

掌握RabbitMQ的核心知識,需從其特點和消息可靠性保障(尤其是消息丟失解決方案)兩方面入手,以下是詳細說明: 一、RabbitMQ的核心特點 RabbitMQ是基于AMQP(Advanced Message Queuing Protocol)協議…

項目升級啦

公司要新做一個醫療行業的業務,經過業務端和產品端的評估該業務與公司已有的產品線關聯不大,用戶后續也不想在老系統那臺老爺車上繼續使用,話說老系統到現在差不多10年了,中間經歷過的前后端開發者形形色色,維護者換了…

Android中頁面生命周期變化

一、Activity切換的生命周期變化(A啟動B)1. 標準流程(B完全覆蓋A)完整生命周期路徑:Activity A:onPause():失去焦點,仍部分可見onStop():完全不可見(當B完全覆…

自動駕駛控制算法——PID算法

自動駕駛控制算法——PID算法 文章目錄自動駕駛控制算法——PID算法一、PID 是什么?二、PID 原理2.1 **比例環節(P)**2.2 **積分環節(I)**2.3 **微分環節(D)**2.4 特點總結2.5 案例分析 —— 小…

Spring Boot 異步執行方式全解析:@Async、CompletableFuture 與 TaskExecutor 對比

在 Spring Boot 開發中,異步執行是提升系統性能的重要手段,尤其適用于處理耗時操作(如日志記錄、郵件發送、數據同步等)。本文將深入對比 Spring Boot 中三種主流的異步實現方式 ——Async注解、手動CompletableFuture和直接使用T…

高效微調2:Prompt-Tuning原理與實戰

高效微調2:Prompt-Tuning原理與實戰 Prompt-Tuning原理介紹 代碼 Prompt-Tuning原理介紹 Prompt-Tuning Prompt-Tuning的思想:凍結主模型全部參數,在訓練數據前加入一小段Prompt,只訓練Prompt的表示層,即一個Embedding模塊。其中,Prompt.又存在兩種形式,一種是hard promp…

使用BART模型和T5模型實現文本改寫

BART模型BART(Bidirectional and Auto-Regressive Transformers)是由 Facebook AI Research(FAIR)在 2019 年提出的序列到序列(seq2seq)預訓練模型,論文發表于《BART: Denoising Sequence-to-Se…

電商前端Nginx訪問日志收集分析實戰

使用FileBeatLogstashES實現分布式日志收集 在大型項目中 ,往往服務都是分布在非常多不同的機器上 ,每個機器都會打印自己的log日志 但是 ,這樣分散的日志 ,本來就無法進行整體分析。再加上微服務的負載均衡體系 ,甚至…

TwinCAT3示例項目1

目錄一、需求分析二、程序編寫1.實現1盞燈的自控(IF、TOF)2. 添加模式控制(Case、枚舉)3. 添加多盞燈(FOR、數組)4. 添加多組燈(二維數組)END項目結合了,FB,I…

如何在 VMware Workstation 虛擬機中利用 Nvidia 顯卡的硬件加速功能

這篇文章詳細介紹了如何在 VMware Workstation 虛擬機中利用 Nvidia 顯卡的硬件加速功能,通過 PCI 設備直通(Pass-Through)技術將顯卡分配給虛擬機使用: 在 VMware Workstation 虛擬機中利用 Nvidia 顯卡的硬件加速功能 1. 檢查…

設計模式(二十二)行為型:策略模式詳解

設計模式(二十二)行為型:策略模式詳解策略模式(Strategy Pattern)是 GoF 23 種設計模式中最具實用性和廣泛影響力的行為型模式之一,其核心價值在于定義一系列算法或行為,并將每個算法封裝到獨立…

AI+向量化

要理解 Java 如何結合 AI 與向量化,我們需要從向量化的核心概念、AI 中向量化的作用、Java 生態中的實現工具以及具體實踐案例四個維度展開。以下是詳細解析:一、核心概念:向量化與 AI 的關系向量化(Vectorization)是將…

Bootstap Vue 之b-form-radio-group 不顯示選中狀態問題

代碼類似&#xff1a;<b-form-radio-groupclass"mt-2"required:disabled"dfrmDisabled"v-model"childDikeForm.SafetyAppraisalRank":options"[一, 二, 三, 四]"name"rankradioopt"></b-form-radio-group>經過測…

Shell 腳本實戰:基于 for 循環的批量操作三例(賬戶創建、網絡檢測與密碼管理)

一、編寫腳本for1.sh,使用for循環創建20賬戶&#xff0c;賬戶名前綴由用戶從鍵盤輸入&#xff0c;賬戶初始密碼由用戶輸入&#xff0c;例如:test1、test2、test3、......、test10實現思路通過read命令獲取用戶輸入的賬戶前綴和初始密碼&#xff1b;加入非空校驗&#xff1a;若前…

PBR技術

一 、PBR的概述1.定義策略路由&#xff1a; PBR 是一種覆蓋路由器默認路由決策機制的技術。它允許管理員根據策略&#xff08;而不僅僅是目標地址&#xff09;來設置數據包的下一跳 IP 地址、出站接口、IP 優先級/DSCP 值等。路由策略&#xff1a;是指在路由器或三層設備上&…