主要分析android的systemui业务,并以此为基础,扩展到view的绘制,事件处理,window管理等等。
这里是第一部分,systemui的view的初步加载。
Systemui的界面,一般形状是如绿色标示部分,拉下来后显示下面全图的样子。
对于view类的管理,可以用hierarchyviewer工具查看。这里也要详细介绍。
最外层的view是StatusbarWindowView,由
private void addStatusBarWindow() { makeStatusBarView(); mStatusBarWindowManager = new StatusBarWindowManager(mContext); mStatusBarWindowManager.add(mStatusBarWindow, getStatusBarHeight()); }
这段代码加载和显示。
mStatusBarWindow= (StatusBarWindowView) View.inflate(context,
R.layout.super_status_bar, null);
mStatusBarView = (PhoneStatusBarView) mStatusBarWindow.findViewById(R.id.status_bar);
mNotificationPanel = (NotificationPanelView) mStatusBarWindow.findViewById( R.id.notification_panel);
mStatusBarWindow 对象,Framelayout的子类,对应的布局为super_status_bar。
在此布局文件中,
layout="@layout/status_bar"
android:layout_width="match_parent"
android:layout_height="@dimen/status_bar_height" />
android:id="@+id/panel_holder"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/transparent" >
layout="@layout/status_bar_expanded"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:visibility="gone" />
第一个为状态栏,对应类PhoneStatusBarView;第二个status_bar_expanded文件,对应着类mNotificationPanel。
看一下他们的布局,或者说dimension。Statusbar_bar,初始状态宽和高各为match_parent和"@dimen/status_bar_height";而PanelHolder为match_parent和"match_parent"。
那在这种情况下,显示高度是多少?都是match_parent,那就看他们的parent。
StatusbarWindowView的dimension是”match_parent”,那就继续找parent。还是看
addStatusBarWindow
这个方法。
通过
getStatusBarHeight
获得状态栏的高度,为25dip。
也就是说在StatusBarWindowManager中设置StatusBarWindowView的高度、宽度。代码为
/** * Adds the status bar view to the window manager. * * @param statusBarView The view to add. * @param barHeight The height of the status bar in collapsed state. */ public void add(View statusBarView, int barHeight) { // Now that the status bar window encompasses the sliding panel and its // translucent backdrop, the entire thing is made TRANSLUCENT and is // hardware-accelerated. mLp = new WindowManager.LayoutParams( ViewGroup.LayoutParams.MATCH_PARENT, barHeight, WindowManager.LayoutParams.TYPE_STATUS_BAR, WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_TOUCHABLE_WHEN_WAKING | WindowManager.LayoutParams.FLAG_SPLIT_TOUCH | WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH | WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS, PixelFormat.TRANSLUCENT); mLp.flags |= WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED; mLp.gravity = Gravity.TOP; mLp.softInputMode = WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE; mLp.setTitle("StatusBar"); mLp.packageName = mContext.getPackageName(); mStatusBarView = statusBarView; mBarHeight = barHeight; mWindowManager.addView(mStatusBarView, mLp); mLpChanged = new WindowManager.LayoutParams(); mLpChanged.copyFrom(mLp); }
设置了WindowManager.LayoutParams参数后,把它添加到window中。
mWindowManager.addView(mStatusBarView, mLp);
type为TYPE_STATUS_BAR,