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

Xamarin动态创建问卷:实现单选按钮互斥选中功能

实现单选按钮组的互斥选中功能

看起来你已经搞定了问卷单选按钮的动态渲染,现在就差同一问题下单选按钮的互斥选中功能了对吧?我给你两个实用方案,你可以根据你的CustomRadioButton实现情况来选:

方案一:利用GroupName属性(推荐,如果你的CustomRadioButton支持)

如果你的CustomRadioButton是基于Xamarin.Forms原生RadioButton扩展的,那原生控件本身就自带GroupName属性——同一组名的单选按钮会自动实现互斥选中。你只需要在创建按钮时,给同一问题下的所有单选按钮设置相同的组名就行:

foreach (var item in Settings.VOCQuestionDetailsSettings.RespondantQuestionnare)
{
    myGrid.Children.Add(new Label { 
        Text = item.Questions, 
        TextColor = Color.Black, 
        HorizontalOptions = LayoutOptions.FillAndExpand, 
        FontAttributes = FontAttributes.Bold 
    }, 0, rowCount);
    rowCount++;

    // 给当前问题设置唯一组名,比如用问题文本的哈希值做标识,确保每组唯一
    var questionGroupName = $"QuestionGroup_{item.Questions.GetHashCode()}";

    for (int i = 0; i < item.Choices.Count; i++)
    {
        if (item.QuestionType == "Radio")
        {
            myGrid.Children.Add(new CustomRadioButton { 
                HorizontalOptions = LayoutOptions.FillAndExpand, 
                VerticalOptions = LayoutOptions.FillAndExpand, 
                Text = item.Choices[i], 
                TextColor = Color.Black, 
                FontSize = 14,
                // 关键:同一问题的单选按钮设置相同GroupName
                GroupName = questionGroupName
            }, 0, rowCount);
            rowCount++;
        }
    }
}

设置完组名后,同一组的单选按钮会自动处理互斥逻辑:选中其中一个时,同组其他按钮会自动取消选中,完全不用额外写事件处理代码。

方案二:手动绑定选中事件处理互斥(如果CustomRadioButton没有GroupName)

如果你的CustomRadioButton没实现GroupName功能,那可以手动给每个按钮添加CheckedChanged事件,当某个按钮被选中时,遍历同一问题下的其他按钮,把它们的IsChecked设为false:

foreach (var item in Settings.VOCQuestionDetailsSettings.RespondantQuestionnare)
{
    myGrid.Children.Add(new Label { 
        Text = item.Questions, 
        TextColor = Color.Black, 
        HorizontalOptions = LayoutOptions.FillAndExpand, 
        FontAttributes = FontAttributes.Bold 
    }, 0, rowCount);
    rowCount++;

    // 先把当前问题的所有单选按钮存到列表里,方便后续批量处理
    List<CustomRadioButton> currentQuestionRadios = new List<CustomRadioButton>();

    for (int i = 0; i < item.Choices.Count; i++)
    {
        if (item.QuestionType == "Radio")
        {
            var radioBtn = new CustomRadioButton { 
                HorizontalOptions = LayoutOptions.FillAndExpand, 
                VerticalOptions = LayoutOptions.FillAndExpand, 
                Text = item.Choices[i], 
                TextColor = Color.Black, 
                FontSize = 14
            };
            // 绑定选中状态变化事件
            radioBtn.CheckedChanged += (sender, e) =>
            {
                if (e.Value) // 只有当前按钮被选中时才处理
                {
                    // 遍历同组其他按钮,取消选中状态
                    foreach (var otherRadio in currentQuestionRadios)
                    {
                        if (otherRadio != sender)
                        {
                            otherRadio.IsChecked = false;
                        }
                    }
                }
            };
            currentQuestionRadios.Add(radioBtn);
            myGrid.Children.Add(radioBtn, 0, rowCount);
            rowCount++;
        }
    }
}

这里要注意:如果你的CustomRadioButton还没暴露IsChecked属性和CheckedChanged事件,得先在自定义控件里补上这些基础功能,示例代码如下:

public class CustomRadioButton : View
{
    // 定义IsChecked绑定属性
    public static readonly BindableProperty IsCheckedProperty =
        BindableProperty.Create(nameof(IsChecked), typeof(bool), typeof(CustomRadioButton), false);

    // 定义Text绑定属性(如果还没实现)
    public static readonly BindableProperty TextProperty =
        BindableProperty.Create(nameof(Text), typeof(string), typeof(CustomRadioButton), string.Empty);

    public bool IsChecked
    {
        get => (bool)GetValue(IsCheckedProperty);
        set => SetValue(IsCheckedProperty, value);
    }

    public string Text
    {
        get => (string)GetValue(TextProperty);
        set => SetValue(TextProperty, value);
    }

    // 定义CheckedChanged事件,用于通知外部状态变化
    public event EventHandler<bool> CheckedChanged;

    // 当IsChecked属性变化时触发事件
    protected override void OnPropertyChanged(string propertyName = null)
    {
        base.OnPropertyChanged(propertyName);
        if (propertyName == IsCheckedProperty.PropertyName)
        {
            CheckedChanged?.Invoke(this, IsChecked);
        }
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.29 07:49:39