绑定并更新静态属性

本文关键字:属性 静态 更新 绑定 | 更新日期: 2023-09-27 18:15:27

我搜索了谷歌的解决方案,但我不能应用我发现我的问题在这里,所以我有一个静态类与静态属性,我希望绑定一个ListView静态属性到一个ObservableCollection属性,这是完成的,但现在我想通知ListView与变化发生在ObservableCollection

 public static class Global
{
   public static ObservableCollection<Dictionary<string,Dictionary<string,object>>> operations;
   ObservableCollection<String> names = new ObservableCollection<string>();
   public static ObservableCollection<String> _Operations
   {
       get
       {               
           for (int i = 0; i < Global.operations.Count; i++)
           {
               if (Global.operations.Count != 0)
               {
                   names.Add(Global.operations[i].Keys.First().ToString());
               }
           }
           return names;
       }
       set
       {
           if (_Operations != value)
           {
               _Operations = value;
           }
       }
   }
}

然后是XAML

<ListView Name="list"  ItemsSource="{Binding Source={x:Static s:Global._Operations}}">
        <ListView.ItemTemplate>
            <DataTemplate>
                <StackPanel Orientation="Horizontal">
                <TextBlock Text="{Binding }"  />
                    <Button Content="Delete" Click="Button_Click"/>
                </StackPanel>
            </DataTemplate>
        </ListView.ItemTemplate>
        </ListView>

这是用于删除的代码,我确信它是添加和删除的,因为我可以立即看到"Operation"被添加或删除的效果

var item = ((Button)sender).DataContext;
        var itemIndex = list.Items.IndexOf(item);
        Global.operations.RemoveAt(itemIndex);
        list.Items.Refresh();

这绑定和显示,显然我需要更新ListView当我删除/添加项目到我的静态ObservableCollection。提前感谢

绑定并更新静态属性

您可以将Global更改为单例并实现INotifyPropertyChanged。像这样:

public class Global : INotifyPropertyChanged
{
    private static Global _instance = new Global();
    public static Global Instance { get { return _instance; } }
    private ObservableCollection<string, Dictionary<string, Dictionary<string, object>>> operations = new ObservableCollection<string, Dictionary<string, Dictionary<string, object>>>();
    public ObservableCollection<string> _Operations
    {
        get
        {
            // ...
        }
        set
        {
            // ...
            OnPropertyChanged("_Operations");
        }
    }
    public event PropertyChangedEventHandler PropertyChanged;
    private void OnPropertyChanged(string propName)
    {
        PropertyChanged(this, new PropertyChangedEventArgs(propName);
    }
}

您可以在绑定中这样设置:

<ListView Name="list" DataContext="{x:Static Global.Instance}" ItemsSource="{Binding Path=_Operations}">
    <ListView.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding }"  />
                <Button Content="Delete" Click="Button_Click"/>
            </StackPanel>
        </DataTemplate>
    </ListView.ItemTemplate>
</ListView>

根据您的代码设置方式,我能想到强制刷新的唯一方法是将ItemsSource设置为null,然后将ItemsSource设置为null

你正在改变操作,而不是你的listview绑定到的_Operations,这就是问题所在。使用下面的代码,它应该工作。

    var item = ((Button)sender).DataContext;
    var itemIndex = list.Items.IndexOf(item);
    Global.operations.RemoveAt(itemIndex);
    list.ItemsSource = null;
    list.ItemsSource = Global._Operations;

如果用以下代码替换Global类,对操作对象所做的添加/删除将被传播到_names,并且绑定将正常工作。

如果需要分配给Global,则需要额外的代码。操作(例如,需要订阅新的collections CollectionChanged事件),但假设您可以修改现有代码,只需从Global.operation中添加/删除。

public static class Global
{
    public static ObservableCollection<Dictionary<string, Dictionary<string, object>>> operations = new ObservableCollection<Dictionary<string, Dictionary<string, object>>>();
    static ObservableCollection<String> names = new ObservableCollection<string>();
    public static ObservableCollection<String> _Operations
    {
        get
        {               
            return names;
        }
    }
    static Global()
    {
        operations.CollectionChanged += operations_CollectionChanged;
    }
    static void operations_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
    {
        if (e.OldItems != null)
        {
            foreach (Dictionary<string, Dictionary<string, object>> value in e.OldItems)
            {
                _Operations.Remove(value.Keys.First().ToString( ));
            }
        }
        if (e.NewItems != null)
        {
            foreach (Dictionary<string, Dictionary<string, object>> value in e.NewItems)
            {
                _Operations.Add(value.Keys.First().ToString());
            }
        }
    }
}