日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 运维知识 > Android >内容正文

Android

Android之Launcher分析和修改3——Launcher启动和初始化

發(fā)布時間:2023/12/4 Android 41 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Android之Launcher分析和修改3——Launcher启动和初始化 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

前面兩篇文章都是寫有關(guān)Launcher配置文件的修改,代碼方面涉及不多,今天開始進入Launcher代碼分析。

我們開機啟動Launcher,Launcher是由Activity?Manager啟動的,而Activity?Manager是由system?server啟動。

原創(chuàng)博文,轉(zhuǎn)載請標(biāo)明出處:http://www.cnblogs.com/mythou/p/3157452.html?

1、Launcher進程啟動過程

可以由下面圖看到Launcher進程是如何被創(chuàng)建啟動:



Activity Manager通過發(fā)送Intend來啟動Launcher。

復(fù)制代碼//Edited by mythou //http://www.cnblogs.com/mythou/Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); intent.setComponent(mTopComponent); if (mFactoryTest != SystemServer.FACTORY_TEST_LOW_LEVEL) {intent.addCategory(Intent.CATEGORY_HOME); } startActivityLocked(null, intent, null, null, 0, aInfo,null, null, 0, 0, 0, false, false);

因此,如果你要開機啟動一個替換Launcher的程序,只要在程序<intent-filter>里面加入action.MAIN 、

category.HOME、category.DEFAULT就可以。如果出現(xiàn)多個程序都加入這種intent,系統(tǒng)會彈出讓你選擇

哪個作為啟動器。

?

2、Launcher初始化——LauncherApplication。

Application類,我想大部分做Android應(yīng)用的朋友都用過,每個Android應(yīng)用默認(rèn)都有一個Application類,

你也可以繼承Application類,然后加入自己代碼。Application是一個全局的應(yīng)用類,在AndroidManifest.xml

我們也可以找到Application標(biāo)簽。

復(fù)制代碼//Edited by mythou //http://www.cnblogs.com/mythou/<applicationandroid:name="com.android.launcher2.LauncherApplication"android:label="@string/application_name" android:icon="@drawable/ic_launcher_home"android:hardwareAccelerated="@bool/config_hardwareAccelerated"android:largeHeap="@bool/config_largeHeap"android:configChanges="locale"></application>

Android四大組件的聲明都需要放到application標(biāo)簽里面,默認(rèn)使用的是系統(tǒng)的Application類,如果你在項目

里面重載了它。就需要在標(biāo)簽,name屬性下寫上你的新的Application類名。Launcher里面就是繼承了Application

LauncherApplication。應(yīng)用啟動的時候首先會加載Application。

我們可以看到Launcher主類Launcher.java的onCreate函數(shù)里面,第一個就是獲取Application的實例。

LauncherApplication app = ((LauncherApplication)getApplication());

接下來我們看看LauncherApplication里面初始化,LauncherApplication大部分工作就是在初始化完成,剩下都是

一些返回接口。

//Edited by mythou //http://www.cnblogs.com/mythou/@Overridepublic void onCreate() {super.onCreate();//獲取屏幕大小,主要用來區(qū)分手機還是平板final int screenSize = getResources().getConfiguration().screenLayout &Configuration.SCREENLAYOUT_SIZE_MASK;sIsScreenLarge = screenSize == Configuration.SCREENLAYOUT_SIZE_LARGE ||screenSize == Configuration.SCREENLAYOUT_SIZE_XLARGE;//屏幕密度sScreenDensity = getResources().getDisplayMetrics().density;//IconCahe里面保存了界面所有應(yīng)用圖標(biāo)的繪畫需要的數(shù)據(jù),這個到時候具體分析再說。//加入這東西的主要原因是為了提高繪畫界面的效率mIconCache = new IconCache(this);//數(shù)據(jù)庫加載類,LauncherModel是Launcher里面非常重要的一個類,相當(dāng)于MVC模式里面的//Model功能,管理數(shù)據(jù)和初始化數(shù)據(jù)mModel = new LauncherModel(this, mIconCache);//下面注冊了一些監(jiān)聽器,主要包含APK文件更新刪除等數(shù)據(jù)變化的時候接收的通知//接收通知后,主要是用來更新Launcher里面的數(shù)據(jù)庫。因為桌面應(yīng)用圖標(biāo)數(shù)據(jù),只會加載一次IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);filter.addAction(Intent.ACTION_PACKAGE_REMOVED);filter.addAction(Intent.ACTION_PACKAGE_CHANGED);filter.addDataScheme("package");registerReceiver(mModel, filter);filter = new IntentFilter();filter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE);filter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE);filter.addAction(Intent.ACTION_LOCALE_CHANGED);filter.addAction(Intent.ACTION_CONFIGURATION_CHANGED);registerReceiver(mModel, filter);filter = new IntentFilter();filter.addAction(SearchManager.INTENT_GLOBAL_SEARCH_ACTIVITY_CHANGED);registerReceiver(mModel, filter);filter = new IntentFilter();filter.addAction(SearchManager.INTENT_ACTION_SEARCHABLES_CHANGED);registerReceiver(mModel, filter);//contentresolver則是用于管理所有程序的contentprovider實例ContentResolver resolver = getContentResolver();//注冊內(nèi)容觀察者,監(jiān)聽application數(shù)據(jù)庫變化,回調(diào)resolver.registerContentObserver(LauncherSettings.Favorites.CONTENT_URI, true, mFavoritesObserver);}

上面是LauncherApplication最主要的工作,初始化整個Launcher的一些關(guān)鍵類,和注冊一些監(jiān)聽器。主要都是用

來監(jiān)聽?wèi)?yīng)用的安裝更新刪除等導(dǎo)致Launcher數(shù)據(jù)庫變化的操作。Launcher數(shù)據(jù)都是使用contentprovider來提供數(shù)據(jù)。

其中注冊的監(jiān)聽接口是

//Edited by mythou //http://www.cnblogs.com/mythou/private final ContentObserver mFavoritesObserver = new ContentObserver(new Handler()) {@Overridepublic void onChange(boolean selfChange) {//重新加載界面數(shù)據(jù)mModel.startLoader(LauncherApplication.this, false);}};
LauncherSettings.Favorites.CONTENT_URI里面數(shù)據(jù)發(fā)生變化的時候,都會調(diào)用mModel.startLoader()接口, 重新加載Launcher的數(shù)據(jù)。startLoader的具體操作,我后面分析LauncherModel類的時候會分析。這一塊涉及 Launcher所有數(shù)據(jù)加載。剩下的接都是返回初始化時候創(chuàng)建的對象或者獲取屏幕密度、獲取是否大屏幕。 后面很多處理都需要判斷是否是大屏幕,4.0以后手機平板都共用一套系統(tǒng),導(dǎo)致多了很多處理。

?

3、Launcher.java初始化

Launcher.java是Launcher里面最主要的類,是一個Activity。啟動的第一個組件。既然是Activity,我們要分析它

初始化,毫無疑問,需要找到onCreate()里面分析。把主要一些分析用注釋方式寫在代碼里面,這樣比較方便閱讀。

//Edited by mythou //http://www.cnblogs.com/mythou/@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);//獲取Application 實例LauncherApplication app = ((LauncherApplication)getApplication());//LauncherModel類里面獲取Launcher的對象引用mModel = app.setLauncher(this);//獲取IconCache,IconCache在Application里面初始化    mIconCache = app.getIconCache();mDragController = new DragController(this);mInflater = getLayoutInflater();mAppWidgetManager = AppWidgetManager.getInstance(this);//監(jiān)聽widget改變,以后在Model里面回調(diào)處理的結(jié)果mAppWidgetHost = new LauncherAppWidgetHost(this, APPWIDGET_HOST_ID);mAppWidgetHost.startListening();//這個是設(shè)置Launcher的跟蹤調(diào)試文件,下面很多信息會寫到這個文件里面。if (PROFILE_STARTUP) {android.os.Debug.startMethodTracing(Environment.getExternalStorageDirectory() + "/launcher");}//讀取本地配置,保存更新配置,清空IconCachecheckForLocaleChange();setContentView(R.layout.launcher);//對所有的UI控件進行加載和配置setupViews();//顯示操作提示,第一次啟動的時候才會顯示showFirstRunWorkspaceCling();//注冊監(jiān)控Launcher數(shù)據(jù)庫變化registerContentObservers();//鎖住APP,初始化不能操作。lockAllApps();mSavedState = savedInstanceState;restoreState(mSavedState);// Update customization drawer _after_ restoring the statesif (mAppsCustomizeContent != null) {mAppsCustomizeContent.onPackagesUpdated();}if (PROFILE_STARTUP) {android.os.Debug.stopMethodTracing();}//加載啟動數(shù)據(jù),所有界面數(shù)據(jù)(快捷方式、folder、widget、allApp)等在loader里面加載,這部分后面我會詳細(xì)分析。if (!mRestoring) {mModel.startLoader(this, true);}if (!mModel.isAllAppsLoaded()) {ViewGroup appsCustomizeContentParent = (ViewGroup) mAppsCustomizeContent.getParent();mInflater.inflate(R.layout.apps_customize_progressbar, appsCustomizeContentParent);}// For handling default keysmDefaultKeySsb = new SpannableStringBuilder();Selection.setSelection(mDefaultKeySsb, 0);IntentFilter filter = new IntentFilter(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);registerReceiver(mCloseSystemDialogsReceiver, filter);//下面這幾個就是Android原生界面上的Market、搜索、聲音輸入按鈕的默認(rèn)圖標(biāo)顯示。boolean searchVisible = false;boolean voiceVisible = false;// If we have a saved version of these external icons, we load them up immediatelyint coi = getCurrentOrientationIndexForGlobalIcons();if (sGlobalSearchIcon[coi] == null || sVoiceSearchIcon[coi] == null ||sAppMarketIcon[coi] == null) {updateAppMarketIcon();searchVisible = updateGlobalSearchIcon();voiceVisible = updateVoiceSearchIcon(searchVisible);}if (sGlobalSearchIcon[coi] != null) {updateGlobalSearchIcon(sGlobalSearchIcon[coi]);searchVisible = true;}if (sVoiceSearchIcon[coi] != null) {updateVoiceSearchIcon(sVoiceSearchIcon[coi]);voiceVisible = true;}if (sAppMarketIcon[coi] != null) {updateAppMarketIcon(sAppMarketIcon[coi]);}mSearchDropTargetBar.onSearchPackagesChanged(searchVisible, voiceVisible);// On large interfaces, we want the screen to auto-rotate based on the current orientationif (LauncherApplication.isScreenLarge() || Build.TYPE.contentEquals("eng")) {setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);}Log.i(TAG,"------------------------>Launcher init over") ;}

?上面就是Launcher.java的初始化,大部分我都寫了注釋。其實這里最主要的工作是加載界面數(shù)據(jù):

mModel.startLoader(this, true); 這塊實現(xiàn)是在LauncherModel里面實現(xiàn)的。下一篇文章,我會詳細(xì)

說明如何加載和獲取管理系統(tǒng)里面的APP相關(guān)數(shù)據(jù)。



總結(jié)

以上是生活随笔為你收集整理的Android之Launcher分析和修改3——Launcher启动和初始化的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。