简体   繁体   English

WPF OneWay绑定仅工作一次

[英]WPF OneWay binding works only once

I have a View that have two comboboxes. 我有一个具有两个组合框的视图。 One is where user selects routing pipe type name, and the other where there should be a list of available diameters for the chosen pipe type. 一个是用户选择管路名称的地方,另一个是应该为所选管道类型提供可用直径的列表。

Whenever user selects the pipe type, the other combobox should update the list of available diameters. 每当用户选择管道类型时,另一个组合框应更新可用直径的列表。

AvailableDiameters and RoutingPipeTypeName properties are static in Context class, that implements INotifyPropertyChanged interface. AvailableDiameters和RoutingPipeTypeName属性在Context类中是静态的,该类实现了INotifyPropertyChanged接口。 In xaml I've set the bindings to these properties, in code behind also the DataContext. 在xaml中,我已经在DataContext后面的代码中将绑定设置为这些属性。

The problem is that the list of diameters get's updated only once, when the view is initialized. 问题在于,初始化视图时,直径列表仅更新一次。

When debugging I can see that the properties backing field's values are updated properly when selection on pipe type name is changed, only in the UI the available diameters list is not updated... 调试时,我看到更改管道类型名称的选择时,属性支持字段的值已正确更新,仅在UI中可用直径列表未更新...

Context class: 上下文类:

public class Context : INotifyPropertyChanged
{
    public static Context This { get; set; } = new Context();
    public static string RoutingPipeTypeName
    {
        get => _routingPipeTypeName;
        set
        {
            if (_routingPipeTypeName != value)
            {
                _routingPipeTypeName = value;

               This.OnPropertyChanged(nameof(RoutingPipeTypeName));
            }
        }
    }

    public static List<double> AvailableDiameters
    {
        get => _availableDiameters;
        set
        {
            //check if new list's elements are not equal
            if (!value.All(_availableDiameters.Contains))
            {
                _availableDiameters = value;
                This.OnPropertyChanged(nameof(AvailableDiameters));
            }
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    private void OnPropertyChanged(string propertyName)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}

xaml: XAML:

<ComboBox Width="80" SelectedValue="{Binding Path=RoutingPipeTypeName, Mode=OneWayToSource}">
                    <ComboBoxItem Content="Example pipe type 1"></ComboBoxItem>
                    <ComboBoxItem Content="Example pipe type 2"></ComboBoxItem>
</ComboBox>

<ComboBox Width="80" SelectedValue="{Binding Path=RoutingDiameter, Mode=OneWayToSource}" ItemsSource="{Binding Path=AvailableDiameters, Mode=OneWay}">
                </ComboBox>

code behind: 后面的代码:

public Context AppContext => Context.This;

public MyView()
{
    InitializeComponent();

    Instance = this;
    DataContext = AppContext;
}

And the client class that is responsible for updating the list of diameters: 负责更新直径列表的客户端类:

public void InitializeUIContext()
{
    Context.This.PropertyChanged += UIContextChanged;

    if (Cache.CachedPipeTypes.Count > 0)
        Context.RoutingPipeTypeName = Cache.CachedPipeTypes.First().Key;
}

private void UIContextChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
{
    if (e.PropertyName == nameof(Context.RoutingPipeTypeName))
    {
        Context.AvailableDiameters = Cache.CachedPipeTypes.First().Value.GetAvailableDiameters();
    }
}

I expected such set-up would update the diameters combobox each time the selection is changed on the pipe types property. 我希望每次在管道类型属性上更改选择时,这种设置都会更新直径组合框。 Instead it updates it only once, when the view is initialized... Why? 相反,当视图初始化时,它仅更新一次...为什么?

Do not use static properties for binding to an object (which you have correctly passed to the DataContext of your view). 不要使用静态属性绑定到对象(已正确传递给视图的DataContext的对象)。

Declare the properties without the static modifier and replace This.OnPropertyChanged by OnPropertyChanged : 声明属性,而无需在static修改和替换This.OnPropertyChanged通过OnPropertyChanged

public string RoutingPipeTypeName
{
    get => _routingPipeTypeName;
    set
    {
        if (_routingPipeTypeName != value)
        {
            _routingPipeTypeName = value;
            OnPropertyChanged(nameof(RoutingPipeTypeName));
        }
    }
}

You should also remove the static This from your Context class and simply write 您还应该从Context类中删除static This并简单地编写

public Context AppContext { get; } = new Context();

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

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