C# 在 MVVM 之后从 WPF 中的组框中确定选中的单选按钮

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/18616721/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-10 12:45:44  来源:igfitidea点击:

Determining checked Radiobutton from groupbox in WPF following MVVM

c#wpfmvvmradio-buttongroupbox

提问by Bhramar

I have a groupbox with some radiobuttons. How do I get to know which one which is checked? I am using WPF and following MVVM.

我有一个带有一些单选按钮的分组框。我如何知道哪个被检查了?我正在使用 WPF 并遵循 MVVM。

<GroupBox Name="grpbx_pagerange" Header="Print Range">
    <Grid >
        <RadioButton Name="radbtn_all" Content="All Pages" GroupName="radios_page_range" IsChecked="True"  />
        <RadioButton x:Name="radbtn_curr" Content="Current Page" GroupName="radios_page_range"  />
        <RadioButton Name="radbtn_pages" Content="Page Range" GroupName="radios_page_range" />

        ....

</GroupBox>

Now, one way I could figure out was to bind each RadioButton's IsCheckedProperty to some property in ViewModel and then do if..else sort of logic in my ViewModel to figure out the selected radiobutton.

现在,我能找到的一种方法是将每个 RadioButton 的IsChecked属性绑定到 ViewModel 中的某个属性,然后在我的 ViewModel 中执行 if..else 类逻辑来找出所选的单选按钮。

But Is there any other elegant way?

但是还有其他优雅的方式吗?

采纳答案by Nitin

you can bind RadioButton.Commandof Radiobuttons to a command of your ViewModel and send a unique CommandParameter to identify which button has called the command in commandhandler.

您可以将RadioButton.CommandRadiobuttons绑定到 ViewModel 的命令,并发送一个唯一的 CommandParameter 来标识哪个按钮调用了 commandhandler 中的命令。

<RadioButton Command="{Binding MyCommand}" CommandParameter="Radio1"/>
<RadioButton Command="{Binding MyCommand}" CommandParameter="Radio2"/>
<RadioButton Command="{Binding MyCommand}" CommandParameter="Radio3"/>

in command handler check for parameter to identify the radiobutton.

在命令处理程序中检查参数以识别单选按钮。

Thanks

谢谢

回答by Sheridan

You can create an enumthat contains the values of the RadioButtonobjects as names (roughly) and then bind the IsCheckedproperty to a property of the type of this enumusing an EnumToBoolConverter.

您可以创建一个enum包含的值RadioButton对象姓名(大约),然后绑定IsChecked属性的这种类型的属性enum使用EnumToBoolConverter

public enum Options
{
    All, Current, Range
}

Then in your view model or code behind:

然后在您的视图模型或代码后面:

private Options options = Options.All; // set your default value here

public Options Options
{ 
    get { return options; }
    set { options = value; NotifyPropertyChanged("Options"); }
}

Add the Converter:

添加Converter

[ValueConversion(typeof(Enum), typeof(bool))]
public class EnumToBoolConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value == null || parameter == null) return false;
        string enumValue = value.ToString();
        string targetValue = parameter.ToString();
        bool outputValue = enumValue.Equals(targetValue, StringComparison.InvariantCultureIgnoreCase);
        return outputValue;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value == null || parameter == null) return null;
        bool useValue = (bool)value;
        string targetValue = parameter.ToString();
        if (useValue) return Enum.Parse(targetType, targetValue);
        return null;
    }
}

Then finally, add the bindings in the UI, setting the appropriate ConverterParameter:

最后,在 UI 中添加绑定,设置适当的ConverterParameter

<RadioButton Content="All Pages" IsChecked="{Binding Options, Converter={
    StaticResource EnumToBoolConverter}, ConverterParameter=All}" />
<RadioButton Content="Current Page" IsChecked="{Binding Options, Converter={
    StaticResource EnumToBoolConverter}, ConverterParameter=Current}" />
<RadioButton Content="Page Range" IsChecked="{Binding Options, Converter={
    StaticResource EnumToBoolConverter}, ConverterParameter=Range}" />

Now you can tell which is set by looking at the Optionsvariable in your view model or code behind. You'll also be able to set the checked RadioButtonby setting the Optionsproperty.

现在,您可以通过Options查看视图模型中的变量或后面的代码来判断哪个设置。您还可以RadioButton通过设置Options属性来设置已选中。

回答by user1513659

I got same problem and i solved by removing "GroupName" Property from Radiobutton.

我遇到了同样的问题,我通过从 Radiobutton 中删除“GroupName”属性来解决。

Please remove "GroupName" Property from all radio buttons. and check

请从所有单选按钮中删除“GroupName”属性。并检查

回答by HelpMatters

There is another MVVM way to solve this using IsChecked Property

还有另一种 MVVM 方法可以使用 IsChecked 属性解决此问题

Here's the XAML

这是 XAML

<Page>
<Page.Resources>
<DataTemplate x:Key="ChoiceItemTemplate">
<RadioButton Content="{Binding individualRadioButtonText}"
     IsTabStop="True"
     GroupName="choice"
     IsChecked="{Binding IsChecked, Mode=TwoWay}"/>
 </DataTemplate>
</Page.Resources>


 <StackPanel>
  <TextBlock Text="{Binding ChoiceQuestion}" />
 <ItemsControl  ItemsSource="{Binding ListOfAnswerOptions}"
                ItemTemplate="{StaticResource ChoiceItemTemplate}" />
 </StackPanel>
</Page>

Your model will be something like this

你的模型将是这样的

 public class RadioButtonQuestion
 {
    public string ChoiceQuestion { get; set; }
    public string answer { get; set; }
    public List<AnswerOption> ListOfAnswerOptions { get; set; }
 }

 public class AnswerOption
 {
    public string individualRadioButtonText { get; set; }
    public bool IsChecked { get; set; }
 }

ViewModel will look something like this (The selection logic)

ViewModel 看起来像这样(选择逻辑)

RadioButtonQuestion r = new RadioButtonQuestion();
var selectedElement = rbuttonQuestion.answerOptions.FirstOrDefault(c => c.IsChecked);
r.answer = selectedElement.individualRadioButtonText;

So if you set the datacontext of the view to this viewmodel. You must be able to get it to work.

因此,如果您将视图的数据上下文设置为此视图模型。你必须能够让它工作。

Hope it helps.

希望能帮助到你。

回答by victor

If you use Tag property on options buttons (boolean, integer, strings) like in his XAML

如果您在选项按钮(布尔值、整数、字符串)上使用 Tag 属性,就像在他的 XAML 中一样

<StackPanel Orientation="Horizontal" Margin="10,10, 0, 0">
    <RadioButton Name="rP0" Content="Low  " Tag="0" />
    <RadioButton Name="rP1" Content="Normal" Tag="1" IsChecked="True" />
    <RadioButton Name="rP2" Content="Medium" Tag="2" />
    <RadioButton Name="rP3" Content="High" Tag="3" />
</StackPanel>

Then you can use following function to get selected value (button)

然后你可以使用以下函数来获取选定的值(按钮)

int priority = SelectedRadioValue<int>(0, rP0, rP1, rP2, rP3);

where

在哪里

public T SelectedRadioValue<T>(T defaultValue, params RadioButton[] buttons)
{
    foreach (RadioButton button in buttons)
    {
        if (button.IsChecked == true)
        {
            if (button.Tag is string && typeof(T) != typeof(string))
            {
                string value = (string) button.Tag;
                return (T) Convert.ChangeType(value, typeof(T));
            }

            return (T)button.Tag;
        }
    }

    return defaultValue;
}