Android基礎------Intent的使用

Intenet的使用


1.Intent的介紹和作用

(1) 什麼是Intent

Intent的中文意思是“意圖,意向”,在Android中提供了Intent機制來協助應用間的交互與通訊,Intent負責對應用中一次操作的動 作、動作涉及數據、附加數據進行描述,Android則根據此Intent的描述,負責找到對應的組件,將 Intent傳遞給調用的組件,並完成組件的調用

可以將Intent理解爲不同組件之間通信的“媒介”專門提供組件互相調用的相關信息。

(2) Intent的作用

Intent 是一個將要執行的動作的抽象的描述,一般來說是作爲參數來使用,由Intent來協助完成android各個組件之間的通訊。比如說調用 startActivity()來啓動一個activity,或者由broadcaseIntent()來傳遞給所有感興趣的 BroadcaseReceiver, 再或者由startService()/bindservice()來啓動一個後臺的service.所以可以看出來,intent主要是用來啓動其他的 activity 或者service,所以可以將intent理解成activity之間的粘合劑。

activity、service和broadcast receiver之間是通過Intent進行通信的,而另外一個組件Content Provider本身就是一種通信機制,不需要通過Intent。我們來看下面這個圖就知道了:

這裏寫圖片描述


2.Intent的分類

Intent大致可以分爲兩種類型:顯式Intent和隱式Intent。

顯式Intent:

如果在我們定義的Intent中明確包含了要啓動的組件的完整類名(包名及類名),即Intent的“意圖”非常明顯,那麼這個Intent就是顯式的。使用顯式Intent最典型的情形是在你自己的程序中啓動一個組件,因爲你自己肯定知道自己的要啓動的組件的類名。比如,爲了響應用戶操作通過顯式的Intent在你的程序中啓動一個Activity或啓動一個Service下載文件。

隱式Intent:

沒有明確指定組件名要啓動哪一個活動,而是系統根據動作(action)、類別(category)、數據(Uri)和數據類型來找到最合適的組件。一般來說我們需要在裏設置category、action和data等信息。需要注意的是,爲了確保App的安全性,我們應該總是使用顯式Intent去啓動Service並且不要爲該Service設置任何的Intent Filter。通過隱式的Intent啓動Service是有風險的,因爲你不確定最終哪個App中的哪個Service會啓動起來以響應你的隱式Intent,更悲催的是,由於Service沒有UI的在後臺運行,所以用戶也不知道哪個Service運行了

Intent Filter,即Intent過濾器,一個組件可以包含0個或多個Intent Filter。Intent Filter是寫在App的manifest文件中的,其通過設置action或uri數據類型等指明瞭組件能夠處理接收的Intent的類型。對於Android的主活動都有下面幾行代碼來表明啓動活動:


<intent-filter>
      <action android:name="android.intent.action.MAIN" />
      <category android:name="android.intent.category.LAUNCHER" />
</intent-filter>

這裏寫圖片描述


3.Intent的相關屬性

component(組件):目的組件
action(動作):用來表現意圖的行動
category(類別):用來表現動作的類別
data(數據):表示與動作要操縱的數據
type(數據類型):對於data範例的描寫
extras(擴展信息):擴展信息
Flags(標誌位):期望這個意圖的運行模式

(1)component

Component屬性明確指定Intent的目標組件的類名稱。(屬於直接Intent)
如果 component這個屬性有指定的話,將直接使用它指定的組件。指定了這個屬性以後,Intent的其它所有屬性都是可選的。

例如,啓動第二個Activity時,我們可以這樣來寫:


 button1.setOnClickListener(new OnClickListener() {            
              @Override
              public void onClick(View v) {
                  //創建一個意圖對象
                  Intent intent = new Intent();
                  //創建組件,通過組件來響應
                  ComponentName component = new ComponentName(MainActivity.this, SecondActivity.class);
                  intent.setComponent(component);                
                  startActivity(intent);                
             }
         });


======================================================================
// 寫簡單一點
                 Intent intent = new Intent();
                 //setClass函數的第一個參數是一個Context對象
                 //Context是一個類,Activity是Context類的子類,也就是說,所有的Activity對象,都可以向上轉型爲Context對象
                 //setClass函數的第二個參數是一個Class對象,在當前場景下,應該傳入需要被啓動的Activity類的class對象
                 intent.setClass(MainActivity.this, SecondActivity.class);
                 startActivity(intent);   
======================================================================
// 再寫簡單一點 
                 Intent intent = new Intent(MainActivity.this,SecondActivity.class);
                 startActivity(intent);
(2)action

當日常生活中,描述一個意願或願望的時候,總是有一個動詞在其中。比如:我想“做”三個俯臥撐;我要“寫” 一封情書,等等。在Intent中,Action就是描述做、寫等動作的,當你指明瞭一個Action,執行者就會依照這個動作的指示,接受相關輸入,表現對應行爲,產生符合的輸出。在Intent類中,定義了一批量的動作,比如ACTION_VIEW,ACTION_PICK等, 基本涵蓋了常用動作。加的動作越多,越精確。

Action 是一個用戶定義的字符串,用於描述一個 Android 應用程序組件,一個 Intent Filter 可以包含多個 Action。在 AndroidManifest.xml 的Activity 定義時,可以在其 節點指定一個 Action列表用於標識 Activity 所能接受的“動作”。

<activity android:name=".TargetActivity">  
    <intent-filter>            
         <action android:name="com.scott.intent.action.TARGET"/>  
         <category android:name="android.intent.category.DEFAULT"/>  
    </intent-filter>  
 </activity>  

TargetActivity在其中聲明瞭,即目標action,如果我們需要做一個跳轉的動作,就需要在Intent中指定目標的action,如下:

public void gotoTargetActivity(View view) {  
     Intent intent = new Intent("com.scott.intent.action.TARGET");  
     startActivity(intent);  
 }  
(3)category

其中標籤指明瞭當前活動可以響應的action。標籤則附加了一些信息,更精確地指明瞭當前活動能響應的Intent還可能帶有的category。只有和同時匹配上Intent中指定的action和category時,活動才能響應該Intent

<category android:name="android.intent.category.LAUNCHER" />  

這裏寫圖片描述

下面我們來一段代碼進行調試以下

  • 1.打開清單文件AndroidManifest.xml
 <activity> 
             android:name=".SecondActivity">
             <intent-filter>
                  <action android:name="com.example.smyh006intent01.MY_ACTION"/>
5                  <category android:name="android.intent.category.DEFAULT" />
6             </intent-filter>            
7         </activity>
  • 2.修改MainActivity.java
 button1.setOnClickListener(new OnClickListener() {            
              @Override
              public void onClick(View v) {
                  //啓動另一個Activity,(通過action屬性進行查找)
                  Intent intent = new Intent();
                  //設置動作(實際action屬性就是一個字符串標記而已)
                  intent.setAction("com.example.smyh006intent01.MY_ACTION"); //方法:Intent android.content.Intent.setAction(String action)
                  startActivity(intent);        
              }
         });
(4)data(數據):表示與動作要操縱的數據

Data屬性是Android要訪問的數據,和action和Category聲明方式相同,也是在中。
多個組件匹配成功顯示優先級高的; 相同顯示列表。
Data是用一個uri對象來表示的,uri代表數據的地址,屬於一種標識符。通常情況下,我們使用action+data屬性的組合來描述一個意圖:做什麼

  • 使用隱式Intent,我們不僅可以啓動自己程序內的活動,還可以啓動其他程序的活動,這使得Android多個應用程序之間的功能共享成爲了可能。比如應用程序中需要展示一個網頁,沒有必要自己去實現一個瀏覽器(事實上也不太可能),而是只需要條用系統的瀏覽器來打開這個網頁就行了。
    案例:實現打開指定網頁
button1.setOnClickListener(new OnClickListener() {            
              @Override
              public void onClick(View v) {
                  Intent intent = new Intent();
                  intent.setAction(Intent.ACTION_VIEW);
                  Uri data = Uri.parse("http://www.baidu.com");
                  intent.setData(data);                
                  startActivity(intent);        
              }
         });
(5)type:對於data範例的描寫

如果Intent對象中既包含Uri又包含Type,那麼,在<intent-filter>中也必須二者都包含才能通過測試。
Type屬性用於明確指定Data屬性的數據類型或MIME類型,但是通常來說,當Intent不指定Data屬性時,Type屬性纔會起作用,否則Android系統將會根據Data屬性值來分析數據的類型,所以無需指定Type屬性。
data和type屬性一般只需要一個,通過setData方法會把type屬性設置爲null,相反設置setType方法會把data設置爲null,如果想要兩個屬性同時設置,要使用Intent.setDataAndType()方法

  • data+type屬性的使用 【實例】:播放指定路徑的mp3文件。
button.setOnClickListener(new OnClickListener(){
              @Override
              public void onClick(View v) {
                  Intent intent = new Intent();
                  intent.setAction(Intent.ACTION_VIEW);
                  Uri data = Uri.parse("file:///storage/sdcard0/平凡之路.mp3");
                  //設置data+type屬性
                  intent.setDataAndType(data, "audio/mp3"); //方法:Intent android.content.Intent.setDataAndType(Uri data, String type)
                  startActivity(intent);                
             }            
         });

(6)extras(擴展信息):擴展信息

是其它所有附加信息的集合。使用extras可以爲組件提供擴展信息,比如,如果要執行“發送電子郵件”這個動作,可以將電子郵件的標題、正文等保存在extras裏,傳給電子郵件發送組件。

  • 存入
public void gotoTargetActivity(View view) {  
     Intent intent = new Intent("com.scott.intent.action.TARGET");  
     Bundle bundle = new Bundle();  
     bundle.putInt("id", 0);  
     bundle.putString("name", "scott");  
     intent.putExtras(bundle);  
     startActivity(intent);  
     }  
  • 取出
Bundle bundle = intent.getExtras();  
     int id = bundle.getInt("id");  
     String name = bundle.getString("name");  
(7)Flags(標誌位):期望這個意圖的運行模式

一個程序啓動後系統會爲這個程序分配一個task供其使用,另外同一個task裏面可以擁有不同應用程序的activity。那麼,同一個程序能不能擁有多個task?這就涉及到加載activity的啓動模式,這個需要單獨講一下。

注:android中一組邏輯上在一起的activity被叫做task,自己認爲可以理解成一個activity堆棧。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章