亚洲激情专区-91九色丨porny丨老师-久久久久久久女国产乱让韩-国产精品午夜小视频观看

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Android中的Intent機制有什么用

發布時間:2021-08-03 09:40:57 來源:億速云 閱讀:121 作者:chen 欄目:移動開發

這篇文章主要介紹“Android中的Intent機制有什么用”,在日常操作中,相信很多人在Android中的Intent機制有什么用問題上存在疑惑,小編查閱了各式資料,整理出簡單好用的操作方法,希望對大家解答”Android中的Intent機制有什么用”的疑惑有所幫助!接下來,請跟著小編一起來學習吧!

對于大型軟件開發經驗較少的程序員來說,這可能是一個不太容易理解的抽象概念,因為它與我們平常使用的簡單函數調用,或者通過庫調用接口的方式不太一樣。 在 Intent 的使用中你看不到直接的函數調用,相對函數調用來說,Intent 是更為抽象的概念,利用 Intent  所實現的軟件復用的粒度是Activity/Service ,比函數復用更高一些,另外耦合也更為松散。

Android 中與Intent 相關的還有  Action/Category 及 Intent Filter 等,另外還有用于廣播的 Intent  ,這些元素摻雜在一起,導致初學者不太容易迅速掌握 Intent 的用法。在講解這些名詞之前,我們先來從下面的例子中感受一下 Intent  的一些基本用法,看看它能做些什么,之后再來思考這種機制背后的意義。

理解 Intent 的關鍵之一是理解清楚Intent 的兩種基本用法:一種是顯式的 Intent ,即在構造 Intent  對象時就指定接收者,這種方式與普通的函數調用類似, 只是復用的粒度有所差別;另一種是隱式的 Intent ,即Intent 的發送者在構造  Intent 對象時,并不知道也不關心接收者是誰,這種方式與函數調用差別比較大,有利于降低發送者和接收 者之間的耦合。另外 Intent  除了發送外,還可用于廣播。

下面的一小節我們來看看顯式 Intent 的用法。

顯式的Intent(Explicit Intent)

同一個應用程序中的Activity切換

通常一個應用程序中需要多個UI 屏幕,也就需要多個Activity 類,并且在這些 Activity 之間進行切換,這種切換就是通過 Intent 機制來實現的。

在同一個應用程序中切換 Activity時,我們通常都知道要啟動的 Activity 具體是哪一個,因此常用顯式的  Intent 來實現。下面的例子用來實現一個非常簡單的應用程序 SimpleIntentTest ,它包括兩個UI 屏幕也就是兩個  Activity——SimpleIntentTest類和 TestActivity 類, SimpleIntentTest類有一個按鈕用來啟動  TestActivity。

程序的代碼非常簡單, SimpleIntentTest類的源代碼如下:

Java代碼

  1. package  com.tope.samples.intent.simple;   

  2.   

  3. import  android.app.Activity;   

  4. import  android.content.Intent;   

  5. import  android.os.Bundle;   

  6. import  android.view.View;   

  7. import  android.widget.Button;   

  8.   

  9. public   class  SimpleIntentTest  extends  Activity  implements  View.OnClickListener{   

  10.      /**   Called   when   the   activity   is   first   created.   */  

  11.      @Override  

  12.      public   void  onCreate(Bundle savedInstanceState) {   

  13.          super .onCreate(savedInstanceState);   

  14.         setContentView(R.layout. main );   

  15.         Button startBtn = (Button)findViewById(R.id. start_activity );   

  16.         startBtn.setOnClickListener( this );   

  17.     }   

  18.     

  19.      public   void  onClick(View v) {   

  20.          switch  (v.getId()) {   

  21.          case  R.id. start_activity :   

  22.             Intent intent =  new  Intent( this , TestActivity. class );   

  23.             startActivity(intent);   

  24.              break ;   

  25.          default :   

  26.              break ;   

  27.          }   

  28.     }      

  29. }  

上面的代碼中,主要是為“Start activity” 按鈕添加了 OnClickListener, 使得按鈕被點擊時執行  onClick() 方法, onClick() 方法中則利用了 Intent 機制,來啟動 TestActivity,關鍵的代碼是下面這兩行:

Intent intent = new Intent( this , TestActivity. class );

startActivity(intent);

這里定義 Intent 對象時所用到的是 Intent 的構造函數之一:

Intent ( Context packageContext, Class <?> cls)

兩個參數分別指定 Context 和 Class ,由于將Class 設置為  TestActivity.class,這樣便顯式的指定了TestActivity 類作為該Intent  的接收者,通過后面的startActivity() 方法便可啟動 TestActivity 。

TestActivity 的代碼更為簡單(定義 TestActivity類需要新建 TestActivity.java  文件,如果你是一個初學者,你需要學會如何在 Eclipse 或其他開發環境下添加一個新的類,這里不作詳述,請參考其他文檔),如下所示:

Java代碼

  1. package  com.tope.samples.intent.simple;   

  2.   

  3. import  android.app.Activity;   

  4. import  android.os.Bundle;   

  5.   

  6. public   class  TestActivity  extends  Activity {   

  7.      /**   Called   when   the   activity   is   first   created.   */  

  8.      @Override  

  9.      public   void  onCreate(Bundle savedInstanceState) {   

  10.          super .onCreate(savedInstanceState);   

  11.         setContentView(R.layout. test_activity );   

  12.     }   

  13. }   

可見 TestActivity僅僅是調用 setContentView 來顯示 test_activity.xml 中的內容而已。對于 test_activity.xml及本例中所用到其他 xml 文件這里不作多余說明。

如果我們僅僅是做上面的一些 工作,還不能達到利用 SimpleIntentTest 啟動  TestActivity的目的。事實上,這樣做會出現下面的 Exception ,導致程序退出。以下是利用 logcat 工具記錄的log  信息(省略了后半部分):

I/ActivityManager(  569): Displayed activity com.tope.samples/.SimpleIntentTest: 3018 ms
I/ActivityManager(  569): Starting activity: Intent { comp={com.tope.samples/com.tope.samples.TestActivity} }
D/AndroidRuntime(  932): Shutting down VM
W/dalvikvm(  932): threadid=3: thread exiting with uncaught exception (group=0x4000fe70)
E/AndroidRuntime(  932): Uncaught handler: thread main exiting due to uncaught exception
E/AndroidRuntime(  932):  android.content.ActivityNotFoundException: Unable to find explicit activity class
 {com.tope.samples/com.tope.samples.TestActivity}; have you declared this activity in your AndroidManifest.xml?
E/AndroidRuntime(  932):     at android.app.Instrumentation.checkStartActivityResult(Instrumentation.java:1480)
E/AndroidRuntime(  932):     at android.app.Instrumentation.execStartActivity(Instrumentation.java:1454)
E/AndroidRuntime(  932):     at android.app.Activity.startActivityForResult(Activity.java:2656)
E/AndroidRuntime(  932):     at android.app.Activity.startActivity(Activity.java:2700)
E/AndroidRuntime(  932):     at com.tope.samples.SimpleIntentTest.onClick(SimpleIntentTest.java:24)
&hellip;

從這些log 中我們可以看到點擊按鈕后 startActivity  的調用過程,主要的原因是:“android.content.ActivityNotFoundException: Unable to find  explicit activity class  {com.tope.samples/com.tope.samples.TestActivity}; have you declared this  activity in your AndroidManifest.xml?”

從這些log 我們可以看到原因是找不到 TestActivity這個 Activity ,并且 log  中還給出了提示:你是否在AndroidManifest.xml 中聲明了這個 Activity?解決問題的方法也就是按照提示在  AndroidManifest.xml 中增加TestActivity 的聲明,如下所示:

XML/HTML代碼

  1. <? xml   version = "1.0"   encoding = "utf-8" ?>  

  2. < manifest   xmlns:android = "http://schemas.android.com/apk/res/android"  

  3.        package = "com.tope.samples"  

  4.        android:versionCode = "1"  

  5.        android:versionName = "1.0" >  

  6.      < application   android:icon = "@drawable/icon"   android:label ="@string/app_name" >  

  7.          < activity   android:name = ".SimpleIntentTest"  

  8.                    android:label = "@string/app_name" >  

  9.              < intent-filter >  

  10.                  < action   android:name = "android.intent.action.MAIN"  />  

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

  12.              </ intent-filter >  

  13.          </ activity >  

  14.           < activity   android:name = ".TestActivity" />  

  15.      </ application >  

  16.      < uses-sdk   android:minSdkVersion = "3"   />  

  17. </ manifest >    

完成這個修改后再重新運行該程序,就一切都正常了。

從 AndroidManifest.xml修改的過程我們可以體會到, Intent  機制即使在程序內部且顯式指定接收者,也還是需要在 AndroidManifest.xml 中聲明  TestActivity。這個過程并不像一個簡單的函數調用,顯式的 Intent 也同樣經過了Android  應用程序框架所提供的支持,從滿足條件的 Activity 中進行選擇,如果不在 AndroidManifest.xml中進行聲明,則  Android 應用程序框架找不到所需要的 Activity。

請讀者通過我們的示例來逐步理解 AndroidManifest.xml在這個過程中所扮演的角色,這樣有利于理解 Intent的作用 ,及后面的 Intent Filter。當然,這個例子僅僅是開始,且看下文分解 。

不同應用程序之間的Activity切換

上面的例子我們所做的是在同 一應用程序中進行 Activity  的切換,那么在不同的應用程序中,是否也能這么做呢,答案是肯定的,不過對應的代碼要稍作修改。本例中我們需要兩個應用程序,可利用上例中  的SimpleIntentTest作為其中之一,另外還需要寫一個新的程序,來調用 SimpleIntentTest 應用程序中的  TestActivity。

我們新建程序 CrossIntentTest(注意不是新建一個類,如果是 Eclipse 環境,選擇  File->New->Project新建工程),其中只有一個 Activity ,其源代碼與  SimpleIntentTest.java 類似 :

Java代碼

  1. package  com.tope.samples.intent.cross;   

  2.   

  3. import  android.app.Activity;   

  4. import  android.content.Intent;   

  5. import  android.os.Bundle;   

  6. import  android.view.View;   

  7. import  android.widget.Button;   

  8.   

  9. public   class  CrossIntentTest  extends  Activity    

  10.      implements  View.OnClickListener{   

  11.      /**   Called   when   the   activity   is   first   created.   */  

  12.      @Override  

  13.      public   void  onCreate(Bundle savedInstanceState) {   

  14.          super .onCreate(savedInstanceState);   

  15.         setContentView(R.layout. main );   

  16.         Button startBtn = (Button)findViewById(R.id. start_activity );   

  17.         startBtn.setOnClickListener( this );   

  18.     }   

  19.     

  20.      public   void  onClick(View v) {   

  21.          switch  (v.getId()) {   

  22.          case  R.id. start_activity :   

  23.             Intent intent =  new  Intent();   

  24.             intent.setClassName( "com.tope.samples.intent.simple" ,    

  25.                      "com.tope.samples.intent.simple.TestActivity" );   

  26.             startActivity(intent);   

  27.              break ;   

  28.          default :   

  29.              break ;   

  30.         }   

  31.     }      

  32. }  

注意比較它與 SimpleIntentTest的不同之處主要在于初始化 Intent 對象的過程:

Java代碼

  1. Intent intent =  new  Intent();   

  2. intent.setClassName( "com.tope.samples.intent.simple" ,    

  3.                      "com.tope.samples.intent.simple.TestActivity" );   

  4. startActivity(intent);  

這里采用了 Intent 最簡單的不帶參數的構造函數 , 然后通過 setClassName()  函數來指定要啟動哪個包中的哪個 Activity, 而不是像上例中的通過 Intent ( Context packageContext,  Class <?> cls) 這個構造函數來初始化Intent 對象,這是因為,要啟動的 TestActivity 與  CrossIntentTest 不在同一個包中 , 要指定 Class 參數比較麻煩 , 所以通常啟動不同程序的 Activity  時便采用上面的 setClassName() 的方式。除此之外,你也可以利用Android 提供的類似的 setComponent()  方法,具體使用方法請參考 Android SDK的文檔。

另外我們還需要修改SimpleIntentTest 程序中的 AndroidManifest.xml 文件,為 TestActivity 的聲明添加Intent Filter ,即將原來的

XML/HTML代碼

  1. <activity android:name = ".TestActivity" />  

修改為:

XML/HTML代碼

  1. <activity   android:name = ".TestActivity" >  

  2.      <intent-filter>  

  3.          <action   android:name = "android.intent.action.DEFAULT" />  

  4.      </intent-filter>  

  5. </activity >   

對于不同應用之間的 Activity 的切換,這里需要在 Intent Filter中 設置至少一個  Action,否則其他的應用將沒有權限調用這個 Activity 。這里我們開始接觸 Intent Filter和 Action  這些概念了,讀者應該可以感覺到,設置Intent Filter 和 Action 主要的目的,是為了讓其他需要調用這個 Activity  的程序能夠順利的調用它。除了Action之外, Intent Filter 還可以設置 Category 、 Data等,用來更加精確的匹配  Intent 與 Activity。

隱式Intent(Implicit Intent)

如果 Intent 機制僅僅提供上面的顯式 Intent 用法的話,這種相對復雜的機制似乎意義并不是很大。確實,Intent  機制更重要的作用在于下面這種隱式的 Intent ,即 Intent 的發送者不指定接收者,很可能不知道也不關心接收者是誰,而由  Android 框架去尋找最匹配的接收者。

最簡單的隱式 Intent

我們先從最簡單的例子開始。 下面的 ImplicitIntentTest 程序用來啟動 Android 自帶的打電話功能的 Dialer 程序。

ImplicitIntentTest 程序只包含一個java 源文件 ImplicitIntentTest.java,代碼如下所示:

Java代碼

  1. package  com.tope.samples.intent.implicit;   

  2.   

  3. import  android.app.Activity;   

  4. import  android.content.Intent;   

  5. import  android.os.Bundle;   

  6. import  android.view.View;   

  7. import  android.widget.Button;   

  8.   

  9. public   class  ImplicitIntentTest  extends  Activity        

  10.      implements  View.OnClickListener{   

  11.      /**   Called   when   the   activity   is   first   created.   */  

  12.      @Override  

  13.      public   void  onCreate(Bundle savedInstanceState) {   

  14.          super .onCreate(savedInstanceState);   

  15.         setContentView(R.layout. main );   

  16.         Button startBtn = (Button)findViewById(R.id. dial );   

  17.         startBtn.setOnClickListener( this );   

  18.     }   

  19.     

  20.      public   void  onClick(View v) {   

  21.          switch  (v.getId()) {   

  22.          case  R.id. dial :   

  23.             Intent intent =  new  Intent(Intent. ACTION_DIAL );   

  24.             startActivity(intent);   

  25.              break ;   

  26.          default :   

  27.              break ;   

  28.         }   

  29.     }      

  30. }   

該程序在Intent 的使用上,與上節中的使用方式有很大的不同,即根本不指定接收者,初始化 Intent 對象時,只是傳入參數,設定 Action為 Intent.ACTION_DIAL :

Intent intent = new Intent(Intent. ACTION_DIAL );

startActivity(intent);

這里使用的構造函數的原型如下:

Intent ( String action);

這里讀者可暫時將action理解為描述這個 Intent 的一種方式,這種使用方式看上去比較奇怪, Intent 的發送者只是指定了 Action為 Intent.ACTION_DIAL ,那么怎么找到接收者呢?來看下面的例子。

增加一個接收者

事實上接收者如果希望能夠接收某些 Intent ,需要像上節例子中一樣,通過在  AndroidManifest.xml中增加Activity 的聲明,并設置對應的 Intent Filter 和 Action ,才能被  Android 的應用程序框架所匹配。為了證明這一點,我們修改上一 節 SimpleIntentTest 程序中的  AndroidManifest.xml 文件,將 TestActivity 的聲明部分改為:

XML/HTML代碼

  1. <activity   android:name = ".TestActivity" >  

  2.          <intent-filter >  

  3.              <action   android:name = "android.intent.action.DEFAULT"   />  

  4.              <action   android:name = "android.intent.action.DIAL"   />  

  5.              <category   android:name = "android.intent.category.DEFAULT"  />  

  6.          </intent-filter >  

  7. </activity >   

修改完之后注意要重新安裝 SimpleIntentTest 程序的apk 包,然后再嘗試運行 ImplicitIntentTest 程序(不是SimpleIntentTest 程序)

這個截圖中的第二幅表示可以選擇 Dialer 或者 SimpleIntentTest 程序來完成  Intent.ACTION_DIAL ,也就是說,針對 Intent.ACTION_DIAL, Android 框架找到了兩個符合條件的  Activity,因此它將這兩個 Activity 分別列出,供用戶選擇。

回過頭來看我們是怎么做到這一點的。我們僅僅在 SimpleIntentTest 程序的 AndroidManifest.xml 文件中增加了下面的兩行:

XML/HTML代碼

  1. <action android:name = "android.intent.action.DIAL" />  

  2.  category android:name = "android.intent.category.DEFAULT"/>  

這兩行修改了原來的 Intent Filter,這樣這個 Activity 才能夠接收到我們發送的 Intent  。我們通過這個改動及其作用,可以進一步理解隱式 Intent, Intent Filter 及 Action, Category 等概念&mdash;&mdash;  Intent 發送者設定 Action 來說明將要進行的動作,而 Intent 的接收者在 AndroidManifest.xml  文件中通過設定 Intent Filter來聲明自己能接收哪些Intent 。

到此,關于“Android中的Intent機制有什么用”的學習就結束了,希望能夠解決大家的疑惑。理論與實踐的搭配能更好的幫助大家學習,快去試試吧!若想繼續學習更多相關知識,請繼續關注億速云網站,小編會繼續努力為大家帶來更多實用的文章!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

安福县| 聂拉木县| 吉木乃县| 河间市| 女性| 织金县| 新沂市| 廊坊市| 揭西县| 逊克县| 普安县| 隆尧县| 崇左市| 昭苏县| 应城市| 天峻县| 锡林郭勒盟| 陇南市| 涞源县| 定兴县| 嘉荫县| 张家港市| 吉首市| 南澳县| 南充市| 昆明市| 邢台县| 水富县| 成武县| 宜州市| 沈丘县| 德格县| 宜黄县| 鹤岗市| 综艺| 蓬溪县| 威海市| 栾城县| 临沧市| 常山县| 疏勒县|