Android View(2)Viewのロードプロセス
6442 ワード
このシリーズでは、Android Viewの使用とコアソース分析を逐次漸進的に学習します.Android View(1)Viewのツリー構造と座標計算Android View(2)ViewのロードプロセスAndroid View(3)View LayoutInflaterソースコード解析Android View(4)Viewの描画プロセス
Viewのロード・プロシージャ
AndroidがビューをロードするプロセスはActivityのsetContentView(@LayoutRes int layoutResID)でロードされるので,ソースコード(オンラインソースリンク)プロセスを解析することによって理解する. setContentView(int layoutResID)ソースコード分析前編では、WindowPhoneクラスがWindowクラスを継承していると述べていますが、Windowクラスはいくつかの方法と仕様を定義しているだけなので、WindowPhoneクラスの方法を直接見てみましょう.3つのリロード方法があります.私たちは1つだけ分析します.コードは以下の通りです.
次にinstallDecor()コードを見てみましょう.
次にgenerateLayout(DecorView decor)メソッドのソースコードを解析する
実はgeneateLayoutでは、リストファイルで設定したトピックに基づいて、対応するトピック、レイアウトなどをロードします.
まとめ setContentView()レイアウトをロードするプロセスを整理します.まず、最初の呼び出しであれば、ActivityルートビューとしてDecorViewオブジェクトを作成します.最初の呼び出しでなければ、前のレイアウトを削除し、ルートビューとしてDecorViewオブジェクトを引き続き使用します.レイアウトをロードするときに設定したThemStyleでプロパティ値を設定します.その後findviewbyidによりDeporeViewにレイアウトファイルを追加し、ActivityのonContentChangedメソッドをコールバックしてレイアウトロード完了 を通知する.ビューをロードする過程で、システムは再帰的に一歩一歩解析的にロードするので、私たちは開発の中で、できるだけ多層のレイアウトをネストしないで、レイアウトのロード効率に影響して、mergeラベルを通じてネスト層数を減らすことができます.
リファレンスソース:http://androidxref.com/8.0.0_r4/xref/frameworks/base/core/ 投げ物線ブログ:http://hencoder.com/ : http://www.jianshu.com/p/f76a6f6f75aasetContentViewロードビューメカニズムhttp://www.jianshu.com/p/0819a858b53csetContentViewソース分析http://www.jianshu.com/p/bb7977990baaAndroid view描画プロセス、ソースコード解読http://www.jianshu.com/p/b272528165a2androidカスタムview ColorFilter:https://github.com/chengdazhi/StyleImageView(カスタムビューの遊び方)
Viewのロード・プロシージャ
AndroidがビューをロードするプロセスはActivityのsetContentView(@LayoutRes int layoutResID)でロードされるので,ソースコード(オンラインソースリンク)プロセスを解析することによって理解する.
@Override
public void setContentView(int layoutResID) {
// Note: FEATURE_CONTENT_TRANSITIONS may be set in the process of installing the window
// decor, when theme attributes and the like are crystalized. Do not check the feature
// before this happens.
//
if (mContentParent == null) {
// DecorView, mContentParent
installDecor();
//hasFeature(FEATURE_CONTENT_TRANSITIONS)
} else if (!hasFeature(FEATURE_CONTENT_TRANSITIONS)) {
// View
mContentParent.removeAllViews();
}
if (hasFeature(FEATURE_CONTENT_TRANSITIONS)) {
// Scene ( View )
final Scene newScene = Scene.getSceneForLayout(mContentParent, layoutResID,
getContext());
transitionTo(newScene);
} else {
// mContentParent
mLayoutInflater.inflate(layoutResID, mContentParent);
}
mContentParent.requestApplyInsets();
final Callback cb = getCallback();
if (cb != null && !isDestroyed()) {
//
cb.onContentChanged();
}
// Whether the client has explicitly set the content view. If false and mContentParent is notnull, then the content parent was set due to window preservation.
//
mContentParentExplicitlySet = true;
}
次にinstallDecor()コードを見てみましょう.
private void installDecor() {
2640 mForceDecorInstall = false;
// mDecor , Decor,
2641 if (mDecor == null) {
// System process doesn't have application context and in that case we need to directly use the context we have.
// Otherwise we want the application context, so we don't cling to the activity.
//generateDecor() Decor Activity
2642 mDecor = generateDecor(-1);
// View View
2643 mDecor.setDescendantFocusability(ViewGroup.FOCUS_AFTER_DESCENDANTS);
// mDecor Activity , DecorView
2644 mDecor.setIsRootNamespace(true);
//
2645 if (!mInvalidatePanelMenuPosted && mInvalidatePanelMenuFeatures != 0) {
2646 mDecor.postOnAnimation(mInvalidatePanelMenuRunnable);
2647 }
2648 } else {
2649 mDecor.setWindow(this);
2650 }
2651 if (mContentParent == null) {
// , , id content FrameLayout mContentParent
2652 mContentParent = generateLayout(mDecor);
2653
2654 // Set up decor part of UI to ignore fitsSystemWindows if appropriate.
2655 mDecor.makeOptionalFitsSystemWindows();
2656 // DecorView , title,window
2657 final DecorContentParent decorContentParent = (DecorContentParent) mDecor.findViewById(
2658 R.id.decor_content_parent);
2659
2660 if (decorContentParent != null) {
2661 //1. decorContentParent mDecorContentParent
//2.
//3. title、icon、logo
2699 } else {
2700 mTitleView = findViewById(R.id.title);
// ActionBar , setContentView
2701 if (mTitleView != null) {
2702 if ((getLocalFeatures() & (1 << FEATURE_NO_TITLE)) != 0) {
2703 final View titleContainer = findViewById(R.id.title_container);
2704 if (titleContainer != null) {
2705 titleContainer.setVisibility(View.GONE);
2706 } else {
2707 mTitleView.setVisibility(View.GONE);
2708 }
2709 mContentParent.setForeground(null);
2710 } else {
2711 mTitleView.setText(mTitle);
2712 }
2713 }
2714 }
2715
2716 if (mDecor.getBackground() == null && mBackgroundFallbackResource != 0) {
2717 mDecor.setBackgroundFallback(mBackgroundFallbackResource);
2718 }
2719 //.... , ,
2770 }
2771 }
2772 }
2773 }
次にgenerateLayout(DecorView decor)メソッドのソースコードを解析する
// Activity , mContentParent
protected ViewGroup generateLayout(DecorView decor) {
2309 // Apply data from current theme.
2310 //
2311 TypedArray a = getWindowStyle();
2312 // Them ,
.......
// title background
2627 }
2628
2629 mDecor.finishChanging();
2630
2631 return contentParent;
2632 }
実はgeneateLayoutでは、リストファイルで設定したトピックに基づいて、対応するトピック、レイアウトなどをロードします.
まとめ
リファレンス