之前研究了一段时间的appium for native app 相应的总结如下:
appium测试环境搭建 :http://www.cnblogs.com/tobecrazy/p/4562199.html
知乎Android客户端登陆:http://www.cnblogs.com/tobecrazy/p/4579631.html
appium实现截图和清空EditText:http://www.cnblogs.com/tobecrazy/p/4592405.html
appium 滑动处理:http://www.cnblogs.com/tobecrazy/p/4612133.html
最近有人问我怎么使用web driver,所以特来研究一下:
appium for mobile web 之使用 ChromeDriver:http://www.cnblogs.com/tobecrazy/p/4836995.html
今天搞一下appium实现手势解锁。
效果如下:
首先看一下招行手机客户端app手势解锁的element,使用uiautomatorviewer看一下
可以看出,该手势解锁共有9个 android.widget.ImageView 构成,使用findelements获取实际上九宫格类似
0 1 2
3 4 5
6 7 8
如果实现九宫格解锁,就需要绘制解锁内容的手势,我在设置的手势是Z
就是0->1->2->4->6->7->8
第一步,使用appium(Android Studio)解析apk包,获取到package和activity
我的PC OS是win 10 ,appium 也是最新的1.4.x,很诡异的是只能获取到package 却获取不到activity。 这里有一个小小的tricky第二步,代码实现
package com.dbyl.core; import org.apache.commons.io.FileUtils; import org.openqa.selenium.By; import org.openqa.selenium.OutputType; import org.openqa.selenium.TakesScreenshot; import org.openqa.selenium.WebElement; import org.openqa.selenium.remote.CapabilityType; import org.openqa.selenium.remote.DesiredCapabilities; import org.testng.annotations.AfterClass; import org.testng.annotations.BeforeMethod; import org.testng.annotations.Test; import io.appium.java_client.MobileDriver; import io.appium.java_client.TouchAction; import io.appium.java_client.android.AndroidDriver; import java.io.File; import java.io.IOException; import java.net.URL; import java.util.List; import java.util.concurrent.TimeUnit; public class slideToUnlock { private MobileDriver driver; @BeforeMethod(alwaysRun = true) public void setUp() throws Exception { // set up appium DesiredCapabilities capabilities = new DesiredCapabilities(); capabilities.setCapability(CapabilityType.BROWSER_NAME, ""); capabilities.setCapability("platformName", "Android"); capabilities.setCapability("deviceName", "Android Emulator"); capabilities.setCapability("platformVersion", "5.1"); // if no need install don't add this capabilities.setCapability("appPackage", "cmb.pb"); // no need sign capabilities.setCapability("noSign", "True"); capabilities.setCapability("appActivity", ".ui.PBInitActivity"); driver = new AndroidDriver<WebElement>(new URL( "http://127.0.0.1:4723/wd/hub"), capabilities); } @Test(groups = "swipeTest", priority = 1) public void swipeTest() { driver.manage().timeouts().implicitlyWait(30, TimeUnit.SECONDS); // swipe to right System.out.println(driver.getPageSource()); // swipeToRight(driver, 2000); driver.manage().timeouts().implicitlyWait(30, TimeUnit.SECONDS); driver.findElement(By.id("cmb.pb:id/item_funcIcon")).click(); driver.manage().timeouts().implicitlyWait(30, TimeUnit.SECONDS); List<WebElement> pic = driver .findElements(By .xpath("//android.widget.FrameLayout/android.widget.ImageView")); for (int i = 0; i < pic.size(); i++) { System.out.println(pic.size()); pic.get(i).click(); } final TouchAction touchAction = new TouchAction(driver); touchAction.press(pic.get(0)).waitAction(1500).moveTo(pic.get(1)) .moveTo(pic.get(2)).moveTo(pic.get(4)).moveTo(pic.get(6)) .moveTo(pic.get(7)).moveTo(pic.get(8)).release(); touchAction.perform(); String username = driver.findElement(By.id("cmb.pb:id/gTvMenuTitle")) .getText(); System.out.println(username); } @AfterClass(alwaysRun = true) public void tearDown() throws Exception { driver.quit(); } /** * This Method create for take screenshot * * @author Young * @param drivername * @param filename */ public static void snapshot(TakesScreenshot drivername, String filename) { // this method will take screen shot ,require two parameters ,one is // driver name, another is file name String currentPath = System.getProperty("user.dir"); // get current work // folder File scrFile = drivername.getScreenshotAs(OutputType.FILE); // Now you can do whatever you need to do with it, for example copy // somewhere try { System.out.println("save snapshot path is:" + currentPath + "/" + filename); FileUtils .copyFile(scrFile, new File(currentPath + "\" + filename)); } catch (IOException e) { System.out.println("Can't save screenshot"); e.printStackTrace(); } finally { System.out.println("screen shot finished, it's in " + currentPath + " folder"); } } public void swipeToRight(MobileDriver driver, int during) { int width = driver.manage().window().getSize().width; int height = driver.manage().window().getSize().height; driver.swipe(width / 4, height / 2, width * 5 / 6, height / 2, during); // wait for page loading } @AfterClass(alwaysRun = true) public void stopAppiumServer() { } }
/** * @see TouchShortcuts#swipe(int, int, int, int, int) */ @Override public void swipe(int startx, int starty, int endx, int endy, int duration) { TouchAction touchAction = new TouchAction(this); // appium converts press-wait-moveto-release to a swipe action touchAction.press(startx, starty).waitAction(duration) .moveTo(endx, endy).release(); touchAction.perform(); }
使用这个原理就能实现滑动,九宫格滑动解锁.
那么问题就来了,我是使用的是moveTo传入的是WebElement,而swipe是使用的X,Y坐标。
由于不同的app使用的九宫格并不同,有app使用的和招行app不同的,不能是单个的imageView,该怎么实现?
由于对坐标的滑动还没完全理解,所以接下来会继续研究。