大家好,我是今天的课程讲师,今天给大家带来的是一个H5小游戏的自动换号
这也是常见的游戏自动化功能
现在我们可以看到这是游戏登录了的一个状态,我们就先从怎么退出游戏再到怎么去登录游戏吧
这个游戏的个人中心是一个悬浮框,你单纯的想去找图找色可能是比较麻烦的,因为它这个是不固定位置的,而且容易被背景干扰到
像这种悬浮框多数是由元素界面组成的,我们可以通过抓取这个元素去定位它,这样不管它在哪个位置,我们都能精准的点击到它
好,我们话不多说,直接开干,先打开按键助手的抓抓工具,把这个游戏界面的元素抓取一下看看
经过我们的抓取可以确认到这个悬浮球的元素,然后我们需要用到一个专门针对元素使用的插件去帮助我们更好更快的编写代码
这个元素插件叫 "ElementEx.luae" 是采用Lua编写的一个加密插件
下面我们用导入插件命令来引用这个插件
找到这个插件的查找元素功能 "ElementEx.Find(匹配模式[,下标,查找超时])"一共有三个参数,我们目前只需要关注第一个匹配模式
这个匹配模式根据插件介绍是有两种模式的,一种是键值对,一种是table表
- //匹配模式1:一个属性对应一个值,不能落单,支持多个属性,所有命令的匹配模式均使用以下格式
- Dim 元素 = ElementEx.Find("text","按键精灵","desc","按键精灵","class","xxxx","desc","xxxxx")
- //匹配模式2:table表
- Dim 元素 = ElementEx.Find({"text":"按键精灵","desc":"按键精灵","class":"xxxx","desc":"xxxxx"})
复制代码使用那一种都是可以的,我们这里就采用第一种
先定义一个变量[悬浮球]来存放游戏悬浮球的元素内容
- Dim 悬浮球 = ElementEx.Find("class","android.widget.LinearLayout","pkg","com.ylwl.res.common","focused",False,"long-clickable",False,"clickable",False,"checkable",False,"checked",False)
复制代码然后判断一下返回的值是不是已经找到了这个悬浮球
- If 悬浮球 Then
- TracePrint "找到了悬浮球~"
- End If
复制代码根据实际的调试结果,我们已经是调试输出找到了悬浮球,但是我们现在还不确定是不是找正确了,我们采用元素点击让它多点几次看看
- Do
- Delay 1000
- TracePrint "点击悬浮球 = " & CStr(ElementEx.Click(悬浮球))
- Loop
复制代码诶,现在出新问题了,游戏的个人中心出现了它还在点这个悬浮球,那我们就要做一个判断
在出现用户中心的情况下,我们要停止点击悬浮球,先把游戏的个人中心打开,我们抓取一下界面元素
然后定义一个变量[我的界面模式]来存放游戏的个人中心的元素
- Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Do
- Delay 1000
- If ElementEx.Find(我的界面模式) Then
- TracePrint "打开我的界面 = " & CStr(True)
- Exit Do
- Else
- TracePrint "点击悬浮球 = " & CStr(ElementEx.Click(悬浮球))
- End If
- Loop
复制代码现在我们已经能顺利打开了游戏个人中心,接下来也是抓取需要点击的元素,这里就不再细说了,开干~
- Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 切换账号模式 = {"text":"切换账号","class":"android.widget.Button","pkg":"com.ylwl.res.common"}
- Dim 确认切换账号 = {"text":"确认切换账号","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 确定 = {"text":"确定","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
复制代码现在代码多了起来,我们就需要把代码封装成功能,这样阅读代码也方便,后期也更好的维护
有些同学可能就要提问了,老师你函数里面有Do Loop 万一游戏闪退了怎么办?
这是一个好问题,那我们就需要在死循环的代码里带上限制条件
一种是,如果出现了问题,我就重启你
一种是,如果出现了问题,我就退出你
- Dim 游戏包名 = "com.tianmu.webshell.dldl.tmjh.xuanzang431"
- Function 切换账号()
- 切换账号 = False
- Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 切换账号模式 = {"text":"切换账号","class":"android.widget.Button","pkg":"com.ylwl.res.common"}
- Dim 确认切换账号 = {"text":"确认切换账号","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 确定 = {"text":"确定","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- If Sys.AppIsFront(游戏包名) = True Then
- If 打开礼包中心() = True Then
- Do
- Delay 200
- If ElementEx.Find(切换账号模式) Then
- TracePrint "点击切换账号模式 = " & CStr(ElementEx.Click(切换账号模式))
- Else
- If ElementEx.Find(我的界面模式) Then
- TracePrint "点击我的界面模式 = " & CStr(ElementEx.Click(我的界面模式))
- End If
- Delay 1000
- End If
- If ElementEx.Find(确认切换账号) Then
- TracePrint "是否在确认切换账号页面 = " & CStr(True)
- If ElementEx.Click(确定) Then
- TracePrint "点击确认按钮 = " & CStr(True)
- 切换账号 = True
- Exit Function
- Delay 1000
- End If
- End If
- If Sys.AppIsFront(游戏包名) <> True Then
- Exit Do
- End If
- Loop
- Else
- TracePrint "打开账号界面 = " & CStr(False)
- End If
- Else
- TracePrint "应用是否在前台 = " & CStr(False)
- End If
- End Function
- Function 打开礼包中心()
- 打开礼包中心 = False
- Dim 悬浮球 = ElementEx.Find("class","android.widget.LinearLayout","pkg","com.ylwl.res.common","focused",False,"long-clickable",False,"clickable",False,"checkable",False,"checked",False)
- Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Do
- Delay 200
- If Sys.AppIsFront(游戏包名) <> True Then
- TracePrint "应用是否在前台 = " & CStr(False)
- Exit Do
- End If
- If ElementEx.Find(我的界面模式) Then
- TracePrint "打开我的界面 = " & CStr(True)
- 打开礼包中心 = True
- Exit Function
- Else
- TracePrint "点击悬浮球 = " & CStr(ElementEx.Click(悬浮球))
- Delay 1000
- End If
- Loop
- End Function
复制代码现在让我们来看一下实际的测试效果吧!
- TracePrint "是否退出账号 = " & CStr(切换账号())
复制代码可以看到,我们已经退出了游戏账号,那我们继续开始编写登录的函数吧
登录需要注意的点
1.编辑框里面的账号是旧的账号还是新的账号?
2.编辑框的密码元素text全是??????不好判断?
3.什么时候才合适点击登录按钮?
我们先把需要的元素数据取出来
- Dim 登录界面 = {"text":"仅对年满18周岁成年人提供游戏服务","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 登录按钮 = {"text":"登录","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
- Dim 账号输入框未输入 = {"res":"com.ylwl.res.common:id/mixsdk_login_et_account","class":"android.widget.EditText","pkg":"com.ylwl.res.common"}
- Dim 密码输入框未输入 = {"res":"com.ylwl.res.common:id/mixsdk_login_et_passwd","class":"android.widget.EditText","pkg":"com.ylwl.res.common"}
复制代码经过实际的测试,我们发现账号输入了密码框可以通过元素text来确定这个账号是不是我们输入的账号
- Dim 账号输入框已输入 = {"text":账号,"res":"com.ylwl.res.common:id/mixsdk_login_et_account","class":"android.widget.EditText"}
复制代码但是密码的text?????并不能找到,那我们就换一个思路,先清空输入框,确定是空的输入框再输入密码,确定账号密码都输入了,就点击登录按钮
- Dim 密码输入框已输入 = {"text":"请输入密码","res":"com.ylwl.res.common:id/mixsdk_login_et_passwd","class":"android.widget.EditText"}
复制代码接下来就是逻辑方面,思路是先判断账号输入框的账号是否符合,然后清空密码框,并且确定了就输入密码,两个步骤都做完了就可以点击登录了
- Dim 账号是否输入 = False, 密码是否输入 = False
- If ElementEx.Find(登录界面) Then
- TracePrint "是否在登录界面 = " & CStr(True)
- If 账号是否输入 = False Then
- If ElementEx.Find(账号输入框已输入) Then
- 账号是否输入 = True
- Else
- If ElementEx.Find(账号输入框未输入) Then
- TracePrint "点击账号输入框 = " & CStr(ElementEx.Click(账号输入框未输入))
- Call 清空输入框()
- Delay 200
- InputText 账号
- Delay 500
- End If
- End If
- End If
- If 密码是否输入 = False Then
- If ElementEx.Find(密码输入框已输入) Then
- InputText 密码
- Delay 500
- 密码是否输入 = True
- Else
- If ElementEx.Find(密码输入框未输入) Then
- TracePrint "点击密码输入框 = " & CStr(ElementEx.Click(密码输入框未输入))
- Call 清空输入框()
- KeyPress "del"
- Delay 200
- End If
- End If
- End If
- If 账号是否输入 = True And 密码是否输入 = True Then
- If ElementEx.Find(登录按钮) Then
- TracePrint "点击登录按钮 = " & CStr(ElementEx.Click(登录按钮))
- Delay 1000
- End If
- End If
- End If
- Sub 清空输入框()
- For 10
- Keypress "PageUp"
- Next
- Keydown 114
- keydown 60
- For 10
- Keydown "PageDown"
- Next
- Keyup 114
- Keyup 60
- Keyup "PageDown"
- End Sub
复制代码点击登录之后,有一个登录中的状态,我们也把它写出来,这样方便客户观看脚本的运行状态
- Dim 登录中 = {"textC":"登录中","class":"android.widget.TextView"}
- If ElementEx.Find(登录中) Then
- TracePrint "正在登录中……"
- End If
复制代码登录完了游戏还有悬浮球的公告
- Dim 公告 = {"text":"公告","class":"android.widget.TextView"}
- Dim 公告关闭按钮 = {"res":"com.ylwl.res.common:id/mixsdk_img_right","class":"android.widget.ImageView","pkg":"com.ylwl.res.common"}
- If ElementEx.Find(公告关闭按钮) Then
- TracePrint "是否登录成功 = " & CStr(True)
- TracePrint "点击公告关闭按钮 = " & CStr(ElementEx.Click(公告关闭按钮))
- End If
复制代码关闭了悬浮球的公告再出来一个游戏公告,由于游戏公告已经不属于元素,所以我们用到了图色插件
这里请出我们的GK插件
- Import "GK.luae"
- If GK.Full(308,1199,415,1232, "Attachment:公告_点击返回.png", 0.9, True) Then
- TracePrint "公告页面点击返回 = " & CStr(True)
- Delay 200
- End If
- If GK.Full(623,43,709,902, "Attachment:公告_点击关闭.png", 0.9, True) Then
- TracePrint "公告页面点击关闭 = " & CStr(True)
- Delay 200
- End If
- If GK.Full(289,904,435,947, "Attachment:进入游戏.png", 0.9, True) Then
- TracePrint "点击进入游戏 = " & CStr(True)
- Delay 200
- End If
- If GK.Full(261,1180,350,1270, "Attachment:主界面_背包.png", 0.9) Then
- TracePrint "进入游戏 = " & CStr(True)
- Delay 200
- End If
复制代码到进去游戏界面看到背包我们就判断登录成功了,接下来把零碎的代码用函数封装起来,最终代码如下~
Import "ElementEx.luae"
Import "GK.luae"
Dim 游戏包名 = "com.tianmu.webshell.dldl.tmjh.xuanzang431"
'到进去游戏界面看到背包我们就判断登录成功了,接下来把零碎的代码用函数封装起来
Function 登录(账号, 密码)
登录 = False
Dim 账号是否输入 = False, 密码是否输入 = False
Dim 登录界面 = {"text":"仅对年满18周岁成年人提供游戏服务","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Dim 登录按钮 = {"text":"登录","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Dim 账号输入框未输入 = {"res":"com.ylwl.res.common:id/mixsdk_login_et_account","class":"android.widget.EditText","pkg":"com.ylwl.res.common"}
Dim 密码输入框未输入 = {"res":"com.ylwl.res.common:id/mixsdk_login_et_passwd","class":"android.widget.EditText","pkg":"com.ylwl.res.common"}
Dim 账号输入框已输入 = {"text":账号,"res":"com.ylwl.res.common:id/mixsdk_login_et_account","class":"android.widget.EditText"}
Dim 密码输入框已输入 = {"text":"请输入密码","res":"com.ylwl.res.common:id/mixsdk_login_et_passwd","class":"android.widget.EditText"}
Dim 登录中 = {"textC":"登录中","class":"android.widget.TextView"}
Dim 公告 = {"text":"公告","class":"android.widget.TextView"}
Dim 公告关闭按钮 = {"res":"com.ylwl.res.common:id/mixsdk_img_right","class":"android.widget.ImageView","pkg":"com.ylwl.res.common"}
If Sys.AppIsFront(游戏包名) = True Then
Do
Delay 200
If ElementEx.Find(登录界面) Then
TracePrint "是否在登录界面 = " & CStr(True)
If 账号是否输入 = False Then
If ElementEx.Find(账号输入框已输入) Then
账号是否输入 = True
Else
If ElementEx.Find(账号输入框未输入) Then
TracePrint "点击账号输入框 = " & CStr(ElementEx.Click(账号输入框未输入))
Call 清空输入框()
Delay 200
InputText 账号
Delay 500
End If
End If
End If
If 密码是否输入 = False Then
If ElementEx.Find(密码输入框已输入) Then
InputText 密码
Delay 500
密码是否输入 = True
Else
If ElementEx.Find(密码输入框未输入) Then
TracePrint "点击密码输入框 = " & CStr(ElementEx.Click(密码输入框未输入))
Call 清空输入框()
KeyPress "del"
Delay 200
End If
End If
End If
If 账号是否输入 = True And 密码是否输入 = True Then
If ElementEx.Find(登录按钮) Then
TracePrint "点击登录按钮 = " & CStr(ElementEx.Click(登录按钮))
Delay 1000
End If
End If
End If
If ElementEx.Find(登录中) Then
TracePrint "正在登录中……"
End If
If ElementEx.Find(公告关闭按钮) Then
TracePrint "是否登录成功 = " & CStr(True)
TracePrint "点击公告关闭按钮 = " & CStr(ElementEx.Click(公告关闭按钮))
End If
If GK.Full(308,1199,415,1232, "Attachment:公告_点击返回.png", 0.9, True) Then
TracePrint "公告页面点击返回 = " & CStr(True)
Delay 200
End If
If GK.Full(623,43,709,902, "Attachment:公告_点击关闭.png", 0.9, True) Then
TracePrint "公告页面点击关闭 = " & CStr(True)
Delay 200
End If
If GK.Full(289,904,435,947, "Attachment:进入游戏.png", 0.9, True) Then
TracePrint "点击进入游戏 = " & CStr(True)
Delay 200
End If
If GK.Full(261,1180,350,1270, "Attachment:主界面_背包.png", 0.9) Then
TracePrint "进入游戏 = " & CStr(True)
登录 = True
Delay 200
Exit Function
End If
Loop
Else
TracePrint "应用是否在前台 = " & CStr(False)
End If
End Function
Function 切换账号()
切换账号 = False
Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Dim 切换账号模式 = {"text":"切换账号","class":"android.widget.Button","pkg":"com.ylwl.res.common"}
Dim 确认切换账号 = {"text":"确认切换账号","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Dim 确定 = {"text":"确定","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
If Sys.AppIsFront(游戏包名) = True Then
If 打开礼包中心() = True Then
Do
Delay 200
If ElementEx.Find(切换账号模式) Then
TracePrint "点击切换账号模式 = " & CStr(ElementEx.Click(切换账号模式))
Else
If ElementEx.Find(我的界面模式) Then
TracePrint "点击我的界面模式 = " & CStr(ElementEx.Click(我的界面模式))
End If
Delay 1000
End If
If ElementEx.Find(确认切换账号) Then
TracePrint "是否在确认切换账号页面 = " & CStr(True)
If ElementEx.Click(确定) Then
TracePrint "点击确认按钮 = " & CStr(True)
切换账号 = True
Exit Function
Delay 1000
End If
End If
Loop
Else
TracePrint "打开账号界面 = " & CStr(False)
End If
Else
TracePrint "应用是否在前台 = " & CStr(False)
End If
End Function
Function 打开礼包中心()
打开礼包中心 = False
Dim 悬浮球 = ElementEx.Find("class","android.widget.LinearLayout","pkg","com.ylwl.res.common","focused",False,"long-clickable",False,"clickable",False,"checkable",False,"checked",False)
Dim 我的界面模式 = {"text":"我的","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Dim 登录界面 = {"text":"仅对年满18周岁成年人提供游戏服务","class":"android.widget.TextView","pkg":"com.ylwl.res.common"}
Do
Delay 200
If Sys.AppIsFront(游戏包名) <> True Then
TracePrint "应用是否在前台 = " & CStr(False)
Exit Do
End If
If ElementEx.Find(登录界面) Then
TracePrint "打开礼包中心错误,处于未登录状态~"
Exit Function
End If
If ElementEx.Find(我的界面模式) Then
TracePrint "打开我的界面 = " & CStr(True)
打开礼包中心 = True
Exit Function
Else
TracePrint "点击悬浮球 = " & CStr(ElementEx.Click(悬浮球))
Delay 1000
End If
Loop
End Function
Sub 清空输入框()
For 10
Keypress "
ageUp"
Next
Keydown 114
keydown 60
For 10
Keydown "
ageDown"
Next
Keyup 114
Keyup 60
Keyup "
ageDown"
End Sub
TracePrint "是否退出账号 = " & CStr(切换账号())
Delay 5000
Call 登录("账号", "密码")
这节课到这里就结束啦,下节课给大家带来日常任务的讲解,谢谢~