从工作线程刷新 DataGrid

Refresh DataGrid from worker thread

我的 WPF 应用程序中有一个 DataGrid。对于这个 DataGrid,我已将 ItemSource 设置如下

ItemsSource="{Binding Path=MyItems}"

MyItems 是在 MyViewModel 中声明的 MyItem 列表

    // ItemsSource for MyItem Grid
    public List<MyItem> MyItems {get;set; }

MyItem 有一组属性,每个 属性 都映射到 DataGrid 中的每一列。在初始化时,我正在填充 MyItems;因此 DataGrid 在每列中显示 MyItems 值。

在按钮命令中,我正在创建一个工作线程,工作线程修改网格中显示的 MyItems 的属性。例如,MyItem 有一个名为 "Status" 的 属性,它绑定到一列网格。状态值在工作线程中更改。我调用的工作线程结束

OnPropertyChanged("MyItems"); //force UI refresh

但是网格中的状态列值没有更新。

单击数据网格列后,只有值在刷新。如何从工作线程刷新数据网格?

如果操作正确,您将不需要告诉网格刷新。如果您确实设法刷新了整个网格,也会出现意想不到的后果,例如跳到网格顶部并丢失任何选定的用户 rows/cells 以及中止编辑(如果适用)。

ObservableCollection

这是设置网格正在查看的列表的方式:

private readonly ObservableCollection<MyItem> _myItems = new ObservableCollection<MyItem>();

public IEnumerable<MyItem> MyItems { get { return _myItems; } }

这意味着新项目和移除会自动更新网格。然而,要更新单个单元格,属性 需要是可观察的,即 class MyItem 必须实现 INotifyPropertyChanged.

多线程

对于多线程,您需要在 UI 线程中设置 MyItem 的属性,即使您在辅助线程中进行计算(见下文)也是如此。您可以使用 Dispatcher. See Updating GUI (WPF) using a different thread

工作线程

至于启动你自己的线程,不要那样做,使用 Task

使用调度程序不是一个好主意。 UI 如果编码不当,可能会变得无响应。在多线程环境中使用数据网格很棘手。

  1. 后台线程处理数据并根据这个结果 处理,数据网格将被更新。
  2. UI WPF 中的控件只能由 UI 线程更新。
  3. 可以有多个 UI 控件一起工作 实现整体功能(进度条、按钮等)。 编码人员经常错误地在 不安全的方式。
  4. 数据网格将绑定到的数据源不应该是 可由任何其他 class.
  5. 修改

我在这里发布了一个模板。它涵盖了在多线程设置中使用数据网格的可能方法。

http://www.codeproject.com/Articles/1086714/A-Template-For-Using-Datagrid-in-Monitoring-UI