cocos2dx跨平台開發中需要了解android開發,昨天快速的瀏覽了一本Android開發入門教程,因為之前也似懂非懂的寫過Activity,Intent,XML文件,還有里面許多控件甚至編程思想都能在IOS中找到影子,所以看起來並不吃力,只求以后看見Android程序能看懂,現在記錄下一些要點心得。
提到Android開發,當然要先搞明白它的四大組件分別代表什么,起什么作用:
(1)活動(Activity)
活動是最基本的 Android 應用程序組件,在應用程序中,一個活動通常就是一個單獨的用戶界面。每一個
活動都被實現為一個獨立的類,並且從活動(Activity)基類中繼承而來,活動類將會顯示由視圖(View)控 件組成的用戶接口,並對事件(Event)做出響應。大多數的應用程序都會有多個用戶界面,因此便會有多個相 應的活動。
Android 的一個活動一般對應界面中的一個屏幕顯示,可以理解成一個界面,每一個活動在界面上可以包 含按鈕、文本框等多種可視的 UI 元素。

圖 1 活動(Activity)的生命周期
(2)廣播接收器(BroadcastReceiver)
廣播接收器用於讓應用程序對一個外部事件做出響應。例如:電話呼入事件、數據網絡可用通知或者到了
晚上時進行通知。
廣播接收器的生命周期
廣播接收器有一個單一的回調方法 onReceive(),當廣播消息到達接收器時,Android 將調用這個方法,並 傳遞給包含在這個消息中的 Intent 對象。
廣播接收器只有在這個方法的執行過程中才處於活動狀態,當 onReceive()返回后,廣播接收器將不再處於 活動狀態。廣播接收器的功能類似於一個回調函數,只是單次運行時處於活動狀態。
(3)服務(Service)
一個服務是一個具有一段較長生命周期但沒有用戶界面的程序。例如:一個正在從播放列表中播放歌曲的
媒體播放器在后台運行。

圖 2 服務(Service)的生命周期
使用 StartService 運行服務的情景:使用這種方法啟動服務,服務的 onCreate()和 onStart()這兩個方法將被 調用,服務會在后台運行直到退出,退出時將調用 onDestroy()方法。
使用 bindService 運行服務的情景:使用這種方法啟動服務,調用者(也就是服務的客戶端)將獲得和服務 交互的類,通過其調用時服務的相關內容會處於活動狀態。
(4)內容提供者(Content Provider)
應用程序能夠將它們的數據保存到文件或 SQLite 數據庫中,甚至是任何有效的設備中。當需要將數據與其 他的應用共享時,內容提供者將會很有用。一個內容提供者類實現了一組標准的方法,從而能夠讓其他應用程序 保存或讀取此內容提供者處理的各種數據類型。
(5)Intent
在一般情況下,Android 的每一個屏幕基本上就是一個活動(Activity),屏幕之間的切換實際上就是在活動間互 相調用的過程,Android 使用 Intent 完成這個動作。
Android 屏幕跳轉的關系和方式如下圖所示:
事實上,在 Android 中,屏幕使用一個活動來實現,屏幕之間是相互獨立的,屏幕之間的跳轉關系通過 Intent 來實現。
實例:本示例是一個簡單的屏幕之間的跳轉,從一個屏幕跳轉到另一個屏幕,在啟動第二個屏幕后,前一個屏幕消失。
布局資源代碼:forward_target.xml 和 forwarding.xml
本示例包含了兩個活動,在 UI 上它們就是兩個屏幕,分別為跳轉的源和目的,因此在 AndroidManifest.xml 中 分別定義。

兩個活動的名稱分別為 Forwarding 和 ForwardTarget,由於第二個活動沒有 intent-filter,因此在程序中只能由第 一個活動來啟動。
Forward 程序的運行結果如圖所示:
啟動第二個活動需要使用 Intent,在其 setClass()函數中設置源和返回的內容,Intent 是 android.content 包中的類, 用於啟動活動、服務或者消息接收器。
這里使用的 Intent 的 setClass()的方法的原型如下所示:

第一個參數是當前的上下文類型 Context,因此把當前的活動設置過去即可(Activity 本身繼承了 Context),第 二個是 Intent 所包含的 JAVA 類,直接設置 ForwardTarget.class 類即可。
本例中使用了 finish()函數表示當前的活動結束,這樣在第二個活動(ForwardTarget)啟動時,第一個活動 (Forward)已經不存在了。如果沒有調用 finish()函數,第二個活動啟動時,第一個活動就處於 OnPause 狀態,當第二個活動退出后,第一個活動重新出現,也就是會調用活動的 onResume()函數。
應用程序包含的各個文件
1.Android.mk:統一工程文件,在SDK開發中可以不需要;
2.AndroidManifest.xml:工程描述文件,在其中定義了各種組件;
AndroidManifest.xml 文件是這個 Android 應用程序的工程描述文件,包含了宏觀上的內容,如下所示:

注解:
1.xmlns:xmlns是XML Namespaces的縮寫,中文名稱是XML命名空間。
3.android:layout_gravity(布局-重力)屬性,其實就是當前view相對於父視圖的位置
android:layout_gravity 可以在各個 View 中使用:top、bottom、left、right、 center_vertical、fill_vertical、center_horizontal、fill_horizontal、center、fill、clip_vertical、clip_horizontal,這些選項 用於處理豎直和水平方向的對齊方式。
application(表示應用程序)標簽中包含了一個 activity(表示活動)。活動是應用程序中的一個組件,一個應用 程序中也可以包含若干個組件。包名定義為 com.example. android.helloactivity,表示將從 src 目錄的 com/example/android/helloactivity 中尋找程序中的 Java 源代碼。活動名稱將被定義為 HelloActivity,表示活動的 代碼是上述源代碼目錄中的HelloActivity.java文件。intent-filter中的內容指定了程序的啟動方式,這里category 中的 android.intent.category.LAUNCHER 表示活動將在 Android 的桌面(Android 默認的桌面程序名稱也是 LAUNCHER)上出現。
這里指定 application 的 android:label 為"Hello,Activity!",這和桌面圖標下面的文字以及活動啟動后上面的 標題文字是一致的。本例沒有指定圖標,所以桌面上的圖標使用的是默認圖標。
在 AndroidManifest.xml 文件中為一個活動指定 label(標簽)和 icon(圖標)的方法 方法如下:

android:label 指定為字符串、android:icon 指定為圖標后,將使用 res/drawable 中對應名稱的圖片文件作為圖 標(本例中將使用 icon_name.png)。
activity 和 application 都具有 android:label 和 android:icon 等屬性,由於活動是程序的單元,且應用可以包 含多個活動,因此程序首先將使用 activity 中的這些標簽,如果沒有則使用上一級的 application 中標簽的定義
3.Java源代碼:按照Java包的方式來組織目錄結構,包括各個Java類的源代碼;

這里的類 HelloActivity 繼承實現了 Android 系統 API 提供的活動類(Activity),使用 setContentView(R.layout.hello_activity)指定了當前活動的布局,這里表示將從 res/layout 目錄中找到 hello_activity.xml 文件作為本例的布局文件使用。
4.資源文件:包含XML文件、圖片、原始數據文件等,其中表示界面情況的布局(Layout)文件比較重要。
hello_activity.xml 是本程序中的布局文件,在 Java 源文件中使用了此文件。本文件在 res/layout 目錄中,其
內容如下所示:

在這個布局文件中,只定義了一個 UI 元素——EditText,就是在界面上出現的占據全屏的可編輯文本框。 在這里定義了這個可編輯文本框的初始化字符串為"@string/hello_activity_text_text",這個值在另外的資源文件 中被定義,本例就是 string.xml。
string.xml 是本例中的一個資源文件,其內容如下所示:

這里定義了名稱為“hello_activity_text_text”的字符串的內容為 Hello,World!,這就是出現在屏幕上的字 符串。

圖 HelloActivity 的運行情況
下面再來個實例,加深理解
在 Android 中,在處理 UI 中的各種元素的時候,兩個程序中的要點為: 得到布局文件(XML)中的控件句柄
設置控件的行為
本小節介紹在 Android 中幾種基本的程序控制方法,要獲得的效果是通過 2 個按鈕來控制一個文本框的背 景顏色,其運行結果如圖所示:
根據以上的布局文件中定義的兩個按鈕和一個文本框,這個布局文件被活動設置為 View 后,顯示的內容就如上 圖所示,只是行為還沒有實現。
行為將在源代碼文件 TestEvent1.java 中實現,這部分的代碼如下所示:

在創建的過程中,通過 findViewById 獲得各個屏幕上面的控件(控件)的背景,這里使用的 R.id.button1 等和 布局文件中各個元素的 id 是對應的。實際上,在布局文件中,各個控件即使不寫 android:id 這一項也可以正常顯示, 但是如果需要在代碼中進行控制,則必須設置這一項。
根據 Button 控件的 setOnClickListener()設置了其中的點擊行為,這個方法的參數實際上是一個 View.OnClickListener 類型的接口,這個接口需要被實現才能夠使用,因此在本例的設置中,實現了其中的 onClick() 函數。這樣既可實現點擊的時候實現相應的功能,在點擊的函數中,將通過 Text 的句柄對其進行控制。
在 Android 的控件使用方面,這兩個編程方面要點是:
使用findViewById()獲取布局文件(XML)中控件的句柄;
使用setOnXXXListener()設置事件處理函數。 在獲取句柄時需要轉換成相應的控件類型,findViewById()函數的參數是一個整數,返回值是一個
android.view.View 類型。通過 R.id.XXX 找到布局文件中定義的 ID,然后通過將基礎類轉換成其實際的類獲得真正的 句柄。注意:所轉換類必須和布局文件中描述的控件一致。
SetOnXXXListener()等函數是 android.view.View 類的函數,各種控件(包括 Button、EditText)都擴展這個類, 同族的函數包括:


這些函數用於事件處理,它們由程序實現,通過設置這些內容也就設置了控件的行為。這些函數的參數都是所 對應的 android.view.View 類中的方法。
Android 中 UI 基本控制內容:使用 findViewById()聯系布局文件中控件和句柄,並通過 OnClickListener()等定制 句柄的行為。
最后還要提一下視圖組(ViewGroup)和布局(Layout)的使用
在屏幕中控件的組織上,可以將各個視圖(控件)組成一個視圖組(ViewGroup),視圖組是一個包含了 其他視圖的視圖。
android.view.ViewGroup 擴展了 android.view.View,它本身也具有 View 的特性,區別僅在於它可以包含其 他的控件。
ViewGroup 視圖組具有一系列的擴展者:AdapterView、AbsoluteLayout、FrameLayout、LinearLayout、 RelativeLayout、AdapterView<T extends android.widget.Adapter>。
Android GUI 程序的屏幕體系結構的組織遵循以下原則: 一個屏幕可以包含一個視圖;
視圖組本身也是一個視圖;
視圖組可以包含若干個視圖。
Android 視圖和視圖組的關系如圖所示:
如圖所示,外部最大的框表示整個屏幕,其中包含一個視圖組 ViewGroup0,ViewGroup0 包含 3 個子視圖, 即 View1、ViewGroup1、ViewGroup2。ViewGroup1 本身也是視圖組,以水平布局的方式包含了 View2 和 View3; ViewGroup2 本身也是視圖組,以垂直的方式包含了 View4、ViewGroup3 和 ViewGroup4;ViewGroup4 本身也 是視圖組,以水平布局的方式包含了 View5 和 View6。
布局(Layout)
布局(Layout)是各個控件在屏幕上的位置關系,視圖組的幾個擴展類與布局相關。在 Android 中布局通常有以 下幾種不同的情況:
FrameLayout(框架布局):系統默認的在屏幕上就有空白區顯示它;
LinearLayout(線性布局):讓所有的子視圖都成為單一的方向,即垂直的或者水平的; AbsoluteLayout(絕對布局):讓子視圖使用x/y坐標確定在屏幕上的位置;
RelativeLayout(相對布局):讓子視圖的位置和其他的視圖相關;
TableLayout(表單布局):位置是它的子視圖的行或列。
FrameLayout、LinearLayout、RelativeLayout、AbsoluteLayout、TableLayout 都是擴展了 ViewGroup 的類,因此 這些視圖可以用於包含其他的控件,並可以控制其他的控件的位置關系。
布局的內容一般通過在布局文件中控制即可,在控制布局時 android:layout_width 和 android:layout_height 等表示 尺寸屬性,除了使用實際的尺寸值外,還有兩個常用的選項:
"fill_parent":表示能填滿父視圖的最大尺寸;
"wrap_content":表示僅包裹子內容的最小尺寸。 這兩個值既可以在視圖組中使用,也可以在普通視圖中使用,如果在視圖中使用"wrap_content",表示包裹其中
的內容,例如按鈕需要包裹上面的文字。
由於Layout是視圖組的子類,所以實際應用中通常都是使用Layout控制一組視圖

