You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Xamarin C#:实现MaterialSpinner选中项点击添加至ListView

问题描述

我希望点击assignstaffButton按钮时,将MaterialSpinner中选中的员工名称添加到ListView中。Spinner里的员工名称来自数据库,只需要把选中项添加到ListView即可,但我不知道正确的语法,也不确定是否需要转成字符串。当前代码无法实现需求,求帮助。

附当前Fragment代码和布局文件:

using AdamsonsEDApp.Adapters;
using AdamsonsEDApp.Data_Models;
using AdamsonsEDApp.Helpers;
using AdamsonsEDApp.Listeners;
using Android.App;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Util;
using Android.Views;
using Android.Widget;
using Firebase.Annotations;
using Firebase.Database;
using FR.Ganfra.Materialspinner;
using Java.Util;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using SupportV7 = Android.Support.V7.App;

namespace AdamsonsEDApp.Fragments
{
    public class AssigningStaffFragment : Android.Support.V4.App.DialogFragment
    {
        MaterialSpinner assignstaffnameSpinner;
        Button assignstaffButton, assignstaffregisterButton, assignstaffremoveButton, assignstaffclearButton;
        ImageView exitFragmentButton;
        ListView assignstaffListView;

        
        public override void OnCreate(Bundle savedInstanceState)
        {
            base.OnCreate(savedInstanceState);

            // Create your fragment here
        }

        public override View OnCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
        {
            View view = inflater.Inflate(Resource.Layout.newassignstaff, container, false);
            this.Dialog.SetCanceledOnTouchOutside(false);


            assignstaffnameSpinner = (MaterialSpinner)view.FindViewById(Resource.Id.assignstaffnameSpinner);
            assignstaffButton = (Button)view.FindViewById(Resource.Id.assignstaffButton);
            assignstaffListView = (ListView)view.FindViewById(Resource.Id.assignstaffListView);
            exitFragmentButton = (ImageView)view.FindViewById(Resource.Id.exitfragmentButton);
            assignstaffremoveButton = (Button)view.FindViewById(Resource.Id.assignstaffremoveButton);
            assignstaffclearButton = (Button)view.FindViewById(Resource.Id.assignstaffclearButton);
            assignstaffregisterButton = (Button)view.FindViewById(Resource.Id.assignstaffregisterButton);

            assignstaffListView.ItemClick += AssignstaffListView_ItemClick;
            assignstaffregisterButton.Click += AssignstaffregisterButton_Click;
            assignstaffButton.Click += AssignstaffButton_Click;
            assignstaffremoveButton.Click += AssignstaffremoveButton_Click;
            assignstaffclearButton.Click += AssignstaffclearButton_Click;
            exitFragmentButton.Click += ExitFragmentButton_Click;
            RetrieveStaffNameData();
            return view;
        }

        private void AssignstaffclearButton_Click(object sender, EventArgs e)
        {
            assignstaffListView.clear();
        }

        private void AssignstaffremoveButton_Click(object sender, EventArgs e)
        {
            //remove selected item
        }

        private void AssignstaffListView_ItemClick(object sender, AdapterView.ItemClickEventArgs e)
        {
            //select item 
        }

            //add spinner value to listview
        private void AssignstaffButton_Click(object sender, EventArgs e)
        {
            MaterialSpinner assignstaffspinner = (MaterialSpinner)sender;
            assignstaffListView.Add(assignstaffnameSpinner.GetItemAtPosition(e.Position).ToString());

            if (staffnameadapter != null)
            {
                staffnameadapter.Dispose();
            }
            staffnameadapter = new ArrayAdapter<string>(this.Activity, Android.Resource.Layout.SimpleListItem1, assignstaffListView);
            FindViewById(Resource.Id.assignstaffListView).Adapter = staffnameadapter;
        }

        private void ExitFragmentButton_Click(object sender, EventArgs e)
        {
            this.Dismiss();
        }

        public void SetupStaffNameSpinner()
        {
            staffnameList = new List<string>();

            foreach (var staffname in stafffullnameList)
            {
                staffnameList.Add(staffname.staffFullName);
            }

            staffnameadapter = new ArrayAdapter<string>(Activity, Android.Resource.Layout.SimpleSpinnerDropDownItem, staffnameList);
            staffnameadapter.SetDropDownViewResource(Android.Resource.Layout.SimpleSpinnerDropDownItem);

            assignstaffnameSpinner.Adapter = staffnameadapter;
            assignstaffnameSpinner.ItemSelected += AssignstaffnameSpinner_ItemSelected;
        }

        private void AssignstaffnameSpinner_ItemSelected(object sender, AdapterView.ItemSelectedEventArgs e)
        {
            staffname = staffnameList[e.Position];
        }

        public void RetrieveStaffNameData()
        {
            staffListeners = new StaffListeners();
            staffListeners.Create();
            staffListeners.StaffRetrieved += StaffListeners_StaffRetrieved;
        }

        private void StaffListeners_StaffRetrieved(object sender, StaffListeners.StaffDataEventArgs e)
        {
            stafffullnameList = e.Staffs;
            SetupStaffNameSpinner();
        }
    }
}
</RelativeLayout>

    <View
        android:layout_width="match_parent"
        android:layout_height="1dp"
        android:background="#e2e2e2"/>

    <LinearLayout
        android:padding="16dp"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">

        <fr.ganfra.materialspinner.MaterialSpinner
            android:layout_height="wrap_content"
            android:layout_width="match_parent"
            android:id="@+id/assignstaffnameSpinner"
            app:ms_enableFloatingLabel="true"
            app:ms_floatingLabelText="Select Event"
            app:ms_hint="Select Event"
            app:ms_alignLabels="true"/>

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="horizontal">
            <Button
                android:id="@+id/assignstaffButton"
                android:layout_width="0dp"
                android:layout_height="40dp"
                android:layout_gravity="center_horizontal"
                android:text="ASSIGN"
                android:layout_weight="1"
                android:background="?android:attr/colorPrimary"
                android:textColor="#fff"
                android:layout_margin="10px"
                android:layout_marginTop="20dp"/>

            <Button
                android:id="@+id/assignstaffremoveButton"
                android:layout_width="0dp"
                android:layout_height="40dp"
                android:layout_gravity="center_horizontal"
                android:text="REMOVE"
                android:layout_weight="1"
                android:background="?android:attr/colorPrimary"
                android:textColor="#fff"
                android:layout_margin="10px"
                android:layout_marginTop="20dp"/>

            <Button
                android:id="@+id/assignstaffclearButton"
                android:layout_width="0dp"
                android:layout_height="40dp"
                android:layout_gravity="center_horizontal"
                android:text="CLEAR"
                android:layout_weight="1"
                android:background="?android:attr/colorPrimary"
                android:textColor="#fff"
                android:layout_margin="10px"
                android:layout_marginTop="20dp"/>

            </LinearLayout>
        <ListView
            android:id="@+id/assignstaffListView"
            android:hint="Staff Names"
            android:layout_width="match_parent"
            android:layout_height="300dp"
            android:layout_marginTop="20dp"
            android:textSize="18sp"
            android:background="#edede0"
            android:textColor="#000"/>

        <Button
            android:id="@+id/assignstaffregisterButton"
            android:layout_width="300dp"
            android:layout_height="40dp"
            android:layout_gravity="center_horizontal"
            android:text="REGISTER DETAILS"
            android:background="?android:attr/colorPrimary"
            android:textColor="#fff"
            android:layout_marginTop="20dp"/>
    </LinearLayout>

</LinearLayout>

问题分析

现有代码存在以下关键错误:

  • AssignstaffButton_Click方法错误将按钮(sender)强制转换为MaterialSpinner,实际sender是点击的Button控件
  • 试图直接调用ListView.Add()方法,ListView本身无该方法,必须通过数据源+适配器的方式更新列表
  • 未维护独立的ListView数据源列表,错误将ListView对象传给ArrayAdapter
  • assignstaffListView.clear()方法不存在,ListView清空需通过数据源和适配器完成
  • 类中多个成员变量未声明,导致编译错误

修正后的完整Fragment代码
using AdamsonsEDApp.Adapters;
using AdamsonsEDApp.Data_Models;
using AdamsonsEDApp.Helpers;
using AdamsonsEDApp.Listeners;
using Android.App;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Util;
using Android.Views;
using Android.Widget;
using Firebase.Annotations;
using Firebase.Database;
using FR.Ganfra.Materialspinner;
using Java.Util;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using SupportV7 = Android.Support.V7.App;

namespace AdamsonsEDApp.Fragments
{
    public class AssigningStaffFragment : Android.Support.V4.App.DialogFragment
    {
        // 控件绑定变量
        MaterialSpinner assignstaffnameSpinner;
        Button assignstaffButton, assignstaffregisterButton, assignstaffremoveButton, assignstaffclearButton;
        ImageView exitFragmentButton;
        ListView assignstaffListView;
        
        // ListView专用数据源与适配器
        private List<string> _assignedStaffList;
        private ArrayAdapter<string> _assignedStaffAdapter;
        
        // Spinner相关变量
        private List<string> staffnameList;
        private ArrayAdapter<string> staffnameadapter;
        private List<Staff> stafffullnameList;
        private StaffListeners staffListeners;
        private string staffname;

        public override void OnCreate(Bundle savedInstanceState)
        {
            base.OnCreate(savedInstanceState);
            // 初始化ListView数据源
            _assignedStaffList = new List<string>();
        }

        public override View OnCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
        {
            View view = inflater.Inflate(Resource.Layout.newassignstaff, container, false);
            this.Dialog.SetCanceledOnTouchOutside(false);

            // 绑定控件
            assignstaffnameSpinner = view.FindViewById<MaterialSpinner>(Resource.Id.assignstaffnameSpinner);
            assignstaffButton = view.FindViewById<Button>(Resource.Id.assignstaffButton);
            assignstaffListView = view.FindViewById<ListView>(Resource.Id.assignstaffListView);
            exitFragmentButton = view.FindViewById<ImageView>(Resource.Id.exitfragmentButton);
            assignstaffremoveButton = view.FindViewById<Button>(Resource.Id.assignstaffremoveButton);
            assignstaffclearButton = view.FindViewById<Button>(Resource.Id.assignstaffclearButton);
            assignstaffregisterButton = view.FindViewById<Button>(Resource.Id.assignstaffregisterButton);

            // 初始化ListView适配器并绑定
            _assignedStaffAdapter = new ArrayAdapter<string>(Activity, Android.Resource.Layout.SimpleListItem1, _assignedStaffList);
            assignstaffListView.Adapter = _assignedStaffAdapter;

            // 绑定事件
            assignstaffListView.ItemClick += AssignstaffListView_ItemClick;
            assignstaffregisterButton.Click += AssignstaffregisterButton_Click;
            assignstaffButton.Click += AssignstaffButton_Click;
            assignstaffremoveButton.Click += AssignstaffremoveButton_Click;
            assignstaffclearButton.Click += AssignstaffclearButton_Click;
            exitFragmentButton.Click += ExitFragmentButton_Click;
            
            RetrieveStaffNameData();
            return view;
        }

        private void AssignstaffclearButton_Click(object sender, EventArgs e)
        {
            // 清空数据源并通知适配器更新UI
            _assignedStaffList.Clear();
            _assignedStaffAdapter.NotifyDataSetChanged();
        }

        private void AssignstaffremoveButton_Click(object sender, EventArgs e)
        {
            // 获取选中项位置,无效则不执行
            int selectedPosition = assignstaffListView.CheckedItemPosition;
            if (selectedPosition != ListView.InvalidPosition)
            {
                _assignedStaffList.RemoveAt(selectedPosition);
                _assignedStaffAdapter.NotifyDataSetChanged();
                assignstaffListView.SetItemChecked(selectedPosition, false);
            }
        }

        private void AssignstaffListView_ItemClick(object sender, AdapterView.ItemClickEventArgs e)
        {
            // 设置点击项为选中状态,方便后续移除操作
            assignstaffListView.SetItemChecked(e.Position, true);
        }

        // 将Spinner选中项添加到ListView
        private void AssignstaffButton_Click(object sender, EventArgs e)
        {
            int selectedPosition = assignstaffnameSpinner.SelectedItemPosition;
            // 校验选中位置有效性
            if (selectedPosition != Spinner.InvalidPosition)
            {
                string selectedStaffName = staffnameList[selectedPosition];
                // 避免重复添加
                if (!_assignedStaffList.Contains(selectedStaffName))
                {
                    _assignedStaffList.Add(selectedStaffName);
                    // 通知适配器更新UI
                    _assignedStaffAdapter.NotifyDataSetChanged();
                }
            }
        }

        private void ExitFragmentButton_Click(object sender, EventArgs e)
        {
            this.Dismiss();
        }

        public void SetupStaffNameSpinner()
        {
            staffnameList = new List<string>();

            foreach (var staffname in stafffullnameList)
            {
                staffnameList.Add(staffname.staffFullName);
            }

            staffnameadapter = new ArrayAdapter<string>(Activity, Android.Resource.Layout.SimpleSpinnerDropDownItem, staffnameList);
            staffnameadapter.SetDropDownViewResource(Android.Resource.Layout.SimpleSpinnerDropDownItem);

            assignstaffnameSpinner.Adapter = staffnameadapter;
            assignstaffnameSpinner.ItemSelected += AssignstaffnameSpinner_ItemSelected;
        }

        private void AssignstaffnameSpinner_ItemSelected(object sender, AdapterView.ItemSelectedEventArgs e)
        {
            staffname = staffnameList[e.Position];
        }

        public void RetrieveStaffNameData()
        {
            staffListeners = new StaffListeners();
            staffListeners.Create();
            staffListeners.StaffRetrieved += StaffListeners_StaffRetrieved;
        }

        private void StaffListeners_StaffRetrieved(object sender, StaffListeners.StaffDataEventArgs e)
        {
            stafffullnameList = e.Staffs;
            SetupStaffNameSpinner();
        }

        private void AssignstaffregisterButton_Click(object sender, EventArgs e)
        {
            // 可在此实现提交选中员工数据到数据库的逻辑
        }
    }
}

关键修改说明
  1. 新增ListView专用数据源:添加_assignedStaffList作为ListView的数据源,_assignedStaffAdapter作为对应适配器,初始化时绑定到ListView
  2. 修正Assign按钮逻辑:
    • 从assignstaffnameSpinner直接获取选中位置,不再错误转换sender
    • 直接从staffnameList取选中的字符串(无需额外转换,Spinner数据源本身就是字符串列表)
    • 添加数据到数据源后,调用NotifyDataSetChanged()通知UI更新
    • 增加重复判断,避免同一员工被多次添加
  3. 完善清空/移除功能:通过操作数据源+通知适配器的方式实现列表清空和选中项移除
  4. 补充成员变量声明:添加所有缺失的类成员变量,确保代码可编译

内容的提问来源于stack exchange,提问作者Zeno

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 14:20:35