代码先是发送”LIST”命令到ViewServer列出所有的打开的窗口,然后把每个窗口都保存起来。342行起按照源码的注释解析就是说:从协议版本3以后开始加入了窗口自动更新的功能,但是在此之前,如果用户想要获得一个获得焦点的窗口的话,需要通过显式的创建一个特殊的哈希值为-1的Window实例来完成。怎么知道它的哈希值是-1呢?请看Window类的getfocusedWindow方法:

return new Window(device, "<Focused Window>", -1);

}

代码14-7-2 Window-getFocusedWindow方法

然后再看其调用的Window的构造函数和对应的传入参数:

public Window(IHvDevice device, String title, int hashCode)

{

this.mHvDevice = device;

this.mTitle = title;

this.mHashCode = hashCode;

this.mClient = null;

}

代码14-7-3 Window-构造函数

最终创建的就是一个标题是”<Focused Window>”,哈希值是-1的Window实例。

通过以上的示例,主要是想说明,ViewServer的版本会影响到代码的不同处理方式,所以我们还是很有必要去看下这些版本信息是如何获得和保存起来的。

好,那么我们继续分析HierarchyViewer在装备ViewServer时的方法setupViewServer最后一个调用方法DeviceBridge.loadViewServerInfo,这个方法有点长,我们对它分开来分析,先看第1部分:

260     public static ViewServerInfo loadViewServerInfo(IDevice device) {

261         int server = -1;

262         int protocol = -1;

263         DeviceConnection connection = null;

264         try {

265             connection = new DeviceConnection(device);

266             connection.sendCommand("SERVER"); //$NON-NLS-1$

267             String line = connection.getInputStream().readLine();

268             if (line != null) {

269                 server = Integer.parseInt(line);

270             }

271         } catch (Exception e) {

272             Log.e(TAG, "Unable to get view server version from device " + device);

273         } finally {

274             if (connection != null) {

275                 connection.close();

276             }

277         }

...

}

代码14-7-4 DeviceBridge - loadViewServerInfo获取ViewServer版本

265行显示的代码的第一个重要的部分是去建立一个DeviceConnection的连接,传入的参数依然是ddmlib的Device类的实例:

36     public DeviceConnection(IDevice device) throws IOException {

37         mSocketChannel = SocketChannel.open();

38         int port = DeviceBridge.getDeviceLocalPort(device);

39         if (port == -1) {

40             throw new IOException();

41         }

42         mSocketChannel.connect(new InetSocketAddress("127.0.0.1", port)); //$NON-NLS-1$

43         mSocketChannel.socket().setSoTimeout(40000);

44     }

代码14-7-5 DeviceConnection - 构造函数

整个代码所做的事情很清晰明了:

  • 创建一个SocketChannel
  • 根据Device实例获得对应的ViewServer本地转发端口号
  • 把SocketChannel连接上本地的ViewServer转发端口

这里值得提一提的倒是如何根据Device实例获得ViewServer本地转发端口号这个事情。大家还记得第4小节我们说端口转发的时候,最终Device实例和对应的本地转发端口号是保存在DeviceBridge的一个名叫sDevicePortMap的静态成员HashMap里面的。所以这里所做的事情就是去到这个HashMap里面以Device实例为键把端口号这个值取出来而已:

155     public static int getDeviceLocalPort(IDevice device) {

156         synchronized (sDevicePortMap) {

157             Integer port = sDevicePortMap.get(device);

158             if (port != null) {

159                 return port;

160             }

161             Log.e(TAG, "Missing forwarded port for " + device.getSerialNumber());

162             return -1;

163         }

164     }

代码14-7-6 DeviceBridge - getDeviceLocalPort

老李推荐:第14章7节《MonkeyRunner源码剖析》 HierarchyViewer实现原理-装备ViewServer-获取版本号 2的更多相关文章

  1. 老李推荐:第6章8节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-小结

    老李推荐:第6章8节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-小结   本章我们重点围绕处理网络过来的命令的MonkeySourceNetwork这个事 ...

  2. 老李推荐:第6章7节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-注入按键事件实例

    老李推荐:第6章7节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-注入按键事件实例   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜 ...

  3. 老李推荐:第6章6节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-命令队列

    老李推荐:第6章6节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-命令队列   事件源在获得字串命令并把它翻译成对应的MonkeyEvent事件后,会把这些 ...

  4. 老李推荐:第6章4节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-翻译命令字串

    老李推荐:第6章4节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-翻译命令字串   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自 ...

  5. 老李推荐:第6章5节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-事件

    老李推荐:第6章5节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-事件   从网络过来的命令字串需要解析翻译出来,有些命令会在翻译好后直接执行然后返回,但有 ...

  6. 老李推荐:第6章3节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-命令翻译类

    老李推荐:第6章3节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-命令翻译类   每个来自网络的字串命令都需要进行解析执行,只是有些是在解析的过程中直接执行 ...

  7. 老李推荐:第6章2节《MonkeyRunner源码剖析》Monkey原理分析-事件源-事件源概览-获取命令字串

    老李推荐:第6章2节<MonkeyRunner源码剖析>Monkey原理分析-事件源-事件源概览-获取命令字串   从上一节的描述可以知道,MonkeyRunner发送给Monkey的命令 ...

  8. 老李推荐:第5章7节《MonkeyRunner源码剖析》Monkey原理分析-启动运行: 循环获取并执行事件 - runMonkeyCycles

    老李推荐:第5章7节<MonkeyRunner源码剖析>Monkey原理分析-启动运行: 循环获取并执行事件 - runMonkeyCycles   poptest是国内唯一一家培养测试开 ...

  9. 老李推荐:第5章6节《MonkeyRunner源码剖析》Monkey原理分析-启动运行: 初始化事件源

    老李推荐:第5章6节<MonkeyRunner源码剖析>Monkey原理分析-启动运行: 初始化事件源   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试 ...

  10. 老李推荐:第5章3节《MonkeyRunner源码剖析》Monkey原理分析-启动运行: 启动脚本

    老李推荐:第5章3节<MonkeyRunner源码剖析>Monkey原理分析-启动运行: 启动脚本   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性 ...

随机推荐

  1. [MongoDB] - mongod.exe参数详解

    mongod.exe是启动mongodb的命令,我们可以通过mongod --help来查看帮助文档.下面是各个参数的对应中文解释.<基于Mongo3.0.5> 通用参数选项 -h/--h ...

  2. ZwQueryVirtualMemory枚举进程模块

    ZwQueryVirtualMemory算是枚举进程方法中的黑科技吧,主要是该方法可以检测出隐藏的模块(类似IceSword). 代码VS2015测试通过 再次奉上源码链接:https://githu ...

  3. devexpress实现模仿Win8桌面metro风格

    1.devexpress强大的控件库,可很容易的实现Win8桌面metro风格.使用的TileControl控件,拖动与Win效果相同.所有图片均来自网络资源.每个块也可实现如图所示的四种大小,如何实 ...

  4. CentOS 7 yum搭建 LAMP

    CentOS 7 搭建LAMP环境 1. Apache 安装 Apache 的软件包名称叫做httpd,因此安装Apache,使用以下命令 [root@localhost ~]# yum -y ins ...

  5. groovy学习(四)io

    package ch5 numbers = [11, 12, 13, 14]def staffTel = ['Ken' : 2745, 'John' : 2746, 'Jessie' : 2772]p ...

  6. MVC和三层架构

    从最开始写程序到现在,一路上听到架构这个词已经无数次了,在工作和圈子里也不停听到大家在讨论它,但是很多时候发现不少人对这个概念的理解都是很模糊的,无意间在知道上看到一个朋友的回答,感觉很不错,特转帖到 ...

  7. JS事件绑定深入

    W3C很好地解决了覆盖问题.相同函数屏蔽的问题.this传递问题.添加额外方法不被覆盖等问题. 但是IE8之前的版本并不支持,IE9已完全支持了. IE和W3C在事件绑定上存在很多差异,我们以冒泡和捕 ...

  8. JavaScript两个变量交换值(不使用临时变量)

    概要  本文主要描述,如何不使用中间值,将两个变量的值进行交换. 一.普通做法 var a = 1, b = 2, tmp; tmp = a; a = b; b = tmp;  普通的做法就是声明多一 ...

  9. jQuery写选项卡

    <!DOCTYPE html> <htmllang="en"> <head> <metacharset="UTF-8" ...

  10. collectionView布局

    关于 collectionView的layout布局方法: 设置cell的间距,行间距,组与组之间的间距,都是在layout里面来设置. 包括,滚动方向. -(void)prepareLayout [ ...