关于安卓游戏自动化方面的资料整理-1

最近裸辞,下周就可以撤了。今天没什么事情做,就心思整理下这方面的研究。
因为都是自己找资料,没实践出来可能就直接下结论了。要是有错误也希望能够指正。
同时也不是专门的自动化方向的测试,更多是喜欢玩游戏,会去写一些脚本。所以这篇文章可能主要是入门的一些内容。代码也都是基于 python 的。

好了,buffer 叠完了,开始正文了。


一、手:点击操作/按钮操作

对于安卓自动化方向来说,问题之一就是如何对手机进行操作。游戏方面更不用说,不同于原生应用,游戏内的操作会更复杂。关于操作方面实现的方式如下:

1、备注

1、记得电脑连接手机,打开手机的开发这选项

2、开发者选项中,开启指针位置,可协助开发

3、小米手机需要开启 USB 调试(安全设置),允许模拟点击。

2、adb

从事安卓方向测试,肯定对 adb 都不陌生。这也是平常工作中最常用的工具之一了。在操作方面比较常用的:


adb shell input tap 500 500  # 点击手机(500,500)坐标位置
adb shell input input keyevent KEYCODE_BACK  # 按手机的返回键

3、adbutils

在自身写脚本的时候,adb 肯定是要配合代码使用。python 中通过 adbutils 来调用 adb。记得先 pip install adbutils

下面的代码就是一个简单的 demo,控制手机点击 500,500


from adbutils import AdbClient
adbc = AdbClient()   
adblist = adbc.device_list()
adb = adblist[0]  # 拿到所有连接手机adb中的第一个
adb.shell("input tap 500 500")

以下代码是一些常用的指令


adb.shell("dumpsys window |grep mCurrentFocus") # 获取手机当前的窗口名称
#运行结果 com.dragonplus.happyhospital/com.unity3d.player.UnityPlayerActivity
adb.shell("am start -n 包名/AppActivity") # 启动应用(上一步的结果可作为包名和AppActivity)
adb.shell("am force-stop 包名") # 结束应用
adb.shell("pm clear 包名") # 清除应用数据,相当于重装

通过 adbutils 我们就已经能够做到一些简单的自动化了。例如我之前有一个工作任务就是手机不同压缩下,各贴图的帧数变化。25 张图片需要每张图片展示 2 分钟,并且还需要,用 3 台设备,分别测试 10 次,提高可信度。
最终就是用这种方式,下班挂机了两个晚上解决的。但也有一些其他问题需要优化。

1、三个手机分辨率不一致,辛亏只需要点一个按钮,三台手机就收集了各自按钮的位置解决了。

2、过程中,若有一次点击失效,整个数据都会偏移。辛亏最后没有发生这个问题。之前预想是,只要发生数据偏移,直接放弃本次整体数据。

4、uiautomator2

uiautomator2 根据调查应该是比较流程的安卓自动化工具了。pip install uiautomator2 进行安装,手机首次运行时,会在手机上安装两个应用。


下面的代码就是一个简单的 demo,控制手机点击 500,500


import uiautomator2 as u2

d = u2.connect_usb("pjhms4rsrgnjxckn") # adb devices获得
d.click(500, 500) 

uiautomator2 的优势在于,不仅通过坐标进行点击,还可以通过标签进行点击。
例如点击页面上的模块按钮


1、pip install weditor
2、python -m weditor
3、点击connect
4、dump Hierarchy 获取刷新页面
5、复制对应的标签

最终代码如下


import uiautomator2 as u2
import time
d = u2.connect_usb("pjhms4rsrgnjxckn")

time.sleep(3)
d(resourceId="com.topjohnwu.magisk:id/modulesFragment").click()

u2 在我看来是好用的,尤其是在原始 app 上进行测试。但也发现了一些问题,不得不衡量使用的效果。

1、不同手机导出的标签不一致

2、游戏无法导出标签

3、minicap,minitouch 在安卓高版本存在问题,无法控制。之前找了一个 github 的项目,存储了一些特殊机型及设备的对应文件。

https://github.com/varundtsfi/Android12Support_withso/tree/main/aosp
https://github.com/pl0514/Xiaomi_Vector_issue

4、u2 首次连接不同的手机需要下载文件,但常常出现下载异常的问题。之前就是每次换电脑都把之前下载好的文件也复制到另一台电脑上

5、appium

说实话,对这个了解的不多。原因也是游戏内获取不到标签。

6、airtest

在安卓游戏自动化上,airtest 绝对是主角了。因为去网上查找资料,最后都是指向它的。
我认为他的优势在于以下几点:

1、支持标签,以及 poco 接入也能获取游戏的标签了

2、封装了图像识别。可通过图像进行点击

3、有 ide,支持录制操作等,降低入手难度。

还是关于点击的代码


from airtest.core.api import *
connect_device("Android:///")
touch((500,500))

虽说知道这个 poco 事情,但一直没有尝试过。之后有时间的话,会专门试一下 unity3d 的项目接入 poco。

7、minitouch

这个上面也提到过,论坛里面也有关于这个的帖子。单独提到这个就是因为很多自动化操作框架都是基于这个实现的。钻研的人感觉可以深入了解下。我是菜鸟一个,就放弃了

8、scrcpy

这个可能部分人使用过,一个安卓的投屏软件,还有基于其二次开发的 QTscrcpy。主要的功能就是将手机画面投屏到电脑上。既然能通过电脑操作手机,那么肯定也是有办法提前出他的操作功能的。

https://github.com/leng-yue/py-scrcpy-client

感谢大佬的这个项目,刚刚打开项目,我发现项目竟然更新了!!!感谢大佬!感谢大佬!

在 scrcpy 中的 control 中,封装了各自操作指令。用时还是先安装 pip install scrcpy-client

import scrcpy

client = scrcpy.Client(
        device="pjhms4rsrgnjxckn",
        flip=False,
        bitrate=2000000,
        max_width=2340, # 注意,这里需要是手机的最长像素
        max_fps=10,
    )

client.start(threaded=True)
client.control.touch(500,500)


代码中会根据实际画面的像素进行换算,例如刚才的手机,我把 max_width 写成 1080。那就缩小了 2340/1080 约等于 2.16。那样填写(100,100)最后就会去点击(216,216)

若想解决这个问题,就需要对 jar 文件进行重新改写。
https://github.com/Genymobile/scrcpy/tree/master

以前的版本我改过一次,目前电脑 AS 没再打算花时间配置。简单看了下代码,应该是把这里修改。直接就是传入什么坐标,返回什么坐标,无需计算。

刚刚搭了环境,简单测试了一遍改成这样就行了

int convertedX = contentRect.left + point.getX();
int convertedY = contentRect.top + point.getY();

build-makeproject-生成一个 server-debug.apk。再次改名成 scrcpy-server.jar 就行。

注意:python 安装的 scrcpy-client 目前没有更新到最新版。所有要使用最新版本的化,还得去 git 上 clone 代码。

9、autojst

这个也是简单提一下,主要是用做手机端进行自动化的。直接在手机端操作生成自动化指令。


关于操作部分就写这么多了。上述也是我收集的一部分内容。希望有好用的工具还有朋友继续分享。之后还会总结关于获取图像,和识别相关的一些内容。


↙↙↙阅读原文可查看相关链接,并与作者交流