原文地址:http://blog.csdn.net/zhubaitian/article/details/39754233

如文章《Appium基于安卓的各种FindElement的控件定位方法实践》所述,Appium拥有众多获取控件的方法。其中一种就是根据控件所在页面的XPATH来定位控件。

本文就是尝试通过自己的试验来尝试对Appium如何用xpath来定位控件做一个阐述,当中如有不对的地方敬请大家指出。

1. 背景

本文尝试使用的试验对象是SDK自带的NotePad应用实例,假设已经有两个Notes分别是“note1”和“note2”添加到Notepad上面,我们要做的就是尝试用xpath的方法来定位“note2”这个ListView下面的TextView控件。
注意界面上有3个TextView类型的控件:
  • 最上面的作为整个ListView的Title文本为“Notes”的TextView,Index为0
  • 中间的文本为“note2”的TextView,Index也是0
  • 最下面的文本为“note1”的TextView,Index是1
 

2. xPath获取控件方式

2.1 通过判断控件属性获取控件

控件的所有属性都可以用作判断,比如它的text,index,resource-id是否clickable等,例如:

2.1.1 通过文本查找目标控件

  1. el = driver.findElementByXPath("//android.widget.TextView[contains(@text,'note2')]");
  2. assertThat(el.getText(),equalTo("note2"));

2.1.2 通过index查找目标控件

如果我们像下面的方式使用index为0来查找控件note2,那么将会失败,因为该xpath只是说“我要查找页面上android.widget.TextView类型的index为0的控件“,但如背景所说我们事实上有3个TextView控件,其中最上面的和中间的控件他们的Index都是0.所以最终获得的控件其实是Appium第一个找到的最上面文本为”Notes“的TextView。

  1. el = driver.findElementByXPath("//android.widget.TextView[contains(@index,0)]");
  2. assertThat(el.getText(),equalTo("note2"));

那么我们就要想办法加多点路径,让xpath能分辨出需要的是下面的index为0的TextView,而不是上面的。观看上图的UIAutomatorViewer控件的分层结构,发现这两个TextView是从LinearLayout开始分叉的,所以我们应该从该路径开始通过数组下标指定我们需要的是”在LinearLayout下面的第二个FrameLayout下面的ListView下面的Index为0的TextView:

  1. el = driver.findElementByXPath("//android.widget.LinearLayout[1]/android.widget.FrameLayout/android.widget.ListView/android.widget.TextView[contains(@index,0)]");
  2. assertThat(el.getText(),equalTo("note2"));

2.1.3 通过其他属性查找目标控件

TBD,这些就不一一列举了,参照以上两个示例进行实现就可以了

2.2 通过指定选择集合的位置获得控件

按照我的实践和理解,通过这种方式获取控件是不靠谱的,起码存在两个问题。

  • 问题1:控件在集合中的位置是不可控的。
  1. el = driver.findElementByXPath("//android.widget.TextView[1]");
  2. assertThat(el.getText(),equalTo("note2"));

以上的例子我原意是想把UIAutomatorViewer里面的上中下3个TextView中的中间那个给找出来,但结果返回来给我的确实最上面的那个“Notes”。

  • 问题2:通过增加路径层数限制查找指定元素集合不起效。
  1. el = driver.findElementByXPath("//android.widget.FrameLayout[1]/android.widget.LinearLayout[1]/android.widget.FrameLayout/android.widget.ListView/android.widget.TextView[0]");
  2. assertThat(el.getText(),equalTo("note2"));

以上例子我本意是想通过增加父路径的限制来表明“我想要的控件是ListView下面的那两个TextView控件中的第一个”,但返回给我的是“An unknown server-side error occurred while processing the command",感觉是越界了的样子。

2.4 xpath用法官方手册

至于其他非主流获的通过xpath取控件的方式,请参考xpath官方手册中文版:http://wenku.baidu.com/link?url=tLdn9X4ucgmzYyKj4dpsgSDbshXEw6W8BTyqQAXd0kTMY6lBQqLiIL9FHtcZmdIeO8o5ZKV-fzlw96mFgvmWZ-qz35EPObyv8hKLTuyxbv3

【转】Appium根据xpath获取控件实例随笔的更多相关文章

  1. Appium依据xpath获取控件实例随笔

    如文章<Appium基于安卓的各种FindElement的控件定位方法实践>所述,Appium拥有众多获取控件的方法.当中一种就是依据控件所在页面的XPATH来定位控件. 本文就是尝试通过 ...

  2. Appium根据xpath获取控件实例随笔

    如文章<Appium基于安卓的各种FindElement的控件定位方法实践>所述,Appium拥有众多获取控件的方法.其中一种就是根据控件所在页面的XPATH来定位控件. 本文就是尝试通过 ...

  3. Appium根据xpath获取控件

    如文章< Appium基于安卓的各种FindElement的控件定位方法实践>所述,Appium拥有众多获取控件的方法.其中一种就是根据控件所在页面的XPATH来定位控件. 本文就是尝试通 ...

  4. wpf datagrid 如何自定义行的控件实例,(textbox 并选中则全选)

    主要是为了用户输入方便 按回车,选中下一列,text自动获取焦点,输入状态 获取控件实例  https://blog.csdn.net/m15188153014/article/details/486 ...

  5. Appium+python自动化(二十五)- 那些让人抓耳挠腮、揪头发和掉头发的事 - 获取控件ID(超详解)

    简介 在前边的第二十二篇文章里,已经分享了通过获取控件的坐标点来获取点击事件的所需要的点击位置,那么还有没有其他方法来获取控件点击事件所需要的点击位置呢?答案是:Yes!因为在不同的大小屏幕的手机上获 ...

  6. UiAutomator源码分析之获取控件信息

    根据上一篇文章<UiAutomator源码分析之注入事件>开始时提到的计划,这一篇文章我们要分析的是第二点: 如何获取控件信息 我们在测试脚本中初始化一个UiObject的时候通常是像以下 ...

  7. 第14章8节《MonkeyRunner源代码剖析》 HierarchyViewer实现原理-获取控件列表并建立控件树

    在上几节的描写叙述中,我们把HierarchyViewer初始化好.也把ViewServer给装备好了.那如今距离获得一个控件去操作它是万事具备仅仅欠东风了,欠了那一股春风了?欠了的是建立控件树这个东 ...

  8. UiAutomator源代码分析之获取控件信息

    依据上一篇文章<UiAutomator源代码分析之注入事件>開始时提到的计划,这一篇文章我们要分析的是第二点: 怎样获取控件信息 我们在測试脚本中初始化一个UiObject的时候一般是像下 ...

  9. asp.net js获取控件ID

    ClientID是由ASP.Net生成的服务器控件得客户端标识符,当这个控件生成到客户端页面的时候,在客户端代码访问该控件时就需要通过ClientID来访问. 以文本框为例: 一.未使用母版页 js可 ...

随机推荐

  1. 由Lucnene 对于预治疗的文字,全角半角转换器(可执行)

    这是我第二次读这本书,在自己的学习之间XML,javascript,的深入研究<JAVA 核心技术>. 在当中深入的学习了java的非常多机制. 回头再来看搜索引擎这本书的时候.就认为比第 ...

  2. 【007】【JVM——内存分配和恢复策略】

     内存分配与收回策略 JVM的自己主动内存管理要自己主动化地解决两个问题:对象分配内存以及回收分配给对象的内存.回收内存前几篇已经讲了.如今说内存分配.对象的内存分配一般分配在堆内存中,也可能经过 ...

  3. c++输入密码以星号代替

    #include <iostream> #include <string>//注意这里的头文件! #include<conio.h> using namespace ...

  4. 经FreeMarkerclasspath加载方式生成静态页面

    package htmlskin; import java.io.BufferedWriter; import java.io.File; import java.io.FileNotFoundExc ...

  5. Android做法说明(3)---Fragment使用app袋或v4包解析

    Android做法说明(3)---Fragment使用app袋或v4包解析 1)问题简述 相信非常多的朋友在调用Fragment都会遇到以下的情况: watermark/2/text/aHR0cDov ...

  6. error C2871: &#39;std&#39; : does not exist or is not a namespace

    #include <iostream.h> using namespace std; 然后编译时出现 error C2871: 'std' : does not exist or is n ...

  7. 【Spark亚太研究院系列】Spark道路的真正的主人-第一章 构建Spark星团(第五步)(6)

    结束historyserver例如,下面的命令可以看到: 第四步:验证Hadoop分布式集群 首先在hdfs文件系统上创建两个文件夹.创建步骤例如以下所看到的: watermark/2/text/aH ...

  8. nginx 提供静态内容

    Serving Static Content 提供静态内容 原文地址:http://nginx.com/resources/admin-guide/serving-static-content/ Th ...

  9. WPF学习(2)XAML

    XAML(eXtensible Application Markup Language,可扩展应用程序标记语言)是一种声明式的编程语言,遵循XML的语法.WPF使用XAML来设计UI具有易用性.高效性 ...

  10. C++ Primer笔记4_静态成员类_IO库

    1.静态成员类 static成员变量与函数 static成员变量:必须在类外初始化.(const或引用类型变量必须在构造函数初始化列表里初始化) static成员函数: 不依赖于类.相当于类里的全局函 ...