<1>關(guān)于Activity和AndroidManifest
我們AS項(xiàng)目里的AndroidManifest.xml文件其實(shí)就是一個(gè)清單文件,用于描述我們的項(xiàng)目?jī)?nèi)容
其中包含了一些Application、activity、包名等信息,還包括一些權(quán)限的聲明(例如在數(shù)據(jù)存儲(chǔ)時(shí)使用SD卡讀寫的權(quán)限聲明)
四大組件也都需要在這里注冊(cè)之后才能使用
?
Application就代表一個(gè)應(yīng)用程序,其中可以包含四大組件
而Activity是用于處理用戶操作,與用戶進(jìn)行交互的(可以理解為一個(gè)容器,一個(gè)窗口,主要用于承載UI內(nèi)容)
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.androidactivitydemo"> //包名
//這兩行就是設(shè)置權(quán)限,允許外置存儲(chǔ)卡讀寫操作
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
//一個(gè)application就代表了一個(gè)應(yīng)用程序
<application
android:allowBackup="true" //允許系統(tǒng)備份
android:icon="@mipmap/ic_launcher" //設(shè)置應(yīng)用的桌面圖標(biāo)(這些圖標(biāo)存儲(chǔ)在res文件夾的mipmap里的lc_launcher下)
android:label="@string/app_name" //設(shè)置應(yīng)用程序的名稱(它存儲(chǔ)在res文件夾的values下的strings里)
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true" //支持從右到左
android:theme="@style/Theme.AndroidActivityDemo"> //用于控制樣式(它存儲(chǔ)在res文件夾的values下的themes里)
<activity
android:name=".MainActivity" //四大組件的靜態(tài)注冊(cè)都要這樣
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
?
如何在一個(gè)Application中再新建一個(gè)activity呢?(即如何再新建一個(gè)UI窗口)
——首先新建一個(gè)類SecondActivity,這個(gè)類繼承Activity
——重寫其中的onCreate()方法
——然后再新建一個(gè)布局activity_second,在SecondActivity類中setContentView()顯示這個(gè)布局
——最后要使這個(gè)新的Activity可以使用,需要在配置列表里注冊(cè)一下
可以看到,在一個(gè)application中注冊(cè)了有兩個(gè)activity,一個(gè)標(biāo)簽設(shè)置為“第一個(gè)ActivityDemo”,另一個(gè)設(shè)置為“第二個(gè)ActivityDemo”,同時(shí)給了兩個(gè)intent-filter,都聲明的是主入口
所以最終的結(jié)果是,在手機(jī)中有兩個(gè)app圖標(biāo),都可以打開這個(gè)程序,分別是這個(gè)程序的兩個(gè)界面
?
<2>利用顯式意圖來實(shí)現(xiàn)界面跳轉(zhuǎn)
(顯式Intent:按名稱(完全限定類名)指定要啟動(dòng)的組件)
用一個(gè)案例來學(xué)習(xí)顯式意圖的界面跳轉(zhuǎn)(目標(biāo)是在主界面輸入賬號(hào)和密碼,點(diǎn)擊登錄按鍵后,跳轉(zhuǎn)到另一個(gè)界面,并在其中顯示我們輸入的賬號(hào)和密碼)
——首先,在MainActivity中和原來一樣,通過id找到我們輸入的賬號(hào)和密碼
——然后判斷賬號(hào)和密碼是否為空,如果不為空,則創(chuàng)建一個(gè)意圖對(duì)象 Intent ,把我們的賬號(hào)和密碼的值存儲(chǔ)到這個(gè)對(duì)象里 putExtra()方法,存儲(chǔ)了鍵值對(duì)
——調(diào)用startActivity()方法進(jìn)行界面的跳轉(zhuǎn)
——新建一個(gè)類SecondActivity,繼承Activity并重寫其中的onCreate()方法
——這個(gè)activity記得要在配置清單中聲明一下才能使用
——最后在SecondActivity類中的onCreate方法里,getIntent()得到第一個(gè)界面中我們創(chuàng)建的意圖對(duì)象,然后獲取其中的內(nèi)容并顯示
——最終效果如下
?
<3>利用隱式意圖來實(shí)現(xiàn)界面跳轉(zhuǎn)
(隱式Intent:不會(huì)指定特定的組件,而是聲明要執(zhí)行的常規(guī)操作,從而允許其他應(yīng)用中的組件來處理它)
隱式意圖實(shí)現(xiàn)界面跳轉(zhuǎn)的方式和顯式差不多,主要差別就是創(chuàng)建Intent的方法
?
<4>區(qū)別
顯式意圖:也就是可以直接看到我們要跳轉(zhuǎn)到的目標(biāo)組件,例如之前要從MainActivity跳轉(zhuǎn)到SecondActivity,用的是new Intent(this, SecondActivity.class);在這里面我們直接就可以看到目標(biāo)組件的名稱(一般是用于應(yīng)用內(nèi)組件的跳轉(zhuǎn))
隱式意圖:用于跳轉(zhuǎn)到第三方應(yīng)用(一般是用于各個(gè)應(yīng)用之間的跳轉(zhuǎn))
?
——?jiǎng)?chuàng)建顯式意圖的幾種寫法:
//第一種:
Intent intent = new Intent();
intent.setClassName("包名","類名");
startActivity(intent);
?
//第二種:
Intent intent = new Intent();
ComponentName componentName = new ComponentName("包名","類名");
startActivity(intent);
?
//第三種:
Intent intent = new Intent(this, 要跳轉(zhuǎn)的界面類名.class );
startActivity(intent);
其實(shí)還有很多種寫法,沒有全部列出來
創(chuàng)建顯式意圖主要就是要找到組件的名稱 ComponentName = 包名/類的路徑名稱
由于顯式意圖主要是用在應(yīng)用內(nèi)部各個(gè)組件之間的跳轉(zhuǎn),所以第三種方式就很方便
?
——?jiǎng)?chuàng)建隱式意圖
隱式意圖的創(chuàng)建步驟為:
創(chuàng)建Intent對(duì)象
給這個(gè)intent對(duì)象設(shè)置Action,設(shè)置它的category值,設(shè)置包名(可以在Android系統(tǒng)源碼里查找過濾器 intent-filter 查看各個(gè)系統(tǒng)應(yīng)用的action值和category值)
使用startActivity()方法跳轉(zhuǎn)到另一個(gè)界面
Intent intent = new Intent();
intent.setAction(" 目標(biāo)應(yīng)用的組件的action值? ");
intent.setCategory(" 目標(biāo)應(yīng)用的組件的category值 ");
intent.setPackage(" 目標(biāo)應(yīng)用的組件的包名 ");
startActivity(intent);
采用這種方式,在創(chuàng)建和使用的時(shí)候我們是看不見這個(gè)組件的名稱的,只通過它的action值,category值和包名就可以使用了
?
<5>組件之間的數(shù)據(jù)傳遞
Activity之間的數(shù)據(jù)傳遞和組件之間的數(shù)據(jù)傳遞是一樣的
數(shù)據(jù)傳遞又分為兩種:1 基本數(shù)據(jù)類型的數(shù)據(jù)傳遞??? 2? 引用數(shù)據(jù)類型的數(shù)據(jù)傳遞(對(duì)象的傳遞)
?
——基本數(shù)據(jù)類型數(shù)據(jù)的傳遞
直接創(chuàng)建一個(gè)意圖intent,調(diào)用intent中的putExtra()方法就可以把基本數(shù)據(jù)類型的數(shù)據(jù)以鍵值對(duì)的形式存儲(chǔ)在這個(gè)intent中
然后切換界面,在接收界面中首先getIntent()拿到這個(gè)intent對(duì)象,然后再用intent.getExtra()方法用鍵獲取到相應(yīng)的值即可
?
——引用數(shù)據(jù)類型數(shù)據(jù)的傳遞
其實(shí)引用數(shù)據(jù)類型的傳遞和基本數(shù)據(jù)類型的數(shù)據(jù)傳遞方式差不多,都是利用了putExtra()和getIntent()兩個(gè)方法,不同的是引用數(shù)據(jù)類型的數(shù)據(jù)在傳遞前必須要把數(shù)據(jù)序列化
要把數(shù)據(jù)序列化,就是要在傳遞的對(duì)象的類中實(shí)現(xiàn)Parcelable接口或者實(shí)現(xiàn)Serializable接口
Parcelable接口是Google自定義的接口,使用起來比較高效,直接將數(shù)據(jù)存儲(chǔ)到內(nèi)存中,然后傳遞
Serializable接口則是Java自帶的,是寫到持久化存儲(chǔ)單元里然后再傳遞的,比較慢
例如我們要傳遞一個(gè)user對(duì)象,首先要對(duì)User類實(shí)現(xiàn)可序列化的接口
然后再傳遞
(需要注意的是,String類和Bitmap類本身就以及實(shí)現(xiàn)了序列化接口的,所以在傳遞string類型數(shù)據(jù)或bitmap類型的數(shù)據(jù)的時(shí)候,不需要再對(duì)其實(shí)現(xiàn)序列化接口,直接和基本數(shù)據(jù)類型傳遞一樣的使用就可以了)
?
?
?
?
來寫一個(gè)撥打電話的按鍵,練習(xí)一下用協(xié)議來傳數(shù)據(jù):
?
?注意要在配置清單中打開打電話的權(quán)限
?
?類似的打電話,發(fā)短信,或者操作其他應(yīng)用的都可以通過這種方法,在Android源碼中找到相應(yīng)的參數(shù),通過創(chuàng)建隱式意圖的方法進(jìn)行跳轉(zhuǎn)和根據(jù)其中規(guī)定的協(xié)議進(jìn)行數(shù)據(jù)傳輸
?
——也可以自己按這種方法定義界面操作,在配置清單中配置一下即可,其中 action 內(nèi)容就是包名.應(yīng)用名稱 , category 意思就是這個(gè)應(yīng)用的類別(例如DEFAULT就表示這是一個(gè)應(yīng)用),data 后面可以自己設(shè)置約束
然后通過隱式意圖,填寫相關(guān)的配置信息,就可以跳轉(zhuǎn)到該應(yīng)用界面并傳輸數(shù)據(jù)
?
?<6>Activity之間的數(shù)據(jù)回傳
例如我們發(fā)微信朋友圈的時(shí)候,需要從朋友圈編輯界面先跳轉(zhuǎn)到相冊(cè)界面,選擇想要發(fā)布的相片,然后選完之后會(huì)自動(dòng)返回到朋友圈的編輯界面,并且選中的相片會(huì)傳到這里
這種類似的情況就用到了Activity之間的數(shù)據(jù)回傳
數(shù)據(jù)回傳和跳轉(zhuǎn)界面差不多,主要的區(qū)別在于數(shù)據(jù)回傳要用到startActivityForResult(intent)這個(gè)方法而不是startActivity(intent)方法
?
寫一個(gè)充值的例子來練習(xí),具體要求是:
在主界面點(diǎn)擊充值按鍵,跳轉(zhuǎn)到充值界面,在充值界面充值等操作后,自動(dòng)返回到主界面并顯示操作結(jié)果
主界面中的操作
?
?支付界面的操作
?
?
?
?
?主要的思路就是,主界面調(diào)用startActivityForResult(intent,requestCode<1> )方法
在充值界面中,當(dāng)完成充值操作會(huì)調(diào)用setResult(resulCode<2> , intent)方法,當(dāng)完成取消充值會(huì)調(diào)用setResult(resultCode<3> ,intent)方法
在主界面中重寫onActivityResult()方法,在這個(gè)方法中通過判斷requestCode來確定返回?cái)?shù)據(jù)應(yīng)該去到哪個(gè)部位
通過判斷resultCode來判斷跳轉(zhuǎn)的那個(gè)界面到底做了什么操作,用data.getExtra()方法獲取到相應(yīng)操作的數(shù)據(jù)結(jié)果
?
本文摘自 :https://www.cnblogs.com/