【问题标题】:combo box does not refresh when observable collection changes可观察集合更改时组合框不会刷新
【发布时间】:2016-12-22 13:25:38
【问题描述】:

我有一个 wpf 桌面应用程序。

我有一个下拉框,它的项目源设置为可观察的集合。

目的是显示用户列表。 我在该表单上有一个按钮,它将删除选定的用户。 它将字段“活动”设置为“0”,其中“1”未被删除。

问题是,即使我可以看到 observable 集合减少了 1。但下拉菜单直观地显示了所有原始用户状态。

这是我的 XAML:

<ComboBox ItemsSource="{Binding Users}" DisplayMemberPath="Login" 
                 SelectedValue="{Binding SelectedManagerUser}"  />

这是它的虚拟机位:

public ObservableCollection<UserRecord> Users
{
    get
    {
        return (from users in UserRecord.Get().Where(d => d.Active == 1)
                     select new UserRecord
                     {
                         FName = users.FName,
                         SName = users.SName,
                         UserRecordId = users.UserRecordId,
                         Login = users.Login,
                         IsAdmin = users.IsAdmin,
                         UserRef = users.UserRef,
                         Disabled = users.Disabled,
                         Branch = users.Branch,
                         Department = users.Department,
                         Position = users.Position,                                
                         Salt = users.Salt,
                     }).OrderBy(d => d.Login).ToList();

    }
    set {
        _Users =  value; RaisePropertyChanged(InformedWorkerCommon.Constants.VM_Users); }
}

我的 POCO/模型:

public class UserRecord
{
    public int UserRecordId { get; set; }
    public string FName { get; set; }
    public string SName { get; set; }
    public string Login { get; set; }
    public string Salt { get; set; }
    public int IsAdmin { get; set; }
    public string UserRef { get; set; }
    public int Disabled { get; set; }
    public string Branch { get; set; }
    public string Position { get; set; }
    public int Active { get; set; }
    public string Department { get; set; }
    public string ServerRef { get; set; }
    public DateTime ServerTS { get; set; }
}

这是将 Active 字段设置为“0”的代码:

我的测试涉及预加载 2 个用户

private void DeleteUser()
{
    try
    {

此时用户数为 2

        UserRecord.Save(new UserRecord()
                {
                    UserRef=UserRef,
                    Branch = Branch,
                    Department = Department,
                    Disabled = Disabled == true ? 1 : 0,
                    FName = FName,
                    IsAdmin = 0,
                    Login = Login,
                    Position = Position,
                    SName = SName,
                    Active = 0,                           
                });

此时用户数为 1,但下拉菜单仍显示 2 个用户

                DisplayInfoMessage(Properties.Resources.Deleted);
            }
        }
    }
    catch (Exception ex)
    {
        //handle the error
    }
}

我对 wpf 比较陌生,所以我可以在这里做正确的咆哮吗?

【问题讨论】:

  • InformedWorkerCommon.Constants.VM_Users 的值是否为“Users”,以通知组合框绑定已更改?您似乎没有在任何地方“设置”该属性,因为您的吸气剂只是从数据库中再次读取所有内容。您实际上并不需要 Users 属性的设置器,它足以通知正确的绑定已从删除函数中更改。
  • 我有点惊讶Delete() 方法被实现为Save(new UserRecord{...})。但是,假设Save 仍然会做正确的事情,您可能只需要更新ComboBox 中的BindingObservableCollection 不会在仅更改项目的属性时自动通知。我认为UserRecord.Save 的代码在这里会有所帮助。
  • 您好,感谢您的建议。删除是有原因的,并且可能都是错误的原因:) 我会在我回到办公室时检查。谢谢你
  • @JanneMatikainen 关于二传手的说法非常正确。返回时将删除并检查该常量值。谢谢你
  • 这段代码能编译吗?你的Users getter 应该返回ObservableCollection&lt;UserRecord&gt;,但它却返回List&lt;UserRecord&gt;。您不能将List 隐式转换为ObservableCollection

标签: c# wpf observablecollection


【解决方案1】:

您应该创建 ObservableCollection 的 一个 单个实例,并从该单个实例中添加和删除项目。

您可以在视图模型的构造函数中创建集合,并将该属性实现为简单的自动实现的只读属性,例如:

public class ViewModel
{
    public ViewModel()
    {
        Users = new ObservableCollection<UserRecord>((from users in UserRecord.Get().Where(d => d.Active == 1)
                                                      select new UserRecord
                                                      {
                                                          FName = users.FName,
                                                          SName = users.SName,
                                                          UserRecordId = users.UserRecordId,
                                                          Login = users.Login,
                                                          IsAdmin = users.IsAdmin,
                                                          UserRef = users.UserRef,
                                                          Disabled = users.Disabled,
                                                          Branch = users.Branch,
                                                          Department = users.Department,
                                                          Position = users.Position,
                                                          Salt = users.Salt,
                                                      }).OrderBy(d => d.Login).ToList());
    }

    public ObservableCollection<UserRecord> Users { get; }

}

然后,当您在源集合中添加或删除项目时,绑定到 Users 属性的 ComboBox 将得到更新。但是你不应该在每次调用源属性的 getter 时都创建一个新的 ObservableCollection。

【讨论】:

  • 感谢您对我的教育。圣诞快乐:)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-05-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-04-01
  • 2012-10-20
相关资源
最近更新 更多