Android控件與佈局——基礎控件Switch

        最近在用原生的控件和佈局繪製一些界面並使用,雖然這些都是Android基本知識,但是有的時候真的感覺力不從心,感覺有必要對Android常用的控件和佈局做一個系統的瞭解。後續一個月甚至更多的時間都會圍繞這個主題展開,畢竟這裏面還是有不少高級控件的,我也會盡量結合應用深入的進行了解。

上一篇:RatingBar     下一篇:Space

今天,我們的主題是Switch,這個名字看着就很熟悉——開關的意思,下面就先來看看它的官方文檔部分介紹:

* A Switch is a two-state toggle switch widget that can select between two options. The user may drag the "thumb" back * * and forth to choose the selected option, or simply tap to toggle as if it were a checkbox.

它是一種有兩種狀態的可以被選中狀態的控件。用戶可以通過前後拖拽控件上的圖標來選中狀態,或者把它當做一個CheckBox通過點擊來進行狀態選擇。

其實,看到上面的關於“兩種狀態”的說話,我們就會想到之前學過的兩個控件CheckBoxRadioButton;他們都是一種有兩種可選狀態的控件,如果查看源碼,你還會發現,它們都繼承至CompoundButton這個控件。說了這麼多,我們先來Switch究竟長得什麼樣

 <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch1"
            android:thumb="@drawable/seek_bar_thumb"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Switch1" />

這裏,我放置了三個Switch在一個LinearLayout佈局中居中放置了;從動圖中我們可以看到,這個控件的狀態調整確實如上所說有兩種方式,此外,我這裏通過控件的寬度屬性來設置三個控件的寬度不一樣,它們的寬度設置如下:

android:layout_width="wrap_content"
android:layout_width="200dp"
android:layout_width="300dp"

可見,寬度多出來的距離都是文本和圖形之前的距離,這裏面的文本以及文本的屬性的設置和TextView基本一樣,這裏不多介紹,重點的內容我們還是看文檔中說到的:

The {@link #setText(CharSequence) text}
* property controls the text displayed in the label for the switch, whereas the
* {@link #setTextOff(CharSequence) off} and {@link #setTextOn(CharSequence) on} text
* controls the text on the thumb.

通過setText()或者android:text屬性對Switch的label text進行設置,此外,通過setTextOff()和setTextOn()或者一下屬性進行thumb圖標上的文本內容進行設置:

 android:textOn="開"
 android:textOff="關"

設置完之後必須還要設置以下屬性,否則設置的文本無法顯示:

android:showText="true"
       <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch1"
            android:textOn="開"
            android:textOff="關"
            android:showText="true"
            android:text="ShowText=true"
            android:textAllCaps="false"
            android:layout_width="200dp"
            android:layout_height="wrap_content"
             />
        <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch2"
            android:textOn="開"
            android:textOff="關"
            android:textAllCaps="false"
            android:text="ShowText=false"
            android:layout_width="200dp"
            android:layout_height="wrap_content"
            />

好了,關於labelText(左側文本)switchText(thumb文本),官方文檔有這麼一段介紹:

* {@link #setTextAppearance(android.content.Context, int) textAppearance} and the related
* setTypeface() methods control the typeface and style of label text, whereas the
* {@link #setSwitchTextAppearance(android.content.Context, int) switchTextAppearance} and
* the related setSwitchTypeface() methods control that of the thumb.

我們可以通過setTextAppearance()和setSwitchTextAppearance()來對它們的顯示樣式進行介紹,當然也可以通過相關的屬性,至於labelText就和TextView屬性差不多,有size,color,style等等,至於switchText主要還是通過switchTextAppearance屬性來進行設置:

        <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch1"
            android:textOn="開"
            android:textOff="關"
            android:showText="true"
            android:text="ShowText=true"
            android:textAllCaps="false"
            android:layout_width="300dp"
            android:layout_height="wrap_content"
             />
        <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch2"
            android:textOn="開"
            android:textOff="關"
            android:textAllCaps="false"
            android:text="ShowText=false"
            android:textColor="#FF0000"
            android:textSize="25sp"
            android:layout_width="300dp"
            android:layout_height="wrap_content"
            />
 aSwitch1=findViewById(R.id.switch1);
 aSwitch1.setSwitchTextAppearance(this, android.R.style.TextAppearance_DeviceDefault_Large);

從上面我們看到,關於switch由一個text和一個可交互的開關圖標構成,前面對labelText和switchText做了一個簡單的介紹,上面的動圖中我們也看到,switchText字體已經超出邊界了,我們通過設置寬度屬性好像也沒有能改變圖標大小,下面主要來看一下後面的動態圖標部分,如何實現自定義的顯示樣式;在開始之前,我們要搞清楚它的組成部分,先看一張圖,然後實例驗證一下:

實例驗證:

       <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch1"
            android:textOn="開"
            android:textOff="關"
            android:showText="true"
            android:text="ShowText=true"
            android:thumb="@drawable/right_angel"
            android:textAllCaps="false"
            android:layout_width="300dp"
            android:layout_height="wrap_content"
             />
        <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch2"
            android:textOn="開"
            android:textOff="關"
            android:track="@color/colorPrimary"
            android:textAllCaps="false"
            android:text="ShowText=false"
            android:layout_width="300dp"
            android:layout_height="wrap_content"
            />

所以雖然示例很難看,但是很形象的證實了上面我們的總結是正確的,並且可以通過thumb屬性和track屬性來設置開關按鈕的樣式和滑動軌道的樣式,下面我們就結合這個結論,來實現自定義的Switch顯示樣式;結合各個的分析,我們只需要分別創建thumb背景和track背景即可,又因爲它們都是有兩種狀態的,所以這個和我們之前介紹的RadioButton和CheckBox是一樣的。下面爲了編輯方便,我把六個xml編寫的Drawable文件放在一起展示:

//switch_thumb_on.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="oval">
    <solid android:color="#94C5FF" />
    <size
        android:width="40dp"
        android:height="40dp" />
</shape>

//switch_thumb_off.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="oval">
    <solid android:color="#E5E5E5" />
    <size
        android:width="40dp"
        android:height="40dp" />
</shape>

//switch_thumb_back.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item  android:state_checked="true" android:drawable="@drawable/switch_thumb_on"></item>
<item  android:state_checked="false" android:drawable="@drawable/switch_thumb_off"></item>
</selector>

//switch_track_on.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#AEEEEE" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
</shape>

//switch_track_off.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#FCFCFC" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
</shape>

//switch_track_back.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item  android:state_checked="true" android:drawable="@drawable/switch_track_on"></item>
    <item  android:state_checked="false" android:drawable="@drawable/switch_track_off"></item>
</selector>

上面的註釋只是爲了方便,顯示的效果如下:

上面是我們自定義的,下面是系統默認的樣式。可見自定義的效果確實是出來了,但是有幾點和我們預想的不一樣

  • track高度和thumb高度一樣
  • track的寬度沒有到300dp

實際上,thumb的和高度switch以及track的高度始終一樣的,我們可以在track背景中加一個邊框看起來更和諧一些:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#AEEEEE" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
    <stroke android:color="@color/colorPrimary"
        android:width="5dp"></stroke>
</shape>


<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#FCFCFC" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
    <stroke android:width="5dp" android:color="#B5B5B5"></stroke>
</shape>

我們可以通過修改track邊界(這裏剛好可以修改stroke,做了鋪墊的喲)爲透明色或者switch邊界爲透明色來實現默認樣式的效果,比如:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#AEEEEE" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
    <stroke android:color="#00000000"
        android:width="10dp"></stroke>
</shape>

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="#FCFCFC" />
    <corners android:radius="30dp" />
    <size
        android:width="300dp"
        android:height="30dp" />
    <stroke android:width="10dp" android:color="#00000000"></stroke>
</shape>

到這裏第一個問題我們說清楚了,還有一個就是track的寬度不是300dp,當我們對track需求的寬度大於實際的wrap_content時,可以通過設置:

android:switchMinWidth="expWidth"

來實現,比如:

          <Switch
            android:layout_marginTop="10dp"
            android:id="@+id/switch1"
            android:textOn="開"
            android:textOff="關"
            android:showText="true"
            android:switchMinWidth="150dp"
            android:thumb="@drawable/switch_thumb_back"
            android:track="@drawable/switch_track_back"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
             />

好了,到這裏,上面的兩個問題就算解釋清楚了;在實際的使用中,自己可以結合需求設計自己想要的樣式即可。自己也可以到github上搜索一下比較優秀的設計,其實難點在設計,實現都不是太難。關於Switch經常結合業務使用的還有對其狀態的監聽:

 aSwitch1.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if(isChecked){
                   
                }
                else {
                    
                }
            }
        });

我們可以通過上面的接口對其設置CompoundButton.OnCheckedChangeListener()監聽即可。具體的演示這裏就不做了。好了,到這裏關於Switch的作用就介紹到這裏了。

注:歡迎掃碼關注

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章