2009-09-13 77 views
1

我有一个单选按钮组:数据绑定单选按钮组属性

<TextBlock Height="24" Text="Update Interval (min):"/> 
<RadioButton x:Name="radioButtonTimerNone" IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, Mode=TwoWay}"} Content="None" /> 
<RadioButton x:Name="radioButtonTimerOne" IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, Mode=TwoWay}" 
       Content="1" /> 
<RadioButton x:Name="radioButtonTimerFive" IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, Mode=TwoWay}" 
       Content="5" /> 

和属性:

public int UpdateInterval { 
     get { return _updateInterval; } 
     set { _updateInterval = value; 
      onPropertyChanged("UpdateInterval"); 
     } 
    } 

如何将单选按钮绑定到属性,所以radioButtonTimerNone检查时UpdateInterval为0 ,当UpdateInterval是1时检查radioButtonTimerOne等。
我试图创建一个转换器,但它不能识别正在设置哪个rb:

[ValueConversion(typeof(RadioButton), typeof(bool))] 
class UpdateIntervalToCheckedConverter : System.Windows.Data.IValueConverter 
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 

我预计'价值'是一个单选按钮,但它似乎是UpdateInterval的值。

感谢您的任何提示...

回答

1

您的值转换器不会被告知该单选按钮改变了价值 - 所有绑定都知道的是,“器isChecked”属性已更改,所以针对该器isChecked新价值它唯一可以告诉转换器的东西。

是弹簧我首先想到的是提供与每个绑定的转换器参数:对“转换”的方法

<RadioButton 
    x:Name="radioButtonTimerNone" 
    IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, ConverterParameter=0, Mode=TwoWay}" 
    Content="None" /> 
<RadioButton 
    x:Name="radioButtonTimerOne" 
    IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, ConverterParameter=1, Mode=TwoWay}" 
    Content="1" /> 
<RadioButton 
    x:Name="radioButtonTimerFive" 
    IsChecked="{Binding UpdateInterval, Converter={StaticResource updateIntervalToCheckedConverter}, ConverterParameter=5, Mode=TwoWay}" 
    Content="5" /> 

所以,现在的“参数”参数将具有值“0 “,”1“或”5“,具体取决于选中哪个RadioButton。我认为,虽然我不确定,参数将是字符串类型,所以您可能不得不在考虑该值时考虑到这一点。

+0

谢谢,我已经得到它使用您的建议工作。虽然看起来不是很干净,但必须通过本质上是我想要绑定到属性的控制ID。 – Number8 2009-09-13 23:12:15

+0

是的,我不知道是否有一个“更清洁”的解决方案。我并不是一般价值转换者的忠实粉丝,但是如果你必须使用一个,那么ConverterParameter可以让你的生活变得更轻松! – 2009-09-13 23:35:51

+0

这是我选择的解决方案。虽然它不是很干净,但我一般都比Anderson在ViewModel上有很多属性的解决方案更好。但是,我想这是因为我不太喜欢让我的ViewModel迎合视图,因此我可以支持结构化蒙皮。 – dustyburwell 2009-09-14 05:05:39

2

如果你使用MVVM并绑定到ViewModel(我猜你是),我通常认为我的ViewModel是一个很大的ValueConverter。为什么不把这个逻辑放到每个属性中?

这里是其中的一个示例:

public bool Timer5Enabled 
{ 
    get { return UpdateInterval == 5; } 
} 

然后你只绑​​定到:

<RadioButton 
    x:Name="radioButtonTimerOne" 
    IsChecked="{Binding Timer5Enabled, Mode=OneWay}" 
    Content="1" /> 

你需要修改的东西将是你的领带间隔更新逻辑,以提高OnChanged您的相关属性:

public int UpdateInterval { 
     get { return _updateInterval; } 
     set { _updateInterval = value; 
      onPropertyChanged("UpdateInterval"); 
      onPropertyChanged("Timer5Enabled"); 
      onPropertyChanged("..."); 
     } 
    } 

ValueConverters是很好的避免,如果你能够。

0

您可以考虑以不同的时间间隔使用List<...>。列表类型应该最好是一些自定义类型(例如UpdateInterval)或KeyValuePair<K,V>以将显示给用户的内容与实际值分开。

然后你可以有一个ListBox绑定到这个列表,并且每个ListBoxItem的模板显示RadioButton。然后,在模板中,将单选按钮的IsChecked绑定到ListBoxItem.IsSelected

最后一个触摸只是将您的财产绑定到ListBoxSelectedItemSelectedValue

0

这对我来说是一个非常烦人的问题。

当您将多个RadioButton分配给同一个GroupName时,WPF RadioButton类有一个错误消除了IsChecked属性的绑定。人们已经做了很多工作,但是当我不得不再次访问它时,我想出了一个不会使我感到恶心的东西。

所以,你必须做的是继承与此RadioButton类:

public class RadioButton: System.Windows.Controls.RadioButton 
{ 
    protected override void OnClick() 
    { 
     base.OnClick(); 

     SetValue(CurrentValueProperty,CheckedValue); 
    } 

    public int CurrentValue 
    { 
     get { return (int)GetValue(CurrentValueProperty); } 
     set { SetValue(CurrentValueProperty, value); } 
    } 

    // Using a DependencyProperty as the backing store for CurrentValue. This enables animation, styling, binding, etc... 
    public static readonly DependencyProperty CurrentValueProperty = 
     DependencyProperty.Register("CurrentValue", typeof(int), typeof(RadioButton), new FrameworkPropertyMetadata(0,FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, CurrentValue_Changed)); 

    public static void CurrentValue_Changed(object sender, DependencyPropertyChangedEventArgs e) 
    { 
     ((RadioButton)sender).IsChecked = ((RadioButton)sender).CurrentValue == ((RadioButton)sender).CheckedValue; 
    } 

    public int CheckedValue 
    { 
     get { return (int)GetValue(CheckedValueProperty); } 
     set { SetValue(CheckedValueProperty, value); } 
    } 

    // Using a DependencyProperty as the backing store for CheckedValue. This enables animation, styling, binding, etc... 
    public static readonly DependencyProperty CheckedValueProperty = 
     DependencyProperty.Register("CheckedValue", typeof(int), typeof(RadioButton), new UIPropertyMetadata(0)); 
} 

这样做只是添加两个依赖属性,所以你可以做一个相等比较。如果你发现你要做的就是 1)结合CurrentValue的财产 2)设置的CheckedValue属性,将使该值

<UserControl x:Class="MyClass" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:c="clr-namespace:MVVMLibrary;assembly=MVVMLibrary" 
    Height="Auto" Width="Auto"> 

      <c:RadioButton CurrentValue="{Binding MyValue}" CheckedValue="1" GroupName="SearchType" >Value 1</c:RadioButton> 
      <c:RadioButton Grid.Column="1" CurrentValue="{Binding MyValue}" CheckedValue="2" GroupName="SearchType" >Value 2</c:RadioButton> 
    </UserControl> 

所以:

所以在XAML的例子是这个RadioButton checked 3)将RadioButtons设置为相同的GroupName

如果您发现我制作了CurrentValue和CheckedValue int类型。我这样做的原因是,你可以将CurrentValue绑定到一个枚举。我认为这很棒,但这只是我的看法,可能不算太多。 :)

希望这可以帮助别人。

0

一种可能性是实施的IValueConverter并配置它传递的预期枚举值,每单选按钮,你需要绑定,正如我在我的博客中描述here