使用注意事项
- UIAutomation只能调用获得许可证书的app。从App Store上下载的软件是不能直接调用的,需要使用专门的软件重新获取证书。
- 在真机运行软件时,脚本中模拟的操作无法阻止屏幕锁屏。当屏幕锁上后,Automation将无法与App产生交互,所以在真机上测试时,应该将自动锁屏关闭
- 当脚本关联的程序崩溃,或者进入后台时,脚本将会停止运行。当程序重新在前台开始运行,脚本也会随之继续运行。
- 在UIAutomation的测试界面中,脚本编写完成后,会保存成trace的格式,其实是保存成了一个文件夹。
一、脚本
1.引用其他脚本
在UIAutomation的脚本中,可以引用后缀名为.js的脚本:
- 语法:#import "<路径>/FileName.js"
- 说明:在实际引入js文件的时候,引用文件后,最好能点击Instrument左上角的Record按钮,重新启动下脚本和模拟器。
2.设置延迟时间
- 语法:UIATarget.localTarget().delay(2);
- 说明:指定延迟时间,程序运行到此处时,停止该时间后再继续运行。
3.设置代码块超时时间
语法:
UIATarget.localTarget().pushTimeout(2);
代码块
UIATarget.localTarget().popTimeout();
说明:
- pushTimeout() 和 popTimeout() 之间的代码块,在超时之前会一直运行。如果运行成功,将会跳出代码块继续运行脚本。否则将会抛出一个异常。
- 超时时间默认是5秒,可以在pushTimeout()中手动设定。
4.将App退到后台
- 语法:UIATarget.localTarget().deactivateAppForDuration(10);
说明:
- 作用是将App退到系统后台,经过指定时间后再唤回到前台。
- 参数是程序退到后台的持续时间,当时间结束后,程序会重新回到前台运行。
5.设置屏幕方向
- 语法:UIATarget.localTarget().setDeviceOrientation(方向参数)
说明:
- UIA_INTERFACE_ORIENTATION_UNKNOWN:设备的旋转方向不确定。
- UIA_INTERFACE_ORIENTATION_PORTRAIT:设备垂直放置,Home键在下方。
- UIA_INTERFACE_ORIENTATION_PORTRAIT_UPSIDEDOWN:设备垂直放置,Home在上方。
- UIA_INTERFACE_ORIENTATION_LANDSCAPELEFT:设备垂直放置,Home在右边。
- UIA_INTERFACE_ORIENTATION_LANDSCAPERIGHT:设备垂直放置,Home键在左边。
- UIA_INTERFACE_ORIENTATION_FACEUP:设备水平放置,屏幕向上。
- UIA_INTERFACE_ORIENTATION_FACEDOWN:设备水平放置,屏幕向下。
6.获取App的屏幕方向
- 语法:UIATarget.localTarget().interfaceOrientation()
返回值:
- UIA_INTERFACE_ORIENTATION_PORTRAIT:软件界面的底部最接近Home键
- UIA_INTERFACE_ORIENTATION_PORTRAIT_UPSIDEDOWN:软件界面的顶部最接近Home键
- UIA_INTERFACE_ORIENTATION_LANDSCAPELEFT:软件界面的左边最接近Home键
- UIA_INTERFACE_ORIENTATION_LANDSCAPERIGHT:软件界面的右边最接近Home键
7.处理提示框
在脚本运行的时候,如果出现了目标App之外的其他程序引起的提示框,UIAutomation会自动处理掉。不过如果处理的提示框数量超过限度,脚本会停止运行。
对于目标App自身引起的提示框,需要自定义一个onAlert方法来处理。
自定义onAlert方法的时候,一般会将弹出的alert对象作为参数传进来。方法内的处理逻辑一般按照这种思路来设计:
- 获取提示框的name属性
- 把name属性作为判断条件,来决定使用那一套处理逻辑
- 将处理结果返回给系统的Alert处理器
二、控件元素
1.控件的层次结构
UIATarget:
- 概念类似于IOS的操作系统,可以是真机或者模拟器
- 声明语法:var target=UIATarget.localTarget();
UIAApplication:
- 概念类似于app
- 声明语法:var app=UIATarget.localTarget().frontMostApp();
UIAWindow:
- 概念为app当前停留的界面窗口
- 声明语法:var window=UIAtarget.localTarget().frontMostApp().mainWindow();
UIALogger:
- 用来在屏幕中输出信息的类,拥有多种输出信息的方法。
Alert:
- 警告窗口,层次较高,不属于window
- 声明语法:var alert=UIATarget.localTarget().frontMostApp().alert();
- 注意:因为alert控件不会同时出现两个,所以在获取该控件时,不能在UIATarget.localTarget().frontMostApp().alert()后面加上[]序号。
2.控件的可访问性
在脚本中,可以通过控件在控件层中的位置来访问,也可以根据控件的名称来访问,但是前提是该控件开启了可访问模式。
在X-code中,可以设置每个控件的Label属性来确定控件的唯一标识符,勾选Accessibility选项来开启控件的可访问性。
3.控件的继承和包含关系
所有可访问的控件都继承自基础元素UIAElement,每一个控件都可以包含0个或者更多的其他控件
4.控件常用属性
- name:用来获取控件,数值与X-code中,为控件设置的accessibility label的属性值是一样的
- value:控件的当前值
- elements:获取当前控件包含的子控件
- parent:获取包含当前控件的父控件
5.获取自定义控件
要获取自定义控件的时候,可以先获取到该控件的父控件,用父控件的.elements()[i]或者.element()[ElementName]来获取。
6.打印子控件列表
- 语法:.logElementTree()
- 说明:任何控件都可以调用的方法,调用后会在日志中打印出当前控件的子控件列表
7.判断控件是否存在
可以用控件的isValid()方法来判断控件是否存在
三、模拟用户操作
1.单击
- 语法:element.tap(); 说明:调用控件的点击方法
- 语法:UIATarget.localTarget().tap({x:100,y:200}); 说明:单击屏幕上指定坐标点
2.双击
- 语法:element.doubleTap(); 说明:调用控件的双击方法。
- 语法:UIATarget.localTarget().doubleTap({x:100,y:100}); 说明:双击屏幕上指定的坐标点
3.双手指单击
- 语法:UIATarget.localTarget.twoFingleTap({x:100,y:100});
4.放大控件
- 语法:UIATarget.localTarget().pinchOpenFromToForDuration( {x:20,y200} , {x:300,y:200} , 2);
说明:
- 第一个参数为操作的起始坐标
- 第二个参数为操作的终止坐标
- 第三个参数为操作持续的时间,用来决定放大的速度
5.缩小控件
- 语法:UIATarget.localTarget().pingCloseFromToForDuration( {x:20,y:200}, {x:300,y:200}, 2);
说明:
- 第一个参数为操作的起始坐标
- 第二个参数为操作的终止坐标
- 第三个参数为操作的持续时间,用来决定缩小的速度
6.拖动
- 语法:UIATarget.localTarget().dragFromToForDuration( {x:20,y:10}, {x:200,y:200},2)
说明:
- 可以用来滚动屏幕或者拖动控件
- 第一个参数为操作的起始坐标
- 第二个参数为操作的终止坐标
- 第三个参数为操作持续的时间,用来决定拖动的速度
- 语法:UIATarget.localTarget().flickFromTo( {x:20,y:10},{x:100,y:100})
- 说明:flick可以理解成非常快速的拖动,因此不需要设置操作持续的时间
7.设置控件value
element.setValue("value");
8.滚动tableview控件
- 语法:UIATarget.localTarget().frontMostApp().mainWindow().tableViews()[0].scrollToElementWithPredicate("name beginswith 'Turtle Pie' ");
说明:
- 获取当前界面中的第一个tableView控件,将tableView滚动到以“Turtle Pie”命名的子控件处
- 除了根据控件名来定位,scrollToElementWithPredicate()方法还可以使用其他属性来定位元素。
9.屏幕截图
- 语法:UIATarget.localTarget().captureScreenWithName("pictureName");
说明:
- 进行一次屏幕截图,图片保存为指定的名字
- IOS模拟器可能不支持这个方法