淺談Activity之啟動方式(5種啟動方式和隱式啟動)
Activity在Android APP中的重要性不言而喻,那麼瞭解Activity的幾種不同的啟動方式對設計出好的App至關重要!
眾所周知Activity的啟動方式有如下幾種
1.在“Home”下點選圖示,啟動應用程式的首個Activity。我們稱之為主Activity,這是最常見的啟動方式,而且代表程式具備獨立的執行條件。通常會在Manifest中指定某個Activity的android.intent.category屬性為Launcher。
(實際上這也是隱式啟動Activity的其中一個)
2.在程式中啟動Activity。應用(startActivity() 或者startActivityForResult()
3.強制程式僅以被其它程式呼叫的方式啟動(沒有直接的啟動入口):在系統中有相當一部分的應用程式需要有嚴格的執行條件(Context),其無法以Stand
alone的方式獨立運行於程序中。具備這種特性的Application大體上分為兩種:其一,帶有特定返回值的應用程式。parent出於當前操作需要,通過啟動其它Application來獲得某些特定的資源。例如:輸入法或者檔案資源選擇器等。另外一種情況,經常被呼叫來修改系統設定或者提供單一有特定目的的操作。這樣的Application無需在Home中提供快捷啟動方式,其僅僅被其它某些程式在特定的需求下來滿足需求。例如:更換系統鈴音程式。
4.在一個Application中包含有多個Mian
Activities,並且各自具備有獨立的啟動入口:很多開發者都習慣於預設的開發配置,一個Application僅僅包含一個獨立的應用。然後在特定的需求下可以打破這個限定,系統允許開發者將多個Main Activities應用捆綁在同一個Application中,而且這些Main Activities可以在Home中有獨立的啟動快捷方式。然而有非常重要的一點需要特別強調,這種方式並不提倡在任何情況下采用,一般當兩個應用程式需要呼叫相同的系統資源或者包含有大部分相同功能的應用時,才可以考慮採用這種方式來簡化使用者的安裝過程(另外一個角度來看,起到優化系統資源的目的)。技術上需要注意為不同的Main
Activity定義不同的Task affinity。例如:Camera和Camcorder,它們共同使用攝像頭,而且同樣採用Gallery作為資源管理器,他們的Task Affinity分別設定為:”com.android.camera” 和 “com.android.videocamera”。
5.以Widget的方式體現Activity的應用價值:嚴格意義上來看,這的確算得上是一種啟動方式,某些Application將部分常用的功能以Widget的形式在Home或者其它Application中被引用。
接下來,我們介紹一下有關隱式啟動:
(1)
根據Action和Category資訊來進行匹配
在Manifest.xml中註冊該Activity
<activity android:name=".TestActivity" android:label="TestActivity">
<intent-filter >
<action android:name="cn.xiaoyao.test"/>
<category android:name="android.intent.category.DEFAULT"/>
</intent-filter>
</activity>
在MainActivity.java裡啟動該Activity:
Intent intent = new Intent();
intent.setAction( "cn.xiaoyao.test");//設定intent的Action屬性值
intent.addCategory(Intent.CATEGORY_DEFAULT);//不加這行也行,因為這個值預設就是Intent.CATEGORY_DEFAULT
startActivity( intent );
(2) 根據Action和Data資訊進行匹配
在Manifest.xml中註冊該Activity
<activity
android:name=".TestActivity"
android:label="@string/testactivity">
<intent-filter>
<action android:name="cn.xiaoyao.test"></action>
<category android:name="android.intent.category.DEFAULT"></category>
<data android:scheme="xiaoyao"></data>
</intent-filter>
</activity>
如上註冊資訊,合法的Uri的寫法如下:
在MainActivity.java裡啟動該Activity:// Uri uri = Uri.parse("xiaoyao"); // 不行 // Uri uri = Uri.parse("xiaoyao://"); // 可以 // Uri uri = Uri.parse("xiaoyao:"); // 可以 // Uri uri = Uri.parse("xiaoyao://www.google.com/getDetails?id=123"); // 可以
Intent intent = new Intent();
intent.setAction("cn.xiaoyao.test");//僅有data不能匹配,所以要設定Action屬性
intent.addCategory(Intent.CATEGORY_DEFAULT);//可去除
intent.setData(uri);//設定data屬性
startActivity(in);
(3) 根據action和data的mimeType屬性匹配 在Manifest.xml中註冊該Activity
<activity android:name=".TestActivity" android:label="@string/testactivity">
<intent-filter>
<action android:name="android.intent.action.VIEW"></action>
<data android:mimeType="vnd.android.cursor.dir/vnd.google.note" />
<category android:name="android.intent.category.DEFAULT"></category>
</intent-filter>
</activity>
在MainActivity.java裡啟動該Activity:
Intent intent = new Intent();
intent .setAction("android.intent.action.VIEW");
intent .addCategory(Intent.CATEGORY_DEFAULT);//可去掉
intent.setType("vnd.android.cursor.dir/vnd.google.note");//要設定Data的MIMEType屬性
startActivity(intent );
注意:一個Activity中可以包括多個intent-filter屬性,intent-filter屬性中也可以包含多個data標籤對,只需要有一個滿足便可以匹配成功。
如果匹配不到合適的Activity啟動時,會丟擲異常給使用者一個提示“應用程式意外停止”!
參考: