選擇框 RadioButton/Check
在學完 Button 之後,我們已經可以和使用者產生一定的互動了,但僅僅這些還遠遠不夠,很多時候我們需要給使用者提供一些選項,比如“記住密碼”、“自動登入”、“投票”等場景,我們需要提供一個或者多個選項給使用者勾選。這種場景下就可以使用 RadioButton 和 Checkbox ,這二者的區別就是前者是單選,而後者支援多選。
1. RadioButton
RadioButton 和 Checkbox 的屬性和用法大體相同,我們先來看看單選框的實現方式。
1.1 RadioButton 的基本用法
當你的 App 需要提供幾個選項讓使用者做單選的時候,RadioButton 毫無疑問是最佳選擇。 RadioButton 需要配合 RadioGroup 一起使用, RadioGroup 可以包含一個或若干個 RadioButton ,每個 RadioButton 對應一個選項可供使用者點選,而一個 RadioGroup 中只有一個 RadioButton 可以進入點選態。比如我們做一個二選一的單選框,佈局程式碼如下:
<RadioGroup xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/group"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="20dp">
<RadioButton
android:id="@+id/rb_male"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="男" />
<RadioButton
android:id="@+id/rb_female"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="女" />
</RadioGroup>
在程式碼中我們設定了一個 RadioGroup ,裡面包含兩個 RadioButton 分別表示“男”、“女”兩個選項,終端使用者只能選擇其一,效果如下:
注意:類似的功能我們還可以用 Spinner View 實現,與之不同的是 Spiner View 只會展示當前選中的選項,其他選項會被收集到下拉列表中,具體的使用我們會在後面的教程中詳細介紹。
1.2 RadioButton 的屬性
如果你執行過上面例子中的程式碼, 會發現預設狀態下兩個選項都沒有選中,但是一旦使用者選擇其中之一就無法在撤銷選擇,只能更改選項,也就是 RadioButton 沒有給我們提供預設選項。我們可以通過android:checked
屬性來實現預設選擇,即 RadioButton 中的android:checked
屬性為 true 的選項會預設被選中,如果有多個 true,那麼只有最後一個被選中。
android:checked="true"
1.3 RadioButton 的排列方式
通過剛剛的例子,我們知道 RadioButton 是需要放到 RadioGroup 當中使用的,所以可以才想 RadioGroup 也是一個 ViewGroup 。沒錯, RadioGroup 是繼承自 LinearLayout 的,所以可以推測 RadioGroup 也有線性佈局的特點,即可以選擇橫向或者縱向。我們按照 LinearLayout 的寫法修改程式碼,在 ViewGroup 中新增方向屬性:
android:orientation="horizontal"
最後執行效果如下:
1.4 獲取 RadioButton 的選中結果
與 EditText 一樣,我們不僅要通過佈局樣式輸出給使用者,還需要得到使用者的輸入資料,對於 RadioButton 而言就是使用者的選項。與 Button 的setOnClickListener
類似,我們通過 RadioGroup 的setOnCheckedChangeListener
介面註冊一個選項變更監聽器,依舊採用上面的佈局,在 Activity 的onCreate()
中增加 Java 程式碼如下:
package com.emercy.myapplication;
import android.app.Activity;
import android.os.Bundle;
import android.widget.RadioGroup;
import android.widget.Toast;
public class MainActivity extends Activity implements RadioGroup.OnCheckedChangeListener {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
RadioGroup radioGroup = findViewById(R.id.group);
radioGroup.setOnCheckedChangeListener(this);
}
@Override
public void onCheckedChanged(RadioGroup group, int checkedId) {
String btText = "";
switch (checkedId) {
case R.id.rb_female:
btText = "性別女";
break;
case R.id.rb_male:
btText = "性別男";
break;
default:
btText = "未選中";
break;
}
Toast.makeText(this, "您選擇了" + btText, Toast.LENGTH_SHORT).show();
}
}
在切換選擇的時候,監聽器就會收到回撥,引數是被選擇的 RadioGroup 及被選擇的 View id,也就是在 xml 中設定的 id。編譯執行,在選項被選擇之後打印出當前的選項,如下:
有兩點需要注意:
- 監聽器是註冊在 RadioGroup 之上的,所以我們需要通過
findViewById
獲取 RadioGroup 而不是 RadioButton 。 - 監聽器傳入的回撥是 RadioGroup 類當中的
OnCheckedChangeListener
介面,所以 Activity 實現的是RadioGroup.OnCheckedChangeListener
介面,與之對應的還有 RadioButton / Checkbox 的父類 CompoundButton 裡也有一個OnCheckedChangeListener
介面,這個會在 Checkbox 的部分講到,注意區分。
2. Checkbox
在學完 RadioButton 之後,Checkbox 就比較好理解了,它可以支援多個選項同時處於選擇狀態,其常用屬性和 RadioButton 一樣,同樣我們可以設定預設被勾選的選項。
2.1 Checkbox 的基本用法
由於不限制選中數量,Checkbox 控制元件不存在類似 RadioGroup 的父容器,我們可以直接在佈局檔案中寫<Checkbox/>
標籤,如下:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/group"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="20dp"
android:orientation="horizontal">
<CheckBox
android:id="@+id/cb_android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:checked="true"
android:text="Android" />
<CheckBox
android:id="@+id/cb_ios"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="iOS" />
</LinearLayout>
我們看到可以有兩個選項同時被選中,和 RadioButton 一樣,通過android:checked
屬性設定預設選中的選項。
2.2 獲取 Checkbox 的選中結果
Checkbox 的選中結果和它的兄弟控制元件 RadioButton 非常類似,通過 CheckBox 的setOnCheckedChangeListener
設定監聽器,在選項被選中或者取消的時候會回撥監聽器的onCheckedChanged
方法,我們基於以上佈局,直接編寫 Activity 程式碼:
package com.emercy.myapplication;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.Toast;
public class MainActivity extends Activity implements CompoundButton.OnCheckedChangeListener {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
CheckBox btAndroid = findViewById(R.id.cb_android);
CheckBox btIOS = findViewById(R.id.cb_ios);
btAndroid.setOnCheckedChangeListener(this);
btIOS.setOnCheckedChangeListener(this);
}
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
String text = isChecked ? "被選中了!" : "被取消了!";
Toast.makeText(this, buttonView.getText() + text, Toast.LENGTH_SHORT).show();
}
}
與 RadioButon 不同的是setOnCheckedChangeListener
介面傳入的是 CompoundButton 類中的OnCheckedChangeListener
,所以 Activity 需要實現CompoundButton.OnCheckedChangeListener
,此方法傳入被選中 / 取消的 Checkbox 物件以及選中的狀態。編譯之後切換選擇,效果如下:
3. 小結
本節我們學習了兩個非常有趣又實用的控制元件——RadioButton / Checkbox,我們學習瞭如何編寫編寫樣式及獲取使用者的選擇結果,並完成了一個簡單的小練習。它們都是派生自 Button,相比 Button 來講使用場景更具體,所以今後在遇到需要選擇的場景,不要忘了這兩個非常好用的控制元件。