【问题标题】:Updating a ComboBox SelectedItem from code behind从后面的代码更新 ComboBox SelectedItem
【发布时间】:2011-11-30 17:49:33
【问题描述】:

我有一个带有绑定到我的 viewModel 属性的 ComboBox 的视图。 一切正常,但我实际上想重用我的视图并且需要 使用给定值更新控件。设置属性不会更新可视 UI 甚至事件被解雇并且一切看起来都很好。

一切正常都接受 ComboBox 可视化 UI。

提示?!

XAML 控件

<telerik:RadComboBox 
            ItemTemplate="{StaticResource SelectUserComboBoxTemplate}"
            SelectedItem="{Binding Path=SelectedUser, Mode=TwoWay,
            UpdateSourceTrigger=PropertyChanged}" 
            ItemsSource="{Binding Path=C_users}" 
            telerik:TextSearch.TextPath="displayName"
            Name="radComboBox1" 
            Margin="14,12,0,0" 
            Height="31" 
            VerticalAlignment="Top" 
            HorizontalAlignment="Left" 
            Width="253" 
            TextSearchMode="Contains"
            IsEditable="True"
            OpenDropDownOnFocus="True" 
            IsFilteringEnabled="True"
            >
    </telerik:RadComboBox>

设置值的重载构造函数

    public TicketControlTabViewModel(ticket t)
    {
        activeTicket = t;
        SelectedUser = customerServiceClient.getUser(t.customer_users.id);
        MetaString = t.meta;
        Description = t.description;
        ActiveId = t.id.ToString();
        Selected_priority = t.priority;
        SelectedStatus = t.status;
        this.RefreshC_users();
        this.RefreshSupportDepartments();
        this.RefreshSupportUsers();
    }

我的 ViewModel 中的属性

    private customer_users selectedUser { get; set; }
    public customer_users SelectedUser
    {

        get {
            return this.selectedUser;
            }
        set {
              if (value != null){
              this.selectedUser = value;
              this.UpdateCustomerDepartment(value);
              this.OnPropertyChanged("SelectedUser");
              SaveTicket();
              }

            }
    }

【问题讨论】:

  • @Bolt 您已编辑,但在标题中留下了该标签?嘘。
  • C_users 是 ObservableCollection 吗?
  • 私有 IEnumerable c_users;公共 IEnumerable C_users { get { return this.c_users; } 设置 { this.c_users = 值; this.OnPropertyChanged("C_users"); } }
  • 但是控件应该对 SelectedUser 做出反应...... itemsource 工作......我仍然可以选择用户并且他们被选中等等。它只是用预先选择的项目更新实际控件....我认为它是因为控件是时间加载问题....

标签: c# wpf mvvm


【解决方案1】:

默认情况下,WPF 通过引用而不是值来比较 SelectedItem。这意味着如果 SelectedItem 与您的 ItemsSource 中的项目在内存中不是完全相同的对象,那么比较将返回 false 并且项目不会被选中。

例如,这可能行不通

MyCollection = new ObservableCollection<User>(DAL.GetUsers());
SelectedUser = DAL.GetUser(1);

然而这会:

MyCollection = new ObservableCollection<User>(DAL.GetUsers());
SelectedUser = MyCollection.FirstOrDefault(p => p.Id == 1);

这是因为第二个示例将 SelectedUser 设置为实际存在于MyCollection 中的项目,而第一个示例可能不存在。即使数据相同,它们引用内存中的不同对象。

如果您选择的项目与您的 ItemsSource 项目在内存中没有引用相同的项目,则使用 SelectedValueSelectedValuePath 绑定您的 ComboBox 的默认选择,或覆盖您的类的 .Equals() 方法以返回如果正在比较的对象中的数据相同,则为 true。

public override bool Equals(object obj)
{
    if (obj == null || !(obj == MyClass))
        return false; 

    return ((MyClass)obj).Id == this.Id);
}

【讨论】:

  • 啊,非常感谢你,我只是浪费了一天的大部分时间试图弄清楚这一点。我使用了您的 LINQ 示例并添加了一个新属性来绑定 ComboBox SelectedItem,然后使用 LINQ 选择并通过引用返回实际项目。
【解决方案2】:

如果您不 Items 集合不包含等于 SelectedItem 的项目,则可能会发生这种情况。检查你是否有这样的项目(可能是你忘记在你的类中重载Equals,它使用了引用比较)

【讨论】:

  • 项目对象来自我的实体模型...(或信息)
  • 在控件之后加载视图模型,反之亦然,它仍然是一样的,所以这样一个简单的修复是希望最好的:)
  • 你的东西 Snowbear....阅读论坛““我在字段类上实现了 Equals 和 GetHashCode 并且它有效””但它在我的用户项目上吗?在我更多地使用它之前想确定一下,因为它来自一个实体,它有点麻烦......
  • 是的,customer_users 应该实现它。否则,仅当您将SelectedItem 设置为与您的收藏中的一项相同时,它才会起作用。在默认 equals 实现方面相同
  • 你在哪里正确的雪熊!添加了一个 Equals 覆盖,瞧!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-12-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多