12.Spinner下拉列表

Spinner(下拉列表)提供了从一个数据集合中快速选择一项值的办法。

默认情况下Spinner显示的是当前选择的值,点击Spinner会弹出一个包含所有可选值的下拉菜单,从该菜单中可以为Spinner选择一个新值。

下拉列表的展示方式有两种:

一种是在当前下拉框的正下方展示列表,此时把spinnerMode属性设置为dropdown

另一种是在页面中部以对话框形式展示列表,此时把SpinnerMode属性设置为dialog

一、最简单的Spinner

首先新建一个SpinnerTest项目,并让Android Studio自动创建活动。

在布局文件中添加Spinner控件,修改activity_main.xml中的代码,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Spinner
        android:id="@+id/spAnimals"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"/>
</LinearLayout>

1、通过android:entries属性添加数据

首先,修改strings.xml字符串资源文件,使用<string-array>元素来包含一些<item>子元素,用于定义生肖名称。代码如下:

<resources>
    ……
    <string-array name="list_animals">
        <item>子鼠</item>
        <item>丑牛</item>
        <item>寅虎</item>
        <item>卯兔</item>
        <item>辰龙</item>
        <item>巳蛇</item>
    </string-array>
</resources>

在字符串资源文件中,增加<string-array>节点,定义name为list_animals,在该节点下增加<item>项目节点。

然后,修改Spinner控件,增加android:entries属性,属性值为@array/list_animals:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Spinner
        android:id="@+id/spAnimals"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:entries="@array/list_animals" />
</LinearLayout>

运行程序,效果如图显示:

 

2、通过适配器添加数据

首先,删除Spinner控件中的android:entries属性,再修改MainActivity中的代码,如下所示:

import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Spinner;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {
    private String[] animals = {"子鼠", "丑牛", "寅虎", "卯兔", "辰龙", "巳蛇", "午马", "未羊", "申猴", "酉鸡", "戌狗", "亥猪"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        //声明一个下拉列表的数组适配器
        ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_spinner_item, animals);

        //从布局文件中获取名叫spAnimals的下拉框
        Spinner spAnimals = findViewById(R.id.spAnimals);

        //设置下拉框的数组适配器
        spAnimals.setAdapter(adapter);
    }
}

这里使用的还是ArrayAdapter,和ListView用的ArrayAdapter一样。这里由于我们提供的数据都是字符串,因此将ArrayAdapter的泛型指定为String。

然后在ArrayAdapter的构造方法中依次传入当前上下文Spinner子项布局的id,以及要适配的数据。

这里的Spinner子项布局的id是android.R.layout.simple_spinner_item(列表-间距紧凑不好看)。

内置的布局样式还有:

  • android.R.layout.simple_spinner_dropdown_item:列表-间距较高比较好看
  • android.R.layout.simple_list_item_single_choice:单选按钮
  • android.R.layout.simple_list_item_checked:复选框-选中的有绿勾

      

android.R.layout.simple_spinner_item                android.R.layout.simple_spinner_dropdown_item

注意:ArrayAdapter构造方法的第2个参数是指”未展开“时的布局样式,
我们可以通过setDropDownViewResource()方法来指定”展开“时的布局样式。
import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Spinner;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {
    private String[] animals = {"子鼠", "丑牛", "寅虎", "卯兔", "辰龙", "巳蛇", "午马", "未羊", "申猴", "酉鸡", "戌狗", "亥猪"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        //声明一个下拉列表的数组适配器
        ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_spinner_dropdown_item, animals);

        // 设置下拉菜单展开时的样式
        adapter.setDropDownViewResource(android.R.layout.simple_list_item_checked);
        
        //从布局文件中获取名叫spAnimals的下拉框
        Spinner spAnimals = findViewById(R.id.spAnimals);

        //设置下拉框的数组适配器
        spAnimals.setAdapter(adapter);
    }
}

       

二、定制Spinner的界面

1、定制”未展开“和”展开“的样式

未展开样式item_select.xml

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="45dp"
    android:background="@android:color/holo_blue_dark"
    android:gravity="center"
    android:textColor="@android:color/holo_red_light"
    android:textSize="14sp" />

展开样式item_dropdown.xml

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="45dp"
    android:gravity="center"
    android:textColor="@android:color/black"
    android:textSize="14sp" />

修改布局文件activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Spinner
        android:id="@+id/spAnimals"
        android:layout_width="200dp"
        android:layout_height="wrap_content"
        android:layout_gravity="center_horizontal"
        android:background="@null"
        android:dropDownVerticalOffset="45dp"
        android:spinnerMode="dropdown" />
</LinearLayout>

修改MainActivity.java

import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Spinner;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {
    private String[] animals = {"子鼠", "丑牛", "寅虎", "卯兔", "辰龙", "巳蛇", "午马", "未羊", "申猴", "酉鸡", "戌狗", "亥猪"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        //声明一个下拉列表的数组适配器
        ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, R.layout.item_select, animals);

        // 设置下拉菜单展开时的样式
        adapter.setDropDownViewResource(R.layout.item_dropdown);

        //从布局文件中获取名叫spAnimals的下拉框
        Spinner spAnimals = findViewById(R.id.spAnimals);

        //设置下拉框的数组适配器
        spAnimals.setAdapter(adapter);
    }
}

运行效果:

2、Spinner的其他方法

(1)设置下拉框的标题。

只在dialog样式中显示,android:spinnerMode="dialog",如左图;不在dropdown样式下显示,android:spinnerMode="dropdown",如右图。

  • setPrompt(CharSequence prompt):参数为字符串
  • setPromptId(int promptId):参数为字符串的ID,如R.string.xxxx

(2)设置下拉框默认的显示第n项,注意该方法要在setAdapter()方法之后调用

  • setSelection(int position):
  • setSelectionInt(int position, boolean animate) :

    

3、dropdown模式下的列表分割线

在下图①中的位置添加自己的style,在②处进行使用。themes.xml文件可能会提示错误,可能是Android Studio语法检查误判,关闭再打开就好了。

 

在style中添加如下代码即可,打开themes.xml文件。

添加样式:

<style name="XSpinnerStyle" parent="android:Widget.ListView.DropDown">
    <!-- 分隔线颜色 -->
    <item name="android:divider">#3F51B5</item>
    <item name="android:dividerHeight">1dp</item>
</style>

然后在AppTheme中调用:

<item name="android:dropDownListViewStyle">@style/XSpinnerStyle</item>

但注意,该分割线只有是dropdown样式时才会显示。运行结果:

 

三、实现选择项事件

调用setOnItemSelectedListener()方法来为Spinner绑定AdapterView.OnItemSelectedListener事件监听器,可以使用匿名类实现接口的方式。

import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;

import java.util.ArrayList;
import java.util.List;

public class MainActivity extends AppCompatActivity {
    private String[] animals = {"子鼠", "丑牛", "寅虎", "卯兔", "辰龙", "巳蛇", "午马", "未羊", "申猴", "酉鸡", "戌狗", "亥猪"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        //声明一个下拉列表的数组适配器
        ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, R.layout.item_select, animals);

        // 设置下拉菜单展开时的样式
        adapter.setDropDownViewResource(R.layout.item_dropdown);

        //从布局文件中获取名叫spAnimals的下拉框
        Spinner spAnimals = findViewById(R.id.spAnimals);

        //设置下拉框的标题。只在dialog样式中显示,android:spinnerMode="dialog";不在dropdown样式下显示,android:spinnerMode="dropdown"。
        spAnimals.setPrompt("请选择你的生肖"); // 参数为字符串
//        spAnimals.setPromptId(R.string.app_name); // 参数为字符串的ID,如R.string.xxxx

        //设置下拉框的数组适配器
        spAnimals.setAdapter(adapter);

        //设置下拉框默认的显示第一项,注意,该方法要在setAdapter()方法之后调用
        spAnimals.setSelection(1, true);

        //给下拉框设置选择监听器,一旦用户选中某一项,就触发监听器的onItemSelected方法
        spAnimals.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
            @Override
            public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
                // parent:为Spinner控件;view:显示文字的TextView;position:下拉选项的位置从0开始
                Toast.makeText(MainActivity.this, "您选择的是:" + animals[position], Toast.LENGTH_SHORT).show();
            }

            @Override
            public void onNothingSelected(AdapterView<?> parent) {

            }
        });
    }
}

运行结果:

 

posted @ 2022-09-19 16:13  熊猫Panda先生  阅读(1117)  评论(0编辑  收藏  举报