Wpf 如何清除列表框';通过绑定将所选项目重新绑定

Wpf 如何清除列表框';通过绑定将所选项目重新绑定,wpf,mvvm,listbox,selection,itemscontrol,Wpf,Mvvm,Listbox,Selection,Itemscontrol,我有一个WPFListBox通过ItemsSource绑定到一个集合。 所选项目以双向模式绑定到VM上的属性。 当我为集合中不存在的模型属性赋值时,我希望所选项在UI上处于“未选中”状态 可能吗?如果没有,是否有其他方法清除所选项目 请记住,我是在MVVM模式下工作的,因此我无法从代码中访问列表本身 谢谢 我将假设如下: listbox的ItemsSource属性绑定到ViewModel中的某个列表(即VM_列表) listbox的SelectedItem属性通过双向绑定绑定到ViewModel

我有一个WPF
ListBox
通过
ItemsSource
绑定到一个集合。 所选项目以双向模式绑定到VM上的属性。 当我为集合中不存在的模型属性赋值时,我希望所选项在UI上处于“未选中”状态

可能吗?如果没有,是否有其他方法清除所选项目

请记住,我是在MVVM模式下工作的,因此我无法从代码中访问列表本身


谢谢

我将假设如下:

  • listbox的ItemsSource属性绑定到ViewModel中的某个列表(即VM_列表)
  • listbox的SelectedItem属性通过双向绑定绑定到ViewModel中的某些属性(即VM_SelectedItem)
  • 如果以上内容不准确,请提供更多关于您的实现的信息

    您的viewmodel应该有如下代码:

    public class VM : INotifyPropertyChanged
    {
        private ObservableCollection<Student> vmlist = new ObservableCollection<Student>();
        private Student vmselecteditem;
    
        public event PropertyChangedEventHandler PropertyChanged;
    
        public VM()
        {
            PropertyChanged = new PropertyChangedEventHandler(VM_PropertyChanged);
        }
    
        private void VM_PropertyChanged(object sender, PropertyChangedEventArgs e)
        {
        }
    
        public ObservableCollection<Student> VM_List
        {
            get
            {
                return vmlist;
            }
        }
    
        public Student VM_SelectedItem
        {
            get
            {
                return vmselecteditem;
            }
            set
            {
                vmselecteditem = value;
            }
        }
    
        public void AddNewStudent(Student NewStudent)
        {
            VM_SelectedItem = null;
            PropertyChanged(this, new PropertyChangedEventArgs("VM_SelectedItem"));
            VM_SelectedItem = NewStudent;
            SaveStudent();
            PropertyChanged(this, new PropertyChangedEventArgs("VM_SelectedItem"));
            //The last line is optional, if you want to select the new student just added.
        }
    
        private void SaveStudent()
        {
            //A fake operation to save the student.
            //To stick with MVVM, the save function should be in the model
            //And this function should just call the one in the model.
            BackgroundWorker b = new BackgroundWorker();
            b.DoWork += new DoWorkEventHandler(b_DoWork);
            b.RunWorkerCompleted += new RunWorkerCompletedEventHandler(b_RunWorkerCompleted);
            b.RunWorkerAsync();
        }
    
        private void AddStudentToList()
        {
            VM_List.Add(VM_SelectedItem);
        }
    
        private void b_DoWork(object sender, DoWorkEventArgs e)
        {
            //Simulating a long save operation
            System.Threading.Thread.Sleep(2000);
        }
    
        private void b_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
            AddStudentToList();
        }
    }
    
    公共类VM:INotifyPropertyChanged
    {
    私有ObservableCollection vmlist=新ObservableCollection();
    私立学生;
    公共事件属性更改事件处理程序属性更改;
    公共虚拟机()
    {
    PropertyChanged=新的PropertyChangedEventHandler(VM_PropertyChanged);
    }
    私有void VM_PropertyChanged(对象发送方,PropertyChangedEventArgs e)
    {
    }
    公共可观察收集虚拟机列表
    {
    得到
    {
    返回vmlist;
    }
    }
    公立学生VM_SelectedItem
    {
    得到
    {
    返回vmselecteditem;
    }
    设置
    {
    vmselecteditem=值;
    }
    }
    public void AddNewStudent(学生新闻学生)
    {
    VM_SelectedItem=null;
    PropertyChanged(这是新的PropertyChangedEventArgs(“VM_SelectedItem”);
    VM_SelectedItem=NewStudent;
    SaveStudent();
    PropertyChanged(这是新的PropertyChangedEventArgs(“VM_SelectedItem”);
    //如果要选择刚添加的新学员,最后一行是可选的。
    }
    私人学生()
    {
    //一次拯救学生的假手术。
    //为了坚持使用MVVM,save函数应该在模型中
    //这个函数应该只调用模型中的函数。
    BackgroundWorker b=新的BackgroundWorker();
    b、 销钉+=新销钉(b_销钉);
    b、 RunWorkerCompleted+=新的RunWorkerCompletedEventHandler(b_RunWorkerCompleted);
    b、 RunWorkerAsync();
    }
    私有void AddStudentToList()
    {
    添加(VM\u SelectedItem);
    }
    私有void b_DoWork(对象发送方,DoWorkEventArgs e)
    {
    //模拟长时间保存操作
    系统线程线程睡眠(2000);
    }
    私有void b_RunWorkerCompleted(对象发送方,RunWorkerCompletedEventArgs e)
    {
    AddStudentToList();
    }
    }
    
    您所做的两个假设是正确的。我忘记提到的是,我还将vmselecteditem属性用于其他目的。我需要它有价值,即使它不是收藏的一部分。谢谢你的回答!那很有趣。。。在这种情况下,将其设置为null实际上不是一个选项。您可能想考虑第二个属性,即UI绑定到“选择一个项目”,比如vMyStRead TimeMeUI属性。VM_SelectedItem_UI将在且仅当VM_SelectedItem是集合的一部分时更新它,反之亦然。我真的想不出更好的办法了。如果您需要澄清,我可以发布一些代码。谢谢!我理解这个解决方案,但对于我的简单要求来说,它听起来有点太复杂了。也许由于我缺乏mvvm的经验,我的设计有点不对劲。我有一个学生列表和一个绑定到选定学生属性的学生数据模板。当我选择一个列表框项目时,它会绑定到同一个选定的学生,然后根据新选定的学生更改数据模板。我问题中的用例是当我想添加一个新的学生,然后我需要它成为一个新的实例,这显然不是学生列表的一部分。我遗漏了什么吗?嗯,如果我没听错的话,你想在向列表中添加新的student实例之前清除所选项目吗?使用我提供的示例,您可以在ViewModel中使用一个函数,该函数1)取消选择当前选定的项目,2)将新学员添加到列表中,3)如果需要,可以选择刚刚添加的新学员。我更新了我的答案以反映这一点。如果这不是你的意思,我很抱歉,有时很难通过互联网进入同一个页面。谢谢你的努力!这不是我想要的:]我不想在保存新学生之前将其添加到列表中。我希望所选属性引用新学员,而不是学员列表的一部分。正如我之前所说的,虽然情况如此,但应该清除列表中的选项