由于Android系統(tǒng)本身是基于Linux 操作系統(tǒng),因此Android應(yīng)用程序也運(yùn)行于Linux 環(huán)境中,它
們具有以下的特點(diǎn):
?? 在默認(rèn)情況下,每一個(gè)應(yīng)用程序運(yùn)行于它們的Linux 進(jìn)程中;
?? 每個(gè)進(jìn)程具有自己的虛擬機(jī)(VM),所以每個(gè)應(yīng)用程序運(yùn)行于獨(dú)立的環(huán)境中;
?? 在默認(rèn)情況下,每一個(gè)應(yīng)用程序具有唯一的Linux用戶 ID。通過(guò)設(shè)置權(quán)限讓?xiě)?yīng)用程序只對(duì)用戶和應(yīng)用程
序本身可見(jiàn),也有一些方法可以把它們暴露給其他的應(yīng)用程序。
應(yīng)用程序的組成部分
一般情況下,Android應(yīng)用程序由以下4 種組件構(gòu)成:
?? 活動(dòng)(Activity);
?? 廣播接收器(BroadcastReceiver);
?? 服務(wù)(Service );
?? 內(nèi)容提供者(Content Provider )。
一個(gè)Android應(yīng)用程序是一個(gè)包(Package),包中可能包含一個(gè)或者多個(gè)Android組件(component )
(1)活動(dòng)(Activity)
活動(dòng)是最基本的Android應(yīng)用程序組件,在應(yīng)用程序中,一個(gè)活動(dòng)通常就是一個(gè)單獨(dú)的用戶界面。每一個(gè)
活動(dòng)都被實(shí)現(xiàn)為一個(gè)獨(dú)立的類(lèi),并且從活動(dòng)(Activity)基類(lèi)中繼承而來(lái),活動(dòng)類(lèi)將會(huì)顯示由視圖(View)控 件組成的用戶接口,并對(duì)事件(Event)做出響應(yīng)。大多數(shù)的應(yīng)用程序都會(huì)有多個(gè)用戶界面,因此便會(huì)有多個(gè)相
應(yīng)的活動(dòng)。
Android 的一個(gè)活動(dòng)一般對(duì)應(yīng)界面中的一個(gè)屏幕顯示,可以理解成一個(gè)界面,每一個(gè)活動(dòng)在界面上可以包
含按鈕、文本框等多種可視的UI元素。
(2)廣播接收器(BroadcastReceiver)
廣播接收器用于讓?xiě)?yīng)用程序?qū)σ粋(gè)外部事件做出響應(yīng)。例如:電話呼入事件、數(shù)據(jù)網(wǎng)絡(luò)可用通知或者到了
晚上時(shí)進(jìn)行通知。
(3)服務(wù)(Service)
一個(gè)服務(wù)是一個(gè)具有一段較長(zhǎng)生命周期但沒(méi)有用戶界面的程序。例如:一個(gè)正在從播放列表中播放歌曲的
媒體播放器在后臺(tái)運(yùn)行。
(4)內(nèi)容提供者(Content Provider)
應(yīng)用程序能夠?qū)⑺鼈兊臄?shù)據(jù)保存到文件或SQLite 數(shù)據(jù)庫(kù)中,甚至是任何有效的設(shè)備中。當(dāng)需要將數(shù)據(jù)與其
他的應(yīng)用共享時(shí),內(nèi)容提供者將會(huì)很有用。一個(gè)內(nèi)容提供者類(lèi)實(shí)現(xiàn)了一組標(biāo)準(zhǔn)的方法,從而能夠讓其他應(yīng)用程序
保存或讀取此內(nèi)容提供者處理的各種數(shù)據(jù)類(lèi)型。
應(yīng)用程序的生命周期
(1)前臺(tái)(Foreground)進(jìn)程
(2)可見(jiàn)(Visible )進(jìn)程
(3)服務(wù)(Service)進(jìn)程
(4)后臺(tái)(Background)進(jìn)程
(5)空(Empty)進(jìn)程
(1)前臺(tái)(Foreground)進(jìn)程
與用戶當(dāng)前正在做的事情密切相關(guān),不同的應(yīng)用程序組件能夠通過(guò)不同的方法使它的宿主進(jìn)程移到前臺(tái)。當(dāng)下面任何一個(gè)條件滿足時(shí),都可以考慮將進(jìn)程移到前臺(tái)。
?? 進(jìn)程正在屏幕的最前端運(yùn)行一個(gè)與用戶交互的Activity(它的 onResume() 方法被調(diào)用);
?? 進(jìn)程有一個(gè)正在運(yùn)行的BroadcastReceiver(它的BroadcastReceiver.onReceive()方法正在執(zhí)行);
?? 進(jìn)程有一個(gè)Service ,并且在 Service 的某個(gè)方法(Service.onCreate()、Service.onStart() 或者Service.onDestroy())內(nèi)有正在執(zhí)行的代碼。
(2)可見(jiàn)(Visible )進(jìn)程
它有一個(gè)可以被用戶從屏幕上看到的Activity,但不在前臺(tái)——其 onPause()方法被調(diào)用。例如:如果前臺(tái)
的Activity是一個(gè)對(duì)話框,以前的Activity隱藏在對(duì)話框之后,就可能出現(xiàn)這種進(jìn)程。這樣的進(jìn)程很重要,一
般不允許被殺死,除非為了保證前臺(tái)進(jìn)程的運(yùn)行不得不這樣做。
(3)服務(wù)(Service)進(jìn)程
有一個(gè)已經(jīng)用startService()方法啟動(dòng)的Service,雖然這些進(jìn)程用戶無(wú)法直接看到,但它們做的事情卻是用
戶所關(guān)心的(例如:后臺(tái)MP3 回放或后臺(tái)網(wǎng)絡(luò)數(shù)據(jù)的上傳/ 下載)。因此,系統(tǒng)將一直運(yùn)行這些進(jìn)程,除非內(nèi)
存不足以維持所有的前臺(tái)進(jìn)程和可見(jiàn)進(jìn)程。
(4)后臺(tái)(Background )進(jìn)程
擁有一個(gè)當(dāng)前用戶看不到的Activity(它的onStop() 方法被調(diào)用),這些進(jìn)程對(duì)用戶體驗(yàn)沒(méi)有直接的影響。
如果它們正確執(zhí)行了Activity生命周期,系統(tǒng)可以在任意時(shí)刻殺死進(jìn)程來(lái)回收內(nèi)存,并提供給前面3 種類(lèi)型的
進(jìn)程使用。系統(tǒng)中通常有很多這樣的進(jìn)程在運(yùn)行,因此要將這些進(jìn)程保存在LRU 列表中,以確保當(dāng)內(nèi)存不足
時(shí)用戶最近看到的進(jìn)程最后一個(gè)被殺死。
(5)空(Empty )進(jìn)程
不包含任何處于活動(dòng)狀態(tài)的應(yīng)用程序組件。保留這種進(jìn)程的唯一原因是,當(dāng)下次應(yīng)用程序的某個(gè)組件需要
運(yùn)行時(shí),不需要重新創(chuàng)建進(jìn)程,這樣可以提高啟動(dòng)速度。
以上所說(shuō)的“進(jìn)程”是從系統(tǒng)運(yùn)行的角度考慮的,各種不同的進(jìn)程可以理解成Android的各種組件的不同
狀態(tài)機(jī)(state machine )。如果從應(yīng)用程序的代碼以及運(yùn)行情況考慮,可以關(guān)注 Android的各種組件相對(duì)應(yīng)的生命周期
1 . 活動(dòng)的生命周期
2 . 服務(wù)的生命周期
3 . 廣播接收器的生命周期
1 . 活動(dòng)的生命周期
活動(dòng)是Android 中最重要、最基礎(chǔ)的組件,用戶在界面上看到的一個(gè)個(gè)可以切換的屏幕界面就是Android
中的活動(dòng);顒(dòng)的生命周期如圖1 所示。
?? 運(yùn)行活動(dòng)的情景:當(dāng)一個(gè)活動(dòng)被啟動(dòng)時(shí),活動(dòng)中的onCreate()、onStart() 和onResume() 這3 個(gè)方法被依次調(diào)用,活動(dòng)對(duì)應(yīng)的界面出現(xiàn)在屏幕上。
?? 活動(dòng)被“覆蓋”的情景:Android的活動(dòng)一般都占據(jù)一個(gè)完整的屏幕,從當(dāng)前活動(dòng)啟動(dòng)另外一個(gè)活動(dòng)時(shí),另
一個(gè)活動(dòng)將被啟動(dòng)到前臺(tái)(Foreground ),當(dāng)前活動(dòng)轉(zhuǎn)入后臺(tái)(Background ),這時(shí)活動(dòng)的 onPasuse()方法將
被調(diào)用,活動(dòng)轉(zhuǎn)入后臺(tái)運(yùn)行。如果活動(dòng)變?yōu)椴豢梢?jiàn),還將調(diào)用onStop()方法。在轉(zhuǎn)入后臺(tái)時(shí),onStop()是否
被調(diào)用取決于活動(dòng)是否被完全覆蓋,在新的活動(dòng)有透明部分時(shí),轉(zhuǎn)入后臺(tái)的活動(dòng)依然“可見(jiàn)”,其他情況下
(較多數(shù)的情況)活動(dòng)均進(jìn)入不可見(jiàn)狀態(tài)(被完全覆蓋)。
?? 活動(dòng)被恢復(fù)的情景:當(dāng)界面上最前面的活動(dòng)退出后,它所覆蓋的活動(dòng)將被恢復(fù),這時(shí)onResume() 方法將被
調(diào)用,活動(dòng)重新轉(zhuǎn)入前臺(tái)運(yùn)行。
?? 活動(dòng)完全退出的情景:當(dāng)使用回退(Back)按鈕退出活動(dòng)時(shí),onDestroy() 方法將被調(diào)用,活動(dòng)關(guān)閉。如果
系統(tǒng)缺少內(nèi)存時(shí),也會(huì)殺死(kill)后臺(tái)的活動(dòng),其中優(yōu)先殺死不可見(jiàn)的活動(dòng),可見(jiàn)的活動(dòng)一般不會(huì)被殺死。
2 . 服務(wù)的生命周期
服務(wù)可以長(zhǎng)時(shí)間運(yùn)行,它的特點(diǎn)是沒(méi)有可視化界面,服務(wù)的生命周期如圖2 所示
使用StartService 運(yùn)行服務(wù)的情景:使用這種方法啟動(dòng)服務(wù),服務(wù)的onCreate()和onStart() 這兩個(gè)方法將被調(diào)用,服務(wù)會(huì)在后臺(tái)運(yùn)行直到退出,退出時(shí)將調(diào)用onDestroy() 方法。
使用bindService 運(yùn)行服務(wù)的情景:使用這種方法啟動(dòng)服務(wù),調(diào)用者(也就是服務(wù)的客戶端)將獲得和服務(wù)
交互的類(lèi),通過(guò)其調(diào)用時(shí)服務(wù)的相關(guān)內(nèi)容會(huì)處于活動(dòng)狀態(tài)。
3 . 廣播接收器的生命周期
廣播接收器有一個(gè)單一的回調(diào)方法onReceive() ,當(dāng)廣播消息到達(dá)接收器時(shí),Android將調(diào)用這個(gè)方法,并
傳遞給包含在這個(gè)消息中的Intent 對(duì)象。
廣播接收器只有在這個(gè)方法的執(zhí)行過(guò)程中才處于活動(dòng)狀態(tài),當(dāng) onReceive() 返回后,廣播接收器將不再處于
活動(dòng)狀態(tài)。廣播接收器的功能類(lèi)似于一個(gè)回調(diào)函數(shù),只是單次運(yùn)行時(shí)處于活動(dòng)狀態(tài)。
Android的工程編譯
在編譯Android應(yīng)用程序的過(guò)程中,Java 源代碼使用Sun JDK 將Java 源程序編譯成Java 字節(jié)碼文件(多
個(gè)后綴名為.class 的文件),這一步驟和標(biāo)準(zhǔn)的Java 一致,然后通過(guò)Android自帶的工具軟件dex 把所有的字
節(jié)碼文件轉(zhuǎn)成dex 文件(單一文件classes.dex )。
AndroidManifest.xml 文件經(jīng)過(guò)Android打包工具(aapt )處理后形成二進(jìn)制格式 AndroidManifest.xml 文件,實(shí)質(zhì)的內(nèi)容與以前相同。
各個(gè)資源文件也經(jīng)過(guò)aapt 處理,其中布局等文本文件處理成二進(jìn)制文件,圖片等文件保持不變。
最后將這三個(gè)部分組合成一個(gè)應(yīng)用程序包(*.apk)。AndroidManifest.xml 描述文件、Java 源文件、資源文
件是Android應(yīng)用程序的三個(gè)部分;在編譯之前的工程中是這三個(gè)部分,在編譯之后APK包依然是由這三個(gè)部
分組成的。
如圖所示,Android源文件經(jīng)過(guò)了標(biāo)準(zhǔn)的Java 編譯器的編譯,又經(jīng)過(guò)了dx工具的處理,標(biāo)準(zhǔn)的Java 字節(jié)
碼作為整個(gè)Android編譯的中間過(guò)程,最終生成的dex 文件(classes.dex )是一個(gè)單一文件,將工程中所有的Java源代碼文件對(duì)應(yīng)的字節(jié)碼集成在一起。資源文件和AndroidManifest.xml 文件通過(guò)aapt 工具進(jìn)行處理。
在運(yùn)行時(shí),APK包將首先進(jìn)行“安裝”,也就是將其中的 dex 文件進(jìn)行優(yōu)化,優(yōu)化后的文件被保存到緩存
區(qū)域,生成格式為 dey 的優(yōu)化文件,然后 Dalvik 虛擬機(jī)將運(yùn)行這些dey 文件。如果應(yīng)用程序包文件不發(fā)生變化,dey 文件不會(huì)被重新生成;在應(yīng)用程序包發(fā)生更新的情況下,將重新由dex 生成dey。
Android和標(biāo)準(zhǔn) JAVA 開(kāi)發(fā)的JAR 包最大的不同在于,標(biāo)準(zhǔn)JAVA 字節(jié)碼是每個(gè)文件一個(gè)Clash文件,而
Android中的一個(gè)包將生成一個(gè)Dex 文件。
使用am工具啟動(dòng)Android 應(yīng)用程序
除了在GUI 界面中啟動(dòng)應(yīng)用程序之外,在 Android的命令行終端(可以使用 adb shell 進(jìn)行連接)也可以使
用am 工具啟動(dòng)應(yīng)用程序。
使用am 啟動(dòng)應(yīng)用程序的格式如下所示:
# am start -n {包名}/{ 包名}.活動(dòng)名
應(yīng)用程序開(kāi)發(fā)的結(jié)構(gòu)
Android應(yīng)用程序開(kāi)發(fā)是Android開(kāi)發(fā)中最上面的一個(gè)層次,它們構(gòu)建在Android系統(tǒng)提供的API 之上。
Android應(yīng)用程序的基礎(chǔ)是Android提供的各個(gè)Java 類(lèi),這些類(lèi)組成了Android系統(tǒng)級(jí)的API。

Android應(yīng)用程序可以基于兩種環(huán)境來(lái)開(kāi)發(fā):Android SDK 和Android源代碼。Android系統(tǒng)本身內(nèi)置了一部分標(biāo)準(zhǔn)應(yīng)用(也包括內(nèi)容提供者),在仿真器(包括 SDK環(huán)境和源代碼環(huán)境)中已經(jīng)包含這些內(nèi)置的程序。 用戶自行開(kāi)發(fā)的應(yīng)用程序和Android內(nèi)置的應(yīng)用層程序包位于同一個(gè)層次,都是基于Android框架層的API來(lái)構(gòu)建的,它們的區(qū)別僅僅在于他們是否被包含在默認(rèn)的Android系統(tǒng)中。
Android目錄結(jié)構(gòu)
src : Java 源代碼文件
assets:主要放置多媒體等數(shù)據(jù)文件。
AndroidManifest.xml: 工程描述文件,相當(dāng)于應(yīng)用的配置文件。在此文件里必須聲明應(yīng)用的名稱,應(yīng)用所用到的Activity,Service,Reveiver等。
可惜的是drawable目錄下不能分子級(jí)目錄,如果有這方面需求只能通過(guò)命名方法來(lái)加以區(qū)分。
每個(gè)猶序都會(huì)有一竢oidManifest在它的根目錄里面。這個(gè)清單為Android系統(tǒng)提供了這個(gè)應(yīng)用的基本信息,系統(tǒng)在運(yùn)行之前必須知道這些信息,另外,如果我們使用系統(tǒng)自帶的服務(wù),如撥號(hào)服務(wù),應(yīng)用安裝服務(wù)等,都必須在AndroidManifest.xml文件中聲明權(quán)限 AndroidManifest.xml的功能: 命名應(yīng)用程序的Java應(yīng)用包,這個(gè)包名用來(lái)唯一標(biāo)識(shí)應(yīng)用程序; 描述應(yīng)用程序的組件,對(duì)實(shí)現(xiàn)每個(gè)組件和公布其功能的類(lèi)進(jìn)行命名,這些聲明使得Android系統(tǒng)了解這些組件以及它們?cè)谑裁礂l件下可以被啟動(dòng) 決定哪個(gè)組件運(yùn)行在哪個(gè)進(jìn)程里面 聲明應(yīng)用程序必須具備的權(quán)限,用以訪問(wèn)受保護(hù)的API,以及和其他進(jìn)程的交互 聲明應(yīng)用程序其他的必備權(quán)限,用以組件之間的交互 列舉application所需要鏈接的庫(kù) drawable-*dpi: 將圖標(biāo)按分辨率的高低放入不同的目錄,其中draeable-hdpi用來(lái)存放高分辨率的圖標(biāo),drawable-mdpi用來(lái)存放中等分辨率的圖標(biāo),drawable-ldpi用來(lái)存放低分辨率的圖標(biāo)
res :資源文件
| |
|
values文件夾:用來(lái)存放文字的信息
(1)strings.xml:用來(lái)定義字符串和數(shù)值
<?xml version="1.0"encoding="utf-8"?>
<resources>
<string >Hello World, Hello 3G</string>
<string >Android1.1</string>
<string >哥想你了</string>
<string >按鈕1</string>
<string >按鈕1</string>
</resources>
每個(gè)string標(biāo)簽生命了一個(gè)字符串,name屬性指定它的引用值
(2)為什么要把這些出現(xiàn)的文字單獨(dú)放在strings.xml文件中?
答案:一是為了國(guó)際化,如果需要將文件中的文字換成別的國(guó)家的語(yǔ)言,就可以只需要替換掉一個(gè)strings.xml文件就可以了;二是為了減少應(yīng)用的體積,例如,我們要在應(yīng)用中使用“哥想你了”這句話1000次,如果我們沒(méi)有將“哥想你了”定義在strings.xml文件中,而是直接在應(yīng)用中使用時(shí)寫(xiě)上這幾個(gè)字,那么我們就會(huì)在應(yīng)用中寫(xiě)4000個(gè)字。4000個(gè)字和4個(gè)字占用的內(nèi)存可是有很大差距的啊,況且手機(jī)的內(nèi)存本來(lái)就小,所以應(yīng)該是能省就省 (3)另外還有arrays.xml,color.xml等定義數(shù)組,顏色的,都最好用單獨(dú)的一個(gè)xml文檔
layout文件:用來(lái)存放界面信息
<?xml version="1.0"encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical">
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="@string/test"/>
</LinearLayout>
<LinearLayout>元素:線性布局的意思,在該元素下的所有子元素都會(huì)根據(jù)他的”orientation”屬性來(lái)決定是按行還是按列或者按逐個(gè)顯示進(jìn)行布局的
<TextView>元素:是一種顯示控件,他的”text”屬性指定了在這個(gè)元素上顯示的內(nèi)容
gen目錄:gen目錄下只有一個(gè)自動(dòng)生成的“R.java”文件
R.java文件:默認(rèn)有attr,drawable,layout,string這四個(gè)靜態(tài)內(nèi)部類(lèi),每個(gè)靜態(tài)內(nèi)部類(lèi)對(duì)應(yīng)一中資源,如layout靜態(tài)內(nèi)部類(lèi)對(duì)應(yīng)layout中的界面文件,string靜態(tài)內(nèi)部類(lèi)對(duì)應(yīng)string內(nèi)部的string標(biāo)簽。如果在layout中在增加一個(gè)界面文件或者在string內(nèi)增加一個(gè)string標(biāo)簽,R.java會(huì)自動(dòng)在其對(duì)應(yīng)的內(nèi)部類(lèi)增加所增加的內(nèi)容。
R.java除了自動(dòng)標(biāo)識(shí)資源的索引功能外,還有另一個(gè)功能,就是當(dāng)res文件中的某個(gè)資源在應(yīng)用中沒(méi)有被用到,在這個(gè)應(yīng)用被編譯時(shí),系統(tǒng)不會(huì)把對(duì)應(yīng)的資源編譯到應(yīng)用中的APR包中。
可以參考:原文鏈接:http://blog.csdn.net/xy84928/article/details/7047419
<project.properties>應(yīng)用要求運(yùn)行的最低Android版本
<android 2.2> 存放Android自身的jar包

android應(yīng)用程序的入口 android應(yīng)用程序中,并沒(méi)有像c++和java這樣有main函數(shù)來(lái)作為應(yīng)用程序的入口.android應(yīng)用程序提供的是入口Activity,而非入口函數(shù). 在eclipse中創(chuàng)建一個(gè)android應(yīng)用程序的時(shí)候,默認(rèn)會(huì)創(chuàng)建一個(gè)Activity.這個(gè)Activity實(shí)際上就是入口Activity了.從哪里定義它是Activity呢?AndroidManifest.xml文件中定義了整個(gè)android應(yīng)用所包含的Activity.默認(rèn)生成的Activity的定義為:
<activity android: android:label="@string/app_name">
<intent-filter>
<action android: />
<category android: />
</intent-filter>
</activity>
android應(yīng)用程序?qū)嶋H上是由多個(gè)Activity按照一定的次序拼裝起來(lái)的,只不過(guò)拼裝的過(guò)程中,后臺(tái)傳遞了一些數(shù)據(jù),使得各個(gè)Activity之間能比較好的銜接起來(lái)。
action節(jié)點(diǎn)中的android.intent.action.MAIN表明它所在的Activity是整個(gè)應(yīng)用程序的入口點(diǎn).而category中的android.intent.category.LAUNCHER意思是把這個(gè)Activityg歸屬到加載器類(lèi),即把這個(gè)Activity標(biāo)注為自動(dòng)會(huì)加載和啟動(dòng)的Activity,這樣程序啟動(dòng)時(shí)候就先加載這個(gè)Activity了.
Android的UI系統(tǒng)實(shí)現(xiàn)1 控制和基本事件的響應(yīng)
2 鍵盤(pán)事件的響應(yīng)
3 運(yùn)動(dòng)事件的處理
4 屏幕間的跳轉(zhuǎn)和事件的傳遞
5 菜單的使用
6 彈出對(duì)話框
7 樣式的設(shè)置
Android UI 系統(tǒng)的知識(shí)結(jié)構(gòu)如下圖所示:
對(duì)于 一個(gè)GUI系統(tǒng)地使用,首先是由應(yīng)用程序來(lái)控制屏幕上元素的外觀和行為,這在各個(gè) GUI 系統(tǒng)中是
不相同的,但是也具有相通性。Android系統(tǒng)在這方面,包含了基本的控件控制,鍵盤(pán)事件響應(yīng),窗口間跳轉(zhuǎn)、
對(duì)話框、菜單、樣式等內(nèi)容,這是GUI 系統(tǒng)所具有的通用內(nèi)容。
1 控件和基本事件的響應(yīng)
在任何一個(gè)GUI 系統(tǒng)中,控制界面上的控件(通常稱為控件)都是一個(gè)基本的內(nèi)容。對(duì)于 Android應(yīng)用程
序,控件稱為View。
在Android中,在處理UI中的各種元素的時(shí)候,兩個(gè)程序中的要點(diǎn)為:
?? 1.得到布局文件(XML)中的控件句柄
?? 2.設(shè)置控件的行為
1.1 事件響應(yīng)方法