lin20080410的专栏

从站在巨人的肩上,向成为巨人迈进... 互相学习!

Android GUI系统-ViewTree的管理者(三)

作为ViewTree的管理者ViewRoot,是怎么工作的。


一,ViewRootImpl跟WMS间的通信

ViewRootImpl.java在构造的时候,需要建立跟WMS的通信的双向通道:

ViewRootImpl –>WMS:IwindowSession

WMS →ViewRootImpl :Iwindow

IwindowSessionIWindow是匿名的BinderServer需要借助一定的方式才能提供服务。

1)在ViewRootImpl的构造函数中,利用WMS提供的openSession接口获取IWindowSession的服务句柄,存储在内部变量mWindowSession中。

public ViewRootImpl(Context context, Display display) @ViewRootImpl.java{
	mWindowSession = WindowManagerGlobal.getWindowSession();
}

public static IWindowSession getWindowSession() @WindowManagerGlobal.java{
	if (sWindowSession == null) {
		InputMethodManager imm = InputMethodManager.getInstance();
		IWindowManager windowManager = getWindowManagerService();
		sWindowSession = windowManager.openSession(
			new IWindowSessionCallback.Stub() {
				public void onAnimatorScaleChanged(float scale) {
					ValueAnimator.setDurationScale(scale);
				}
			},
			imm.getClient(), imm.getInputContext());
	}
	return sWindowSession;
}

这里的IWindowManagerWindowManagerService在本地进程端的代理,windowManager的请求都是在远程端有WMS实现;

ActivityThread中,处理handleResumeActivity时,也有一个WindowManager,即:ViewManager wm =a.getWindowManager();这里的wmViewManager,它是WindowManager类的基类,最终实现是WindowManagerImpl,是完全属于本地端的,存储与应用进程内部用于窗口管理的相关事务。


2)在handleResumeActivity中,通过wm.addView(decor,l),最后会调用ViewRootImplsetView,这个函数一方面把DecorView,也即是viewtree的根设置到ViewRootImpl中,用mView保存;另一方面会向WMS申请注册一个窗口,同时把mWindow对象(W类型,也是ViewRootImpl的内部类,是Iwindow服务端的实现)传给WMS,实现WMS跟Viewroot的通信。

public void setView(View view, WindowManager.LayoutParams attrs, View panelParentView) 	@ViewRootImpl.java{
	res = mWindowSession.addToDisplay(mWindow, mSeq, mWindowAttributes,
		getHostVisibility(), mDisplay.getDisplayId(),
		mAttachInfo.mContentInsets, mAttachInfo.mStableInsets,
		mAttachInfo.mOutsets, mInputChannel);
}

跟窗口相关的两个概念,phoneWindow继承自Window类,是应用进程端对窗口的描述,表达了对窗口的一种约束;WMS中的window是一个抽象的概念,用WindowState来描述其状态,WindowState可以认为是WMS中对窗口的描述。


二,ViewRootImpl的工作方式

每个ViewTree只对应一个ViewRoot,它将跟WMS进行一系列的通信,包括窗口的注册、大小调整等。什么情况会执行这些操作?

1ViewTree内部的请求,如view对象要更新UI,它会通过invalidate或者其他方式发起请求,随后这些请求会沿着ViewTree层层网上传递,最终到达ViewRoot,做为ViewTree的管理者它根据一系列实际情况来执行相应操作(如发起一次遍历、通知WMS等)。

2)外部的状态更新,如WMS回调viewroot通知界面大小改变、触摸事件、按键事件等。

不管是内部请求、还是外部请求,viewroot通常会把这些消息入栈,然后ViewRootImplViewRootHandler类来统一处理他们。ViewRootImpl是在WindowManagerImpladdView的过程中创建的,addView调用的起点是ActivityThreadhandleResumeActivity,所以说ViewRootImpl实际是运行在主线程中,ViewRootHandler实际上会跟主线程的消息队列挂钩。


内外部的请求都先入队到主线程的messagequeue,再有Viewroot具体处理。



阅读更多
版权声明:笔记记录,互相学习,不足之处,欢迎指正! https://blog.csdn.net/lin20044140410/article/details/78886242
想对作者说点什么? 我来说一句

viewTree

u011052996 u011052996

2015-03-20 14:11:26

阅读数:304

没有更多推荐了,返回首页

加入CSDN,享受更精准的内容推荐,与500万程序员共同成长!
关闭
关闭