WPF绑定失效问题(规避解决)

使用WPF绑定后台数据,在多次切换数据后绑定失效

将一个后台数据绑定到多个RadioButton的IsChecked上,通过自定义转换将整型数据转换成bool型数据。点击界面上的新增按钮,在button事件中,将绑定的对象数据加1,然后再前台显示,在多次后,前台的RadioButton中会出现某个绑定失败问题。


自定义转换器代码:

#region 方法
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value != null)
            {
                try
                {
                    if (parameter != null)
                    {
                        int par = 0;
                        if (int.TryParse(parameter.ToString(), out par))
                        {
                            return (value as int?).Value - par == 0;
                        }
                        return false;
                    }
                    else
                        return false;
                }
                catch (System.Exception)
                {
                    return false;
                }
            }
            return false;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            try
            {
                if (parameter != null)
                {
                    int par = 0;
                    if (int.TryParse(parameter.ToString(), out par))
                    {
                        if ((bool)value)
                            return par;
                        return null;
                    }
                    return 0;
                }
                else
                {
                    return (bool)value ? 1 : 0;
                }
            }
            catch (System.Exception)
            {

            }
            return null;
        }
        #endregion

XAml代码:

<DockPanel x:Name="grid" LastChildFill="False">
        <DockPanel.DataContext>
            <local:Student/>
        </DockPanel.DataContext>
        <StackPanel DockPanel.Dock="Top" Orientation="Horizontal" HorizontalAlignment="Center" >
            <Button HorizontalAlignment="Center" Width ="60" Height="60" Click="Add_Click" Content="新增"/>
            <Button HorizontalAlignment="Center" Width ="60" Height="60" Click="Delete_Click" Content="删除"/>
        </StackPanel>

        <RadioButton x:Name="rbtn_4" Content="test4" DockPanel.Dock="Top" IsChecked="{Binding Age, ConverterParameter=1, Converter={StaticResource IntToBoolConverter}}" GroupName="test2" Margin="0,10,0,0"/>
        <RadioButton x:Name="rbtn_5" Content="test5" DockPanel.Dock="Top" IsChecked="{Binding Age, ConverterParameter=2, Converter={StaticResource IntToBoolConverter}}" GroupName="test2"/>
        <RadioButton x:Name="rbtn_6" Content="test6" DockPanel.Dock="Top" IsChecked="{Binding Age, ConverterParameter=3, Converter={StaticResource IntToBoolConverter}}" GroupName="test2"/>
        <RadioButton x:Name="rbtn_7" Content="test7" DockPanel.Dock="Top" IsChecked="{Binding Age, ConverterParameter=4, Converter={StaticResource IntToBoolConverter}}" GroupName="test2"/>

        <TextBox DockPanel.Dock="Top" Margin="0,10,0,0" Text="{Binding Age, ConverterParameter=1, Converter={StaticResource IntToBoolConverter}}"></TextBox>
        <TextBox DockPanel.Dock="Top" Margin="0,10,0,0" Text="{Binding Age, ConverterParameter=2, Converter={StaticResource IntToBoolConverter}}"></TextBox>
        <TextBox DockPanel.Dock="Top" Margin="0,10,0,0" Text="{Binding Age, ConverterParameter=3, Converter={StaticResource IntToBoolConverter}}"></TextBox>
        <TextBox DockPanel.Dock="Top" Margin="0,10,0,0" Text="{Binding Age, ConverterParameter=4, Converter={StaticResource IntToBoolConverter}}"></TextBox>
    </DockPanel>

前台代码:

private void Add_Click(object sender, RoutedEventArgs e)
 {
     Student tstd = grid.DataContext as Student;
     tstd.Age = tstd.Age % 4 + 1;
 }

Student:

class Student : INotifyPropertyChanged
    {
        #region 属性
        string name;
        public string Name
        {
            get { return name; }
            set
            {
                name = value;
                if (this.PropertyChanged != null)
                {
                    this.PropertyChanged.Invoke(this, new PropertyChangedEventArgs("Name"));
                }
            }
        }
        public String ID
        {
            set;
            get;
        }
        int age = 1;
        public int Age
        {
            set
            {
                if (value == -1)
                    return;
                age = value;
                if (this.PropertyChanged != null)
                {
                    this.PropertyChanged.Invoke(this, new PropertyChangedEventArgs("Age"));
                }
            }
            get { return age; }
        }

        IP ip = new IP("127.0.0.1");
        public IP IP
        {
            get { return ip; }
            set
            {
                ip = value;
                if (this.PropertyChanged != null)
                {
                    this.PropertyChanged.Invoke(this, new PropertyChangedEventArgs("IP"));
                }
            }
        }
        #endregion

        #region 方法

        public Student Clone()
        {
            Student stu = new Student();
            stu.Name = this.Name;
            stu.Age = this.Age;
            stu.ID = this.ID + 1;
            return stu;
        }
        #endregion

        #region 事件
        #endregion
        public event PropertyChangedEventHandler PropertyChanged;
    }

目前的解决方案是使用CheckBox代替Radiobutton,同时针对CheckBox的Click方法额外处理(禁用Check的取消选中功能)。

private void CheckBox_Click(object sender, RoutedEventArgs e)
  {
      (sender as CheckBox).IsChecked = true;
      e.Handled = true;
  }

多个CheckBox之间的单选性采用绑定到同一个变量来处理(使用到上面的自定义转换器)。

猜测:
单选按钮同一组内按钮的是否选中是关联的,在你选中其中某个项时,底层会将其他选项的IsChecked属性进行更新,此时与绑定冲突照成绑定的失效,而CheckBox是否选中只针对自己。


猜你喜欢

转载自blog.csdn.net/wqq_9/article/details/79805718
今日推荐