Intent是一個消息傳遞對象,您可以使用它從其他應用組件請求操作。盡管 Intent 可以通過多種方式促進組件之間的通信,但其基本用例主要包括以下三個:
1.啟動 Activity:
Activity 表示應用中的一個屏幕。通過將 Intent 傳遞給 startActivity(),您可以啟動新的 Activity 實例。Intent 描述了要啟動的 Activity,並攜帶了任何必要的數據。如果您希望在 Activity 完成後收到結果,請調用 startActivityForResult()。在 Activity 的 onActivityResult() 回調中,您的 Activity 將結果作為單獨的 Intent 對象接收。
2.啟動服務:
Service是一個不使用用戶界面而在後台執行操作的組件。通過將 Intent 傳遞給 startService(),您可以啟動服務執行一次性操作(例如,下載文件)。Intent 描述了要啟動的服務,並攜帶了任何必要的數據。如果服務旨在使用客戶端-服務器接口,則通過將 Intent 傳遞給 bindService(),您可以從其他組件綁定到此服務。
3.傳遞廣播:
廣播是任何應用均可接收的消息。系統將針對系統事件(例如:系統啟動或設備開始充電時)傳遞各種廣播。通過將 Intent 傳遞給 sendBroadcast()、sendOrderedBroadcast() 或 sendStickyBroadcast(),您可以將廣播傳遞給其他應用。
Intent 類型
Intent 分為兩種類型:
1.顯式 Intent :按名稱(完全限定類名)指定要啟動的組件。通常,您會在自己的應用中使用顯式 Intent 來啟動組件,這是因為您知道要啟動的 Activity 或服務的類名。例如,啟動新 Activity 以響應用戶操作,或者啟動服務以在後台下載文件。
2.隱式 Intent :不會指定特定的組件,而是聲明要執行的常規操作,從而允許其他應用中的組件來處理它。例如,如需在地圖上向用戶顯示位置,則可以使用隱式 Intent,請求另一具有此功能的應用在地圖上顯示指定的位置。
創建顯式 Intent 啟動 Activity 或服務時,系統將立即啟動 Intent 對象中指定的應用組件。
創建隱式 Intent 時,Android 系統通過將 Intent 的內容與在設備上其他應用的清單文件中聲明的 Intent 過濾器進行比較,從而找到要啟動的相應組件。Intent如果 Intent 與 Intent 過濾器匹配,則系統將啟動該組件,並將其傳遞給對象。如果多個 Intent 過濾器兼容,則系統會顯示一個對話框,支持用戶選取要使用的應用。
Intent 過濾器是應用清單文件中的一個表達式,它指定該組件要接收的 Intent 類型。例如,通過為 Activity 聲明 Intent 過濾器,您可以使其他應用能夠直接使用某一特定類型的 Intent 啟動 Activity。同樣,如果您沒有為 Activity 聲明任何 Intent 過濾器,則 Activity 只能通過顯式 Intent 啟動。
圖 1.隱式 Intent 如何通過系統傳遞以啟動其他 Activity 的圖解
(1)Activity A 創建包含操作描述的intent,並將其傳遞給startActivity。
(2)Android 系統搜索所有應用中與 Intent 匹配的 Intent 過濾器。找到匹配項之後。
(3)該系統通過調用匹配 Activity(Activity B)的onCreate方法並將其傳遞給Intent,以此啟動匹配 Activity。
警告:為了確保應用的安全性,啟動 Service 時,請始終使用顯式 Intent,且不要為服務聲明 Intent 過濾器。使用隱式 Intent 啟動服務存在安全隱患,因為您無法確定哪些服務將響應 Intent,且用戶無法看到哪些服務已啟動。從 Android 5.0(API 級別 21)開始,如果使用隱式 Intent 調用 bindService(),系統會拋出異常。
構建 Intent
Intent對象攜帶了 Android 系統用來確定要啟動哪個組件的信息(例如,准確的組件名稱或應當接收該 Intent 的組件類別),以及收件人組件為了正確執行操作而使用的信息(例如,要采取的操作以及要處理的數據)。
Intent 中包含的主要信息如下:
1.組件名稱(ComponentName):要啟動的組件名稱。
這是可選項,但也是構建顯式 Intent 的一項重要信息,這意味著 Intent 應當僅傳遞給由組件名稱定義的應用組件。如果沒有組件名稱,則 Intent 是隱式的,且系統將根據其他 Intent 信息(例如,以下所述的操作、數據和類別)決定哪個組件應當接收 Intent。因此,如需在應用中啟動特定的組件,則應指定該組件的名稱。
注意:啟動 Service 時,您應始終指定組件名稱。否則,您無法確定哪項服務會響應 Intent,且用戶無法看到哪項服務已啟動。
Intent 的這一字段是 ComponentName 對象,您可以使用目標組件的完全限定類名指定此對象,其中包括應用的軟件包名稱。例如,com.example.ExampleActivity。您可以使用 setComponent()、setClass()、setClassName() 或 Intent 構造函數設置組件名稱。
2.操作(action):指定要執行的通用操作(例如,“查看”或“選取”)的字符串。
對於廣播 Intent,這是指已發生且正在報告的操作。操作在很大程度上決定了其余 Intent 的構成,特別是數據和 extra 中包含的內容。
您可以指定自己的操作,供 Intent 在您的應用內使用(或者供其他應用在您的應用中調用組件)。但是,您通常應該使用由 Intent 類或其他框架類定義的操作常量。以下是一些用於啟動 Activity 的常見操作:
(1) ACTION_VIEW :
如果您擁有一些某項 Activity可向用戶顯示的信息(例如,要使用圖庫應用查看的照片;或者要使用地圖應用查找的地址),請使用 Intent 將此操作與 startActivity() 結合使用。
(2)ACTION_SEND:
這也稱為“共享” Intent。如果您擁有一些用戶可通過其他應用(例如,電子郵件應用或社交共享應用)共享的數據,則應使用 Intent 中將此操作與 startActivity() 結合使用。
您可以使用 setAction() 或 Intent 構造函數為 Intent 指定操作。
如果定義自己的操作,請確保將應用的軟件包名稱作為前綴。 例如:
static final String ACTION_TIMETRAVEL = "com.example.action.TIMETRAVEL";
3.數據(data):引用待操作數據和/或該數據 MIME 類型的 URI(Uri 對象)。
提供的數據類型通常由 Intent 的操作決定。例如,如果操作是 ACTION_EDIT,則數據應包含待編輯文檔的 URI。
創建 Intent 時,除了指定 URI 以外,指定數據類型(其 MIME 類型)往往也很重要。例如,能夠顯示圖像的Activity可能無法播放音頻文件,即便 URI 格式十分類似時也是如此。因此,指定數據的 MIME 類型有助於 Android 系統找到接收 Intent 的最佳組件。但有時,MIME 類型可以從 URI 中推斷得出,特別當數據是 content: URI 時尤其如此。這表明數據位於設備中,且由 ContentProvider 控制,這使得數據 MIME 類型對系統可見。
要僅設置數據 URI,請調用 setData()。要僅設置 MIME 類型,請調用setType()。如有必要,您可以使用 setDataAndType() 同時顯式設置二者。
警告:若要同時設置 URI 和 MIME 類型,請勿調用 setData() 和 setType(),因為它們會互相抵消彼此的值。請始終使用setDataAndType() 同時設置 URI 和 MIME 類型。
4.類別(CATEGORY):一個包含應處理 Intent 組件類型的附加信息的字符串。
您可以將任意數量的類別描述放入一個 Intent 中,但大多數 Intent 均不需要類別。以下是一些常見類別:
(1) CATEGORY_BROWSABLE
目標 Activity 允許本身通過 Web 浏覽器啟動,以顯示鏈接引用的數據,如圖像或電子郵件。
(2)CATEGORY_LAUNCHER
該 Activity 是任務的初始 Activity,在系統的應用啟動器中列出。
您可以使用 addCategory() 指定類別。
以上列出的這些屬性(組件名稱、操作、數據和類別)表示 Intent 的既定特征。通過讀取這些屬性,Android 系統能夠解析應當啟動哪個應用組件。但是,Intent 也有可能會一些攜帶不影響其如何解析為應用組件的信息。Intent 還可以提供:
5.Extra:攜帶完成請求操作所需的附加信息的鍵值對。
正如某些操作使用特定類型的數據 URI 一樣,有些操作也使用特定的附加數據。
您可以使用各種 putExtra() 方法添加附加數據,每種方法均接受兩個參數:鍵名(key)和值(value)。您還可以創建一個包含所有附加數據的 Bundle 對象,然後使用 putExtras() 將 Bundle 插入 Intent 中。例如,使用 ACTION_SEND 創建用於發送電子郵件的 Intent 時,可以使用 EXTRA_EMAIL 鍵指定“目標”收件人,並使用 EXTRA_SUBJECT 鍵指定“Theme”。
Intent 類將為標准化的數據類型指定多個 EXTRA_* 常量。如需聲明自己的附加數據 鍵(對於應用接收的 Intent ),請確保將應用的軟件包名稱作為前綴。例如:
static final String EXTRA_GIGAWATTS = "com.example.EXTRA_GIGAWATTS";
6.標志(flag):
在 Intent 類中定義的、充當 Intent 元數據的標志。標志可以指示 Android 系統如何啟動 Activity(例如,Activity 應屬於哪個 任務 ),以及啟動之後如何處理(例如,它是否屬於最近的 Activity 列表)。
Intent 示例
1.顯式 Intent 示例
顯式 Intent 是指用於啟動某個特定應用組件(例如,應用中的某個特定 Activity 或服務)的 Intent。要創建顯式 Intent,請為 Intent 對象定義組件名稱。Intent 的所有其他屬性均為可選屬性。
例如,如果在應用中構建了一個名為 DownloadService、旨在從 Web 中下載文件的服務,則可使用以下代碼啟動該服務:
// Executed in an Activity, so 'this' is the Context
// The fileUrl is a string URL, such as "http://www.example.com/image.png"
Intent downloadIntent = new Intent(this, DownloadService.class);
downloadIntent.setData(Uri.parse(fileUrl));
startService(downloadIntent);
Intent(Context, Class) 構造函數分別為應用和組件提供 Context 和 Class 對象。因此,此 Intent 將顯式啟動該應用中的 DownloadService 類。
2.隱式 Intent 示例
隱式 Intent 指定能夠在可以執行相應操作的設備上調用任何應用的操作。如果您的應用無法執行該操作而其他應用可以,且您希望用戶選取要使用的應用,則使用隱式 Intent 非常有用。
例如,如果您希望用戶與他人共享您的內容,請使用 ACTION_SEND 操作創建 Intent,並添加指定共享內容的 Extra。使用該 Intent 調用 startActivity() 時,用戶可以選取共享內容所使用的應用。
警告:用戶可能沒有任何應用處理您發送到 startActivity() 的隱式 Intent。如果出現這種情況,則調用將會失敗,且應用會崩潰。要驗證 Activity 是否會接收 Intent,請對 Intent 對象調用 resolveActivity()。如果結果為非空,則至少有一個應用能夠處理該 Intent,且可以安全調用 startActivity()。如果結果為空,則不應使用該 Intent。如有可能,您應禁用發出該 Intent 的功能。
// Create the text message with a string
Intent sendIntent = new Intent();
sendIntent.setAction(Intent.ACTION_SEND);
sendIntent.putExtra(Intent.EXTRA_TEXT, textMessage);
sendIntent.setType("text/plain");
// Verify that the intent will resolve to an activity
if (sendIntent.resolveActivity(getPackageManager()) != null) {
startActivity(sendIntent);
}
注意:在這種情況下,系統並沒有使用 URI,但已聲明 Intent 的數據類型,用於指定 Extra 攜帶的內容。
調用 startActivity() 時,系統將檢查已安裝的所有應用,確定哪些應用能夠處理這種 Intent(即:含 ACTION_SEND 操作並攜帶“text/plain”數據的 Intent )。如果只有一個應用能夠處理,則該應用將立即打開並提供給 Intent。如果多個 Activity 接受 Intent,則系統將顯示一個對話框,使用戶能夠選取要使用的應用。
3.強制使用應用選擇器
如果有多個應用響應隱式 Intent,則用戶可以選擇要使用的應用,並將其設置為該操作的默認選項。 如果用戶可能希望今後一直使用相同的應用執行某項操作(例如,打開網頁時,用戶往往傾向於僅使用一種 Web 浏覽器),則這一點十分有用。
但是,如果多個應用可以響應 Intent,且用戶可能希望每次使用不同的應用,則應采用顯式方式顯示選擇器對話框。選擇器對話框要求用戶選擇每次操作要使用的應用(用戶無法為該操作選擇默認應用)。例如,當應用使用 ACTION_SEND 操作執行“共享”時,用戶根據目前的狀況可能需要使用另一不同的應用,因此應當始終使用選擇器對話框,如圖 2 中所示。
圖 2. 選擇器對話框。
要顯示選擇器,請使用 createChooser() 創建 Intent,並將其傳遞給 startActivity()。例如:
Intent sendIntent = new Intent(Intent.ACTION_SEND);
...
// Always use string resources for UI text.
// This says something like "Share this photo with"
String title = getResources().getString(R.string.chooser_title);
// Create intent to show the chooser dialog
Intent chooser = Intent.createChooser(sendIntent, title);
// Verify the original intent will resolve to at least one activity
if (sendIntent.resolveActivity(getPackageManager()) != null) {
startActivity(chooser);
}
這將顯示一個對話框,其中包含響應傳遞給 createChooser() 方法的 Intent 的應用列表,並使用提供的文本作為對話框標題。
接收隱式 Intent
要公布應用可以接收哪些隱式 Intent,請在清單文件中使用 intent-filter 元素為每個應用組件聲明一個或多個 Intent 過濾器。每個 Intent 過濾器均根據 Intent 的操作、數據和類別指定自身接受的 Intent 類型。僅當隱式 Intent 可以通過 Intent 過濾器之一傳遞時,系統才會將該 Intent 傳遞給應用組件。
注意:顯式 Intent 始終會傳遞給其目標,無論組件聲明的 Intent 過濾器如何均是如此。
應用組件應當為自身可執行的每個獨特作業聲明單獨的過濾器。例如,圖像庫應用中的一個 Activity 可能會有兩個過濾器,分別用於查看圖像和編輯圖像。當 Activity 啟動時,它將檢查 Intent並根據 Intent 中的信息決定具體的行為(例如,是否顯示編輯器件)。
每個 Intent 過濾器均由應用清單文件中的 intent-filter 元素定義,並嵌套在相應的應用組件(例如,activity元素)中。在 intent-filter內部,您可以使用以下三個元素中的一個或多個指定要接受的 Intent 類型:
(1)action:在 name 屬性中,聲明接受的 Intent 操作。該值必須是操作的文本字符串值,而不是類常量。
(2)data:使用一個或多個指定 數據 URI(scheme、host、port、path 等)各個方面和 MIME 類型的屬性,聲明接受的數據類型。
(3)category:在 name 屬性中,聲明接受的 Intent 類別。該值必須是操作的文本字符串值,而不是類常量。
注意:為了接收隱式 Intent,必須將 CATEGORY_DEFAULT 類別包括在 Intent 過濾器中。方法 startActivity() 和startActivityForResult() 將按照已申明 CATEGORY_DEFAULT 類別的方式處理所有 Intent。如果未在 Intent 過濾器中聲明此類別,則隱式 Intent 不會解析為您的 Activity。
例如,以下是一個使用 Intent 過濾器進行的 Activity 聲明,當數據類型為文本時,系統將接收 ACTION_SEND Intent :
您可以創建一個包括多個 action、data或 &category實例的過濾器。創建時,僅需確定組件能夠處理這些過濾器元素的任何及所有組合即可。
如需僅以操作、數據和類別類型的特定組合來處理多種 Intent,則需創建多個 Intent 過濾器。
系統通過將 Intent 與所有這三個元素進行比較,根據過濾器測試隱式 Intent。隱式 Intent 若要傳遞給組件,必須通過所有這三項測試。如果 Intent 甚至無法匹配其中任何一項測試,則 Android 系統不會將其傳遞給組件。但是,由於一個組件可能有多個 Intent 過濾器,因此未能通過某一組件過濾器的 Intent 可能會通過另一過濾器。
警告:為了避免無意中運行不同應用的 Service,請始終使用顯式 Intent 啟動您自己的服務,且不必為該服務聲明 Intent 過濾器。
注意:對於所有 Activity,您必須在清單文件中聲明 Intent 過濾器。但是,廣播接收器的過濾器可以通過調用 registerReceiver() 動態注冊。稍後,您可以使用 unregisterReceiver() 注銷該接收器。這樣一來,應用便可僅在應用運行時的某一指定時間段內偵聽特定的廣播。
限制對組件的訪問:
使用 Intent 過濾器時,無法安全地防止其他應用啟動組件。盡管 Intent 過濾器將組件限制為僅響應特定類型的隱式 Intent,但如果開發者確定您的組件名稱,則其他應用有可能通過使用顯式 Intent啟動您的應用組件。如果必須確保只有您自己的應用才能啟動您的某一組件,請針對該組件將 exported 屬性設置為 "false"。
過濾器示例:
為了更好地了解一些 Intent 過濾器的行為,我們一起來看看從社交共享應用的清單文件中截取的以下片段。
第一個 Activity MainActivity 是應用的主要入口點。當用戶最初使用啟動器圖標啟動應用時,該 Activity 將打開:
(1)ACTION_MAIN 操作指示這是主要入口點,且不要求輸入任何 Intent 數據。
(2)CATEGORY_LAUNCHER 類別指示此 Activity 的圖標應放入系統的應用啟動器。如果 activity 元素未使用 icon 指定圖標,則系統將使用application元素中的圖標。
這兩個元素必須配對使用,Activity 才會顯示在應用啟動器中。
第二個 Activity ShareActivity 旨在便於共享文本和媒體內容。盡管用戶可以通過從 MainActivity 導航進入此 Activity,但也可以從發出隱式 Intent(與兩個 Intent 過濾器之一匹配)的另一應用中直接進入 ShareActivity。
注意:MIME 類型 application/vnd.google.panorama360+jpg 是一個指定全景照片的特殊 數據類型,您可以使用 Google 全景 API 對其進行處理。
使用PendingIntent
PendingIntent 對象是 Intent 對象的包裝器。PendingIntent 的主要目的是授權外部應用使用包含的 Intent,就像是它從您應用本身的進程中執行的一樣。
PendingIntent主要用例包括:
(1)聲明用戶使用您的通知執行操作時所要執行的 Intent(Android 系統的 NotificationManager 執行 Intent)。
(2)聲明用戶使用您的 應用小工具執行操作時要執行的 Intent(主屏幕應用執行 Intent)。
(3)聲明未來某一特定時間要執行的 Intent(Android 系統的 AlarmManager 執行 Intent)。
由於每個 Intent 對象均設計為由特定類型的應用組件進行處理(Activity、Service 或 BroadcastReceiver),因此還必須基於相同的考慮因素創建 PendingIntent。使用待定 Intent 時,應用不會使用調用(如 startActivity())執行該 Intent。相反,通過調用相應的創建器方法創建 PendingIntent 時,您必須聲明所需的組件類型:
(1)PendingIntent.getActivity(),適用於啟動 Activity 的 Intent。
(2)PendingIntent.getService(),適用於啟動 Service 的 Intent。
(3)PendingIntent.getBroadcast(),適用於啟動 BroadcastReceiver 的 Intent。
除非您的應用正在從其他應用中接收PendingIntent,否則上述用於創建 PendingIntent 的方法可能是您所需的唯一 PendingIntent 方法。
每種方法均會提取當前的應用 Context、您要包裝的 Intent 以及一個或多個指定應如何使用該 Intent 的標志(例如,是否可以多次使用該 Intent)。
Intent 解析
當系統收到隱式 Intent 以啟動 Activity 時,它根據以下三個方面將該 Intent 與 Intent 過濾器進行比較,搜索該 Intent 的最佳Activity:
(1)Intent 操作
(2)Intent 數據(URI 和數據類型)
(3)Intent 類別
下文根據如何在應用的清單文件中聲明 Intent 過濾器,描述 Intent 如何與相應的組件匹配。
1、操作測試
要指定接受的 Intent 操作, Intent 過濾器既可以不聲明任何action元素,也可以聲明多個此類元素。例如:
...
要通過此過濾器,您在 Intent 中指定的操作必須與過濾器中列出的某一操作匹配。
如果該過濾器未列出任何操作,則 Intent 沒有任何匹配項,因此所有 Intent 均無法通過測試。但是,如果 Intent 未指定操作,則會通過測試(只要過濾器至少包含一個操作)。
2、類別測試
要指定接受的 Intent 類別, Intent 過濾器既可以不聲明任何category元素,也可以聲明多個此類元素。例如:
...
若要 Intent 通過類別測試,則Intent 中的每個類別均必須與過濾器中的類別匹配。反之則未必然,Intent 過濾器聲明的類別可以超出 Intent 中指定的數量,且 Intent 仍會通過測試。因此,不含類別的 Intent 應當始終會通過此測試,無論過濾器中聲明何種類別均是如此。
注意:Android 會自動將 CATEGORY_DEFAULT 類別應用於傳遞給 startActivity() 和 startActivityForResult() 的所有隱式 Intent。因此,如需 Activity 接收隱式 Intent,則必須將 "android.intent.category.DEFAULT" 的類別包括在其 Intent 過濾器中(如上文的 intent-filter示例所示)。
3、數據測試
要指定接受的 Intent 數據,Intent 過濾器既可以不聲明任何data元素,也可以聲明多個此類元素。例如:
...
每個
元素均可指定 URI 結構和數據類型(MIME 介質類型)。URI 的每個部分均包含單獨的scheme、host、port 和 path 屬性:scheme://host:port/path
例如:content://com.example.project:200/folder/subfolder/etc,在此 URI 中,架構是 content,主機是 com.example.project,端口是 200,路徑是 folder/subfolder/etc。
在data元素中,上述每個屬性均為可選,但存在線性依賴關系:
(1)如果未指定架構,則會忽略主機。
(2)如果未指定主機,則會忽略端口。
(3)如果未指定架構和主機,則會忽略路徑。
將 Intent 中的 URI 與過濾器中的 URI 規范進行比較時,它僅與過濾器中包含的部分 URI 進行比較。例如:
(1)如果過濾器僅指定架構,則具有該架構的所有 URI 均與該過濾器匹配。
(2)如果過濾器指定架構和權限、但未指定路徑,則具有相同架構和權限的所有 URI 都會通過過濾器,無論其路徑如何均是如此。
(3)如果過濾器指定架構、權限和路徑,則僅具有相同架構、權限和路徑 的 URI 才會通過過濾器。
注意:路徑規范可以包含星號通配符 (*),因此僅需部分匹配路徑名即可。
數據測試會將 Intent 中的 URI 和 MIME 類型與過濾器中指定的 URI 和 MIME 類型進行比較。規則如下:
a.僅當過濾器未指定任何 URI 或 MIME 類型時,不含 URI 和 MIME 類型的 Intent 才會通過測試。
b.對於包含 URI、但不含 MIME 類型(既未顯式聲明,也無法通過 URI 推斷得出)的 Intent,僅當其 URI 與過濾器的 URI 格式匹配、且過濾器同樣未指定 MIME 類型時,才會通過測試。
c.僅當過濾器列出相同的 MIME 類型且未指定 URI 格式時,包含 MIME 類型、但不含 URI 的 Intent 才會通過測試。
d.僅當 MIME 類型與過濾器中列出的類型匹配時,包含 URI 和 MIME 類型(通過顯式聲明,或可以通過 URI 推斷得出)的 Intent 才會通過測試的 MIME 類型部分。如果 Intent 的 URI 與過濾器中的 URI 匹配,或者如果 Intent 具有 content: 或 file: URI 且過濾器未指定 URI,則 Intent 會通過測試的 URI 部分。換而言之,如果過濾器僅列出 MIME 類型,
則假定組件支持 content: 和 file: 數據。
最後一條規則,即規則 (d),反映了期望組件能夠從文件中或內容提供商處獲得本地數據。因此,其過濾器可以僅列出數據類型,而不必顯式命名 content: 和 file: 架構。這是一個典型的案例。例如,下文中的data元素向 Android 指出,組件可從內容提供商處獲得並顯示圖像數據:
...
由於大部分可用數據均由內容提供商分發,因此指定數據類型(而非 URI)的過濾器也許最為常見。
另一常見的配置是具有架構和數據類型的過濾器。例如,下文中的 data元素向 Android 指出,組件可從網絡中檢索視頻數據以執行操作:
...
4、Intent 匹配
通過 Intent 過濾器匹配 Intent,這不僅有助於發現要激活的目標組件,還有助於發現設備上組件集的相關信息。例如,主頁應用通過使用指定 ACTION_MAIN 操作和 CATEGORY_LAUNCHER 類別的 Intent 過濾器查找所有 Activity,以此填充應用啟動器。
您的應用可以采用類似的方式使用 Intent 匹配。PackageManager 提供了一整套 query...() 方法來返回所有能夠接受特定 Intent 的組件。此外,它還提供了一系列類似的 resolve...() 方法來確定響應 Intent 的最佳組件。例如,queryIntentActivities() 將返回能夠執行那些作為參數傳遞的 Intent 的所有 Activity 列表,而 queryIntentServices() 則可返回類似的服務列表。這兩種方法均不會激活組件,而只是列出能夠響應的組件。對於廣播接收器,有一種類似的方法: queryBroadcastReceivers()。