Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android學習之基於隱式的Intent的通訊

Android學習之基於隱式的Intent的通訊

編輯:關於Android編程

Intent隱式通訊

Intent對象可以向操作系統描述我們需要處理的任務。使用顯式intent,我們需明確地告訴操作系統要啟動的activity類名。

下面是之前創建過的顯式intent:

Intent i = new intent(Context packageContext,  Class cls);
startActivity(i);

而使用隱式intent,只需向操作系統描述清楚我們的工作意圖。操作系統會去啟動那些對外宣稱能夠勝任工作任務的activity。如果操作系統找到多個符合的activity,用戶將會看到一個可選應用列表,然後就看用戶如何選擇了。

隱式intents並不聲明要啟動組件的具體類名,而是聲明一個需要執行的action。這個action指定了我們想做的事情,例如查看,編輯,發送或者是獲取一些東西。Intents通常會在發送action的同時附帶一些數據,例如你想要查看的地址或者是你想要發送的郵件信息。數據的具體類型取決於我們想要創建的Intent,比如Uri或其他規定的數據類型,或者甚至也可能根本不需要數據。

典型隱式intent的組成

下面是一個隱式intent的主要組成部分,可以用來定義我們的工作任務。

要執行的操作

通常以Intent類中的常量來表示。
例如,要訪問查看某個URL,可以使用Intent.ACTION_VIEW
要發送郵件,可以使用Intent.ACTION_SEND

例如,查看網頁:

Uri webpage = Uri.parse(http://www.android.com);
Intent webIntent = new Intent(Intent.ACTION_VIEW, webpage);

要訪問數據的位置

這可能是設備以外的資源,如某個網頁的URL,也可能是指向某個文件的URI,或者是指向ContentProvider中某條記錄的某個內容URI(content URI)。

如果數據是一個Uri,會有一個簡單的Intent() 構造方法 用於定義action與data。

例如,下面是一個帶有指定電話號碼的intent:

Uri number = Uri.parse(tel:1234567);
Intent callIntent = new Intent(Intent.ACTION_DIAL, number);

操作涉及的數據類型

這指的是MIME形式的數據類型,如text/html或audio/mpeg3。如果一個intent包含某類數據的位置,那麼通常可以從中推測出數據的類型。

可選類別

如果操作用於描述具體要做什麼,那麼類別通常用來描述我們是何時、何地或者說如何使用某個activity的。
Android的android.intent.category.LAUNCHER類別表明,activity應該顯示在頂級應用啟動器中。
而android.intent.category.INFO類別表明,雖然activity向用戶顯示了包信息,但它不應該顯示在啟動器中。

一個用來查看某個網址的簡單隱式intent會包括一個Intent.ACTION_VIEW操作,以及某個具體URL網址的uri數據。

基於以上信息,操作系統將啟動適用應用的適用activity(如果有多個適用應用可選,用戶可自行如何選擇)。

舉例intent過濾器

通過配置文件中的intent過濾器設置,activity會對外宣稱自己是適合處理ACTION_VIEW的activity。

如果是開發一款浏覽器應用,為響應ACTION_VIEW操作,需要在activity聲明中包含以下intent過濾器:


   
      
      
      
   
 

DEFAULT類別必須明確地在intent過濾器中進行設置。intent過濾器中的action元素告訴操作系統,activity能夠處理指定的任務。
DEFAULT類別告訴操作系統,activity願意處理某項任務。DEFAULT類別必須明確地在intent過濾器中進行設置。

DEFAULT類別實際隱含添加到了幾乎每一個隱式intent中。(唯一的例外是LAUNCHER類別)。

有時間再探索下這個Intent過濾器的使用^_^

隱式intent的附加數據

如同顯式intent,隱式intent也可以包含extra信息。不過,操作系統在尋找適用的activity時,它不會使用任何附加在隱式intent上的extra。

一些需要extra數據的隱式intent,我們可以使用 putExtra() 方法來添加那些數據。 默認的,系統會根據Uri數據類型來決定需要哪些合適的MIME type。如果我們沒有在intent中包含一個Uri, 則通常需要使用 setType() 方法來指定intent附帶的數據類型。設置MIME type 是為了指定應該接受這個intent的activity

例如,發送一個帶附件的email:

Intent emailIntent = new Intent(Intent.ACTION_SEND);
// 這個 intent 沒有一個URI, 因此需要聲明text/plain MIME type
emailIntent.setType(HTTP.PLAIN_TEXT_TYPE);
emailIntent.putExtra(Intent.EXTRA_EMAIL, new String[] {[email protected]}); // 收件人
emailIntent.putExtra(Intent.EXTRA_SUBJECT, Email 主題);
emailIntent.putExtra(Intent.EXTRA_TEXT, Email的文本信息);
emailIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse(content://path/to/email/attachment));
// 你也可以附加多個項通過ArrayList

注意:請盡可能的將隱式Intent定義的更加確切。例如,如果想要使用ACTION_VIEW 的intent來顯示一張圖片,則還應該指定 MIME type 為image/*.這樣能夠阻止其他能夠 “查看” 其他數據類型的app(比如一個地圖app) 被這個intent喚起。

驗證是否有App去接收這個Intent

盡管Android系統會確保每一個確定的intent會被系統內置的app(如the Phone, Email, or Calendar app)之一接收,但是我們還是應該在觸發一個intent之前做驗證是否有App接受這個intent的步驟。

如果系統沒有對應的activity被喚起,則應用會崩潰!

為了驗證是否有合適的activity會響應這個intent,需要執行queryIntentActivities() 來獲取到能夠接收這個intent的所有activity的list。若返回的List非空,那麼我們才可以安全的使用這個intent。

下面是一個演示了如何創建一個intent來查看通訊錄聯系人的完整例子,首先驗證有app可以處理這個intent,然後啟動它

// 新建的隱式intent將由操作以及數據獲取位置組成。
// 操作為Intent.ACTION_PICK
// 數據位置為ContactsContract.Contacts.CONTENT_URI,聯系人通訊錄
Intent i = new Intent(Intent.ACTION_PICK, ContactsContract.Contacts.CONTENT_URI);

// 檢查設備中可以響應的activity
PackageManager pm = getActivity().getPackageManager();
List activities = pm.queryIntentActivities(i, 0);
boolean isIntentSafe = activities.size() > 0;
if (isIntentSafe) {
    // 需要從打開的activity中獲得返回數據
    startActivityForResult(i, CONTACT_REQUEST_CODE);
}

Note:我們必須在第一次使用之前做這個檢查,若是不可行,則應該關閉這個功能。

使用Intent啟動Activity

當創建好了intent並且設置好了extra數據後,通過執行startActivity() 將intent發送到系統。若系統確定了多個activity可以處理這個intent,它會顯示出一個對話框,讓用戶選擇啟動哪個app。如果系統發現只有一個app可以處理這個intent,則系統將直接啟動該app。

startActivity(intent);

這裡寫圖片描述

顯示分享App的選擇界面

當以startActivity()的形式傳遞一個intent,並且有多個app可以處理時,用戶可以在彈出對話框的時候選擇默認啟動的app(通過勾選對話框下面的選擇框,如上圖所示)。該功能對於用戶有特殊偏好的時候非常有用(例如用戶總是喜歡啟動某個app來查看網頁,總是喜歡啟動某個camera來拍照)。

然而,如果用戶希望每次都彈出選擇界面,而且每次都不確定會選擇哪個app啟動,例如分享功能,用戶選擇分享到哪個app都是不確定的,這個時候,需要強制彈出選擇的對話框。(這種情況下用戶不能選擇默認啟動的app)。

為了顯示選擇對話框, 需要使用createChooser()來創建Intent。

Intent intent = new Intent(Intent.ACTION_SEND);
...

// 分享對話框的標題
String title = getResources().getText(R.string.chooser_title);
// 創建和啟動選擇器
Intent chooser = Intent.createChooser(intent, title);
startActivity(chooser);

這裡寫圖片描述

這樣就列出了可以響應createChooser()中Intent的app,並且指定了標題。

Android學習之基於顯式的Intent的通訊

 

  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved