環境設定
- Android Studio 2.1.1
- Android 版本設定在 N preview
- Activity 則為了簡單,選擇了 "Empty Activity" ,如下圖

期望達成功能
- 在 Main Activity 的畫面中加上一個按鈕
- 在 Java 檔案中接取按鈕的點擊事件
- 接到點擊事件後在畫面上顯示一個簡單的訊息提示,這裡會使用
Toast
這個 UI 元件
建立專案
實作開始
開專案時,除了名字自訂之外,其他的像是 activity name 等等的,為了簡化實作過程,先照著預設的設定即可,也就是 "Main Activity"。
加上一個按鈕
按鈕要加在 activity_main.xml
這個檔案中,雖然專案開起來時預設就會開著了,如果沒找到的話,可以在左邊的目錄循著下面寫的路徑找到:
app/res/layout/activity_main.xml
移除預設的內容
預設會有一個內容是 "Hello World!" 的 TextView 在裡面,內容如下
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello World!" />
直接把這一段移除
加上按鈕標籤
加上以下的標籤
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
Android xml 檔案輸入的方式與基本屬性的含義
先輸入 <Button
,就會開始跳出候選清單,接著按下鍵盤 Tab 鍵,就會自動完成下面這一段程式碼:
<Button
android:layout_width=""
android:layout_height="" />
接著在兩個引號我就都選 wrap_content
,字意上是「包覆內容」,意思就是「根據內容」決定該參數的值會是多少。
以這個按鈕的話就是指:
- 按鈕的 寬度 就是 內容 的 最大寬度
- 按鈕的 高度 就是 內容 的 最大高度
這兩個屬性則是 Android UI 元件的必填屬性。
而這兩個屬性的前綴 android
意思就是:「這個屬性是 android 自己內建的」,算是有點 namespace (命名空間)的味道吧!
這個屬性還有一個值是 match_parent
,意思則是指被設定到的屬性,需要填滿自己所在的父容器。換句話說,如果設定一個 UI 元件的寬度是 match_parent
的話,它的寬度就會像是在 css 裡面把畫面寬度這樣設定 width: 100%;
。
設定按鈕文字
這時候按下 Run, 或是快捷鍵 Ctrl+R ,接著選定模擬器或是實體裝置,就可以執行這個 app 了。
這時候就會發現按鈕上面空空的,接著就來設定文字。
在按鈕裡面要設定文字內容,要使用以下這個屬性
android:text
一開始我寫死,直接設定一個字串,像是這樣:
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text = "我的按鈕"
/>
這時候 Android Studio 就會抱怨了,畫上底色,說這樣寫不好,會造成以下影響
- 當要建立不同尺寸的畫面時,必須要重新設定這個字串
- 對多國語言設定會有不良影響
於是說要在 string resource 裡面設定會比較好。
要設定這個字串的話,有兩種方式:
- 直接開啟
app/res/values/strings.xml
在裡面新增字串設定 - 使用 Android Studio 的自動抽離功能 (automatically extract) ,把指定字串加入第一點提到的
strings.xml
這個檔案裡
手動加入字串設定
這時候點兩下開啟 app/res/values/strings.xml
這個檔案,當開新的專案時只會有一個 app name 的設定:
<resources>
<string name="app_name">ButtonBasic</string>
</resources>
app_name
設定的字串會跟專案名稱不同而改變
接著在他的下一行加上這段
<string name="buttonText">我的按鈕</string>
把這個字串的名稱從簡先設定成 buttonText
,把內容設定成 我的按鈕
。這邊設定的 buttonText
,可以讓我們用這個 resource ID 在 UI 的 xml 裡面設定之後,顯示出來的文字就會是「我的按鈕」。
更新 UI 的 xml 檔案
接著回到 activity_main.xml
,把剛剛打的字串,換成 buttonText
這個 resource ID :
android:text="@string/buttonText"
Resource ID
在 Android 官方的文件裡面是用這個詞來表示這一類參照資源用的 ID 。
@string
這是 Android 在 xml 裡面用來指定 string resource 的 syntax , 編譯器會幫忙根據 /
後面的 id 找到指定的字串後,轉成 String
物件後,讓指定的 UI 可以把預期中的字串顯示出來。 (String Resource 的 官方文件說明)
使用 Automatically Extract - 自動抽離功能
Automatically extract 提供了一些使用者介面,來快速方便的達成建立 string resource 的這個目的。當建立完 resource ID 後, Android Studio 還會幫忙把原本寫死的字串直接換成 resource ID ,非常的方便。
1. 選取寫死的字串,接著按下快捷鍵 Alt+Enter
如下圖:

接著點選 Extract string resource
2. 設定 Resource ID
如下圖:

在這邊除了輸入資源名稱,其他參數沒有調整維持預設,接著點下 OK
3. 完成
這時候就會發現原本的字串被替換成使用 string resource 的格式:

這時候如果去在前面一段有提到的 strings.xml
查看的話,也會看到這個檔案被新增了一行設定,原本輸入寫死的字串「我的按鈕」,也直接被設定成這個 string resource 的值:
<string name="buttonText">我的按鈕</string>
目前為止的成果:

設定按鈕的事件
拉回按鈕設定,接著要把 xml 和 Java 連結在一起了。
Button
有個屬性是叫 android:onClick
,是用來指定當按鈕被按的時候會呼叫對應到的 activity 中的 method 。
新增後,我們先指定我們要呼叫的 method 是 buttonOnClick
,這裡的名字是可以任意的,等一下我們就會需要在 MainActivity 這個 class 裡面新增這個 method 。
我們的 Button
設定發展到這個樣子:
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/buttonText"
android:onClick="buttonOnClick"
/>
這時候會發現 buttonOnClick
被上了底色,是因為 Android Studio 有檢查到對應的 activity - 這邊就是指 MainActivity
裡面沒有名為 buttonOnClick
的 method 。
新增反應點擊事件的 Method
接著開啟 MainActivity.java
,位置在左側目錄中 app/java/[你的專案 module id]/MainActivity
在原本的 onCreate
的下方,新增一個 method :
// ... 前略
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
void buttonOnClick(View view) {
}
}
- 這時候打完
View
的時候, Android Studio 會提醒我們需要引入這個 class ,接著只需要按下 Alt+Enter 即可自動在檔案的最前面幫忙引入,而不用自己手打出來。 - 為什麼需要加上
View view
這個參數?
- 因為這個按鈕並沒有透過
findViewById
並在這個 class 中用一個變數存起來,但是我們又必須要有辦法存取觸發這個 method 的 Button ,所以才需要這個 view 。
我都知道他是 Button 了,參數類別可以改成 Button 嗎?
不行。
當改成
void buttonOnClick(Button button) {
}
的時候,
只要按下按鈕, app 就會 crash ,說明他找不到 buttonOnClick(View)
這個東西,因此看起來,他只接受參數型態是 View
的 method 。
因此,如果要使用這個按鈕的話,可以這樣做,轉型後用一個 local 變數存起來:
void buttonOnClick(View view) {
Button button = (Button) view;
}
這邊因為不會需要對按鈕做任何操作,因此這個 method 先留空白就好。
這時候重新 Run 之後,點下去不會有任何視覺上的反應。
接下來要在按鈕按下觸發的 method 中,加上一段程式碼,讓 app 可以跳出一個 Toast
反饋。
新增 Toast 物件
Android 的 Toast 是一個會在畫面下半部出現的一個暫時性質的 UI 元件,他的功能基本上是拿來顯示給使用者簡要的提示訊息。
建立一個 Toast 物件:
void buttonOnClick(View view) {
Toast toast = Toast.makeText(this, "按鈕已經被點擊", Toast.LENGTH_SHORT);
}
這裡使用了 Toast 的 makeText
method 來產生我們要顯示的 Toast 物件。它包含了三個參數:
參數 1
、這個 Toast 物件要顯示的環境:在這裡就是指我們當下的 Main Activity 物件,所以帶入 this
代表是自己這個物件
參數 2
、要顯示的字串,這邊寫死一個字串在這邊。由於這個 method 的第二個參數可以接 id 也可以接字串,因此這樣寫 Android Studio 不會畫重點警告。
參數 3
、這個 Toast 物件該顯示的時間,一定要設定為 Toast.LENGTH_SHORT
或是 Toast.LENGTH_LONG
的其中一個。
使用 String Resource
就像上一個大部分裡面有提到寫死字串是不好的,因此這裡也來把字串轉換成 string resource 並用 resource ID 取用。
在這邊我把它叫做 buttonOnClickMessage
,名字一樣是可以自選。
和 xml 不同的是,在 java 檔案裡面並不是用 @string/
作為前綴,而是透過 R.string.
再加上 resource ID 來取用 string resource 。
因此,我們建立一個 Toast 物件的程式碼就變成這樣:
Toast toast = Toast.makeText(this, R.string.buttonOnClickMessage, Toast.LENGTH_SHORT);
R 是什麼東西?
R
是一個特殊的 class , 是在專案被編譯過後,由 aapt
(Android Asset Packaging Tool) 打包資源後所產生的的一個類別。
每一個資源一定會由兩個部分所組成, 資源的種類 和 資源的名稱 (resource type, resource name)。
格式會是如此
R.[resource type].[resource name]
就像目前有用到的 string
,每一種不同的 resource ,就會被群組成一個 type ,接著再由 resource name 或是 resource ID 存取想要的資源。
以目前用到的程式碼來說,就是從 aapt 打包出來的 R
class 取用叫做 string
的這個 type 中, name 是 buttonOnClickMessage
對應到的資源:
R.string.buttonOnClickMessage
顯示 Toast 物件
顯示這個 Toast 物件很簡單,直接呼叫 .show()
method 即可:
void buttonOnClick(View view) {
Toast toast = Toast.makeText(this, R.string.buttonOnClickMessage, Toast.LENGTH_SHORT);
toast.show();
}
最後這個 onClick
事件所呼叫的 method 就如上面的程式碼。
這時候再 Run 或 Debug 一次,點擊按鈕之後,就會看到最下面如預期般的跳出剛剛新增並顯示的 Toast 物件:
