前言最近在玩公主连结,之前也玩过阴阳师之类的游戏。此类游戏将具有诸如初始编号之类的东西,或者可以发行的东西。当然,作为一个程序员,肝之类的东西是可以通过写代码自动帮我们完成的。游戏脚本其实不是很高级。最简单的体验方式就是下载一个Airtest,直接截几张图,写几层代码,然后按照自己的逻辑玩游戏。当然,本文不是讲如何使用Airtest,而是使用原始的python+opencv来实现上述操作。这两天写了一个刷公主连结初始号的程序,算不上是写游戏脚本的老手了。这篇文章主要是分享一些基本的技巧和使用中的心得。准备工作首先,我们要完成以下准备工作。Android设备:模拟器或真实设备都可以。安装adb并添加到系统的PATH中:adb用于安装tesseract-ocr并添加到系统的PATH中:帮助我们实现简单的字符识别。安装python3.7或以上版本。这里我把adb和tesseract放到了百度网盘里,顺便放了一个录制的效果视频在里面。链接:pan.baidu.com/s/1edTPu2o7...提取码:33awpython库安装pipinstallpillowpytesseractopencv-pythoncopycode另外,如果需要可以安装uiautomator2,本文不涉及这块知识。使用adb获取Android设备这里我们主要涉及到单个Android设备的ADB连接操作,首先我们打开模拟器。然后我们调用adbdevices获取当前的Android设备,这里是一个模拟器。接下来可以调用adbshell测试是否可以进入Android设备的shell环境,确认可以输入exit退出。如果有时候进不了shell,可以先调用adbkill-server,再调用adbdevices。可能常用到的ADBShell命令后面还有一些ADB命令操作。通过adb命令,我们可以使用python来操作Android设备。截图最常见的操作就是截屏。先调用screencap进行截图放到Android设备中,然后将截图拉取到电脑上。deftake_screenshot():os.system("adbshel??lscreencap-p/data/screenshot.png")os.system("adbpull/data/screenshot.png./tmp.png")下拉文件下拉文件是刚才的adbpull,以公主连结为例,下面的代码可以导出账号信息的xml,后面可以通过xml进行登录。os.system(f"adbpull/data/data/tw.sonet.princessconnect/shared_prefs/tw.sonet.princessconnect.v2.playerprefs.xml./user_info.xml")上传文件会随着下拉自然上传,通过adbpush来完成。以公主连结为例,以下代码即可完成账号切换。#切换账号1os.system("adbpush./user_info1.xml/data/data/tw.sonet.princessconnect/shared_prefs/tw.sonet.princessconnect.v2.playerprefs.xml")#切换账号2os.system("adbpush./user_info2.xml/data/data/tw.sonet.princessconnect/shared_prefs/tw.sonet.princessconnect.v2.playerprefs.xml")点击屏幕某个位置defadb_click(center,offset=(0,0)):(x,y)=centerx+=offset[0]y+=offset[1]os.system(f"adbshel??linputtap{x}{y}")inputtexttext="YourPassword"os.system(f"adbshel??linputtext{text}")删除字符有时候输入框会有输入缓存,我们需要删除字符。#删除10个字符foriinrange(10):os.system("adbshel??linputkeyevent67")查询当前运行的包名和Activity通过下面的代码可以查询当前运行程序的Activity,也可以通过查看包名道路。adbshel??ldumpsysactivityactivities停止一个应用程序有时你需要停止一个应用程序,你需要提供应用程序的包名。adbshel??lamforce-stoptw.sonet.princessconnect打开应用打开应用需要提供包名和Activity。adbshel??lamstart-W-ntw.sonet.princessconnect/jp.co.cygames.activity.OverrideUnityActivity图片操作对图片的第一个操作是图片搜索,比如Airtest提供的无非就是判断一张图片是否在截屏in,哪里是in这个字。另外,还需要一些抠图。比如我们要获取账号id和账号级别,就需要截取一部分图片,然后进行OCR操作。图片搜索图片搜索其实就是先获取两张图片,然后调用cv2.matchTemplate方法查找存在和位置。这里的匹配是比较模糊的匹配,会有相似的概率,最高为1。我们设置一个阈值来判断模板是否在截图中。这里截图如下,文件名为tmp.png:模板如下:代码如下:importcv2defimage_to_position(screen,template):image_x,image_y=template.shape[:2]result=cv2.matchTemplate(屏幕、模板、cv2.TM_CCOEFF_NORMED)min_val,max_val,min_loc,max_loc=cv2.minMaxLoc(result)print("prob:",max_val)ifmax_val>0.98:globalcentercenter=(max_loc[0]+image_y/2,max_loc[1]+image_x/2)returncenterelse:returnFalseif__name__=="__main__":screen=cv2.imread('tmp.png')template=cv2.imread('Xuandan.png')print(image_to_position(screen,template))后运行上面的代码,可以看到模板匹配的概率是0.9977,位置是(1165,693)。一张图片,左上角是原点,因为我的分辨率是1280*720,那么右下角的坐标是(1280,720)。你可以看到我们的菜单实际上就在右下角。如何快速裁剪模板?(win10)游戏脚本其实不难写,但是需要裁剪很多图片,而且这些图片的分辨率必须和原图一样。我发现如果在win10中用画图打开图片,可以保证QQ截图的分辨率和图片本身的分辨率一致。这时候QQ直接抓取的模板就可以直接用来识别了。图像裁剪下一步是有时需要裁剪一些图像。当然我们的模板图片也可以通过裁剪图片得到。这样的模板图像是最准确的。裁剪其实就是需要裁剪的位置,以及需要的高度和宽度。说白了,就是一个长方形的区域。以下代码是使用PIL库实现的。fromPILimportImagedefcrop_screenshot(img_file,pos_x,pos_y,width,height,out_file):img=Image.open(img_file)region=(pos_x,pos_y,pos_x+width,pos_y+height)cropImg=img.crop(region)cropImg.save(out_file)print("exported:",out_file)if__name__=="__main__":crop_screenshot("tmp.png",817,556,190,24,"test_id.png")以上代码以截取玩家id为例。代码运行后截图如下:SimpleOCR得到以上图像信息后,进行OCR,即光学字符识别。这里的代码很简单,调用API即可。fromPILimportImageimportpytesseractimage=Image.open('test_id.png')content=pytesseract.image_to_string(image)#识别图片print(content),但是需要注意的是pytesseract识别出来的结果会有空格,换行等符号,真正要用的时候,可以过滤一些字符。TheEnd的这篇文章到这里就结束了,主要介绍ADB和images相关的一些基本操作。谢谢大家收看。
