繁体   English   中英

在依赖属性 WPF 上使用绑定时出现问题

[英]Problem using a binding on a dependency property WPF

我正在尝试在 CustomView class 上使用 IsHighlighted 依赖项属性。 当我向它传递一个硬布尔值时它按预期工作,但当我向它传递一个绑定时它不起作用。 有谁知道为什么?

我还应该在 IsHighlighted 设置器中调用 OnPropertyChanged 吗?

主窗口.xaml

<StackPanel>

    <!-- The data context is set properly -->
    <TextBlock Text="{Binding Text}" FontSize="50"/>
    
    <!-- This works! -->
    <views:CustomView IsHighlighted="true"/>

    <!-- This does not! -->
    <views:CustomView IsHighlighted="{Binding Path=One}"/>

</StackPanel>

MainWindowViewModel.cs

public class MainWindowViewModel : ViewModelBase
{

    private string _text;

    public string Text
    {
        get { return _text; }
        set { _text = value; }
    }

    private bool _one;

    public bool One
    {
        get { return _one; }
        set { _one = value; }
    }

    public MainWindowViewModel()
    {
        Text = "bound text!";
        One = true;
    }
}

CustomView.xaml

<UserControl>
    <Grid Background="{Binding Path=CurrentBackground, 
                               RelativeSource={RelativeSource FindAncestor, 
                               AncestorType={x:Type local:CustomView}, AncestorLevel=1}}">
        <TextBlock Text="{Binding IsHighlighted}" FontSize="40"/>
    </Grid>
</UserControl>

CustomView.xaml.cs

public partial class CustomView : UserControl
{
    public CustomView()
    {
        InitializeComponent();
        DataContext = this;
    }

    public static readonly DependencyProperty IsHighlightedProperty =
        DependencyProperty.Register(
          name: "IsHighlighted",
          propertyType: typeof(bool),
          ownerType: typeof(CustomView)
        );

    public bool IsHighlighted
    {
        get => (bool)GetValue(IsHighlightedProperty);
        set => SetValue(IsHighlightedProperty, value);
    }

    public Brush CurrentBackground
    {
        get 
        {
            if (IsHighlighted)
                return new SolidColorBrush(Colors.Yellow); // highlighted
            else
                return new SolidColorBrush(Colors.White); // not highlighted
        }
    }


    public event PropertyChangedEventHandler PropertyChanged;

    protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChangedEventHandler handler = this.PropertyChanged;
        if (handler != null)
        {
            var e = new PropertyChangedEventArgs(propertyName);
            handler(this, e);
        }
    }
}

首先删除行DataContext = this; . 用户控件将从他的父级继承DataContext (在这种情况下MainWindow.xaml和上下文将为MainViewModel )。

另一个问题是您正确地将 DataContext 设置为MainWindow 您是否设置了MainWindow.xamlDataContext之类的

this.DataContext = new MainWindowViewModel();

如果没有,请在MainWindow.cs中的某处进行(例如在构造函数中)。 DataContext属性是绑定的默认源。

https://docs.microsoft.com/en-us/dotnet/api/system.windows.frameworkelement.datacontext?view=windowsdesktop-6.0

第二件事是,您需要在MainWindowViewModel One属性设置器中调用PropertyChanged

public bool One
{
    get { return _one; }
    set 
    { 
       _one = value; 
       OnPropertyChanged();
    }
}

我期待您的ViewModelBase正在实现INotifyPropertyChanged接口。 如果没有,您将需要实施它。 在您的情况下,它可以在没有INotifyPropertyChanged实现的情况下工作,因为您在构造函数中设置了One属性。 但是,当您想在 ViewModel 中的某些逻辑中更改此属性时,您需要通知视图One属性正在更改/更改(您将使用 INotifyPropertyChanged 接口实现来完成)。

https://docs.microsoft.com/en-us/dotnet/api/system.componentmodel.inotifypropertychanged?view=net-6.0

Xaml 中对这些代码行的注释。

<Grid Background="{Binding Path=CurrentBackground, 
                           RelativeSource={RelativeSource FindAncestor, 
                           AncestorType={x:Type local:CustomView}, AncestorLevel=1}}">

如何更改背景的更好方法是创建一个 ValueConverter 之类的。

  public class BackgroundConverter : IValueConverter
  {
      public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
      {
         return (bool)value ? new SolidColorBrush(Colors.Yellow) : SolidColorBrush(Colors.White);
      }

      public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
      {
         throw new NotImplementedException();
      }
  }

用法:

<Grid Background="{Binding IsHighlighted, Converter={StaticResource BackgroundConverter}}">

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM