2014-10-01 31 views
0

我有一个绑定到某些XML数据的DataGrid。刷新WPF中的单个项目CollectionCollection

当我在XML数据中进行更改时,DataGrid不刷新以反映这些更改。

解决此问题的“简单”方法是在每次进行更改时调用MyDataGrid.Items.Refresh()。

但是,这是laggy,似乎相当低效。

我该如何刷新一个单个的行,而不是整个数据网格?我可以轻松访问DataGridRow以及已更改的XmlElement,但我只是不知道要调用哪个函数。

一直在这个问题上停留了3-4个小时,现在已经尝试了几十种解决方案,但却无法让它正常工作。

下面是相关的代码。

A)定义样式。

<!-- Field Value Style --> 
    <local:FieldValueConverter x:Key="FieldValueConverter"/> 
    <local:Node x:Key="Node"/> 
    <Style x:Key="fieldValueStyle" TargetType="{x:Type TextBlock}"> 
     <Setter Property="Text" Value="{Binding ., Converter={StaticResource FieldValueConverter}}"/> 
     <Setter Property="KeyboardNavigation.IsTabStop" Value="False"/> 
     <Setter Property="Focusable" Value="False"/> 
    </Style> 

B)定义的DataGrid

<DataGrid x:Name="FieldPanelDataGrid" DockPanel.Dock="Left" 
     AutoGenerateColumns="False" 
     DataContext="{Binding ElementName=ObjectPanelListBox, Path=SelectedItem}" 
     ItemsSource="{Binding}" 
     IsSynchronizedWithCurrentItem="True" 
     IsReadOnly="True" 
     CanUserResizeRows="False" 
     CanUserResizeColumns="True" 
     KeyboardNavigation.IsTabStop="False" 
     Visibility="Visible" 
     SelectionMode="Single"> 
    <DataGrid.Resources> 
     <Style TargetType="DataGridRow"> 
      <EventSetter Event="MouseDoubleClick" Handler="FieldCell_MouseDoubleClick"/> 
      <EventSetter Event="PreviewMouseLeftButtonDown" Handler="FieldCell_PreviewMouseLeftButonDown"></EventSetter> 
      <EventSetter Event="PreviewKeyDown" Handler="FieldCell_PreviewKeyDown"></EventSetter> 
     </Style> 
    </DataGrid.Resources> 
    <DataGrid.Columns> 
     <DataGridTextColumn x:Name="FieldName" Header="Name" CanUserSort="False" ElementStyle="{StaticResource fieldNameStyle}"/> 
     <DataGridTextColumn x:Name="FieldValue" Header="Value" Width="*" ElementStyle="{StaticResource fieldValueStyle}"/> 
    </DataGrid.Columns> 
</DataGrid> 
+0

您可以从源集合中移除已更改的XmlElement,然后将其重新插入到相同的位置吗?它可以工作.. – 2014-10-01 22:04:23

+0

也许首先向我们展示读取XML并填充数据网格的代码。另外,对应用程序外部的XML(文件)进行了更改?如果是这样,也许你可以挂接一个filesystemwatcher来观看你的xml文件,并相应地更新你的数据网格。 – failedprogramming 2014-10-01 22:04:38

+0

@ h.alex:好的想法。我得到了一个错误:“虽然ItemsSource正在使用时操作无效,但使用ItemsControl.ItemsSource访问和修改元素”。和失败的编程:我用一些代码更新了原文。这些更改在应用程序内。 – Brent 2014-10-01 22:22:11

回答

1

我建议使用一个ObservableCollection作为的ItemSource和在的ObservableCollection中的条目必须执行INotifyPropertyChanged。然后,如果行更改,您就会受益,ObservableCollection会告知您的UI并且它会更新。

例子:

您的入门级:

public class MyXmlObject : INotifyPropertyChanged 
{ 

    public event PropertyChangedEventHandler PropertyChanged; 

    private string fieldName; 

    public string FieldName 
    { 
     get { return fieldName; } 
     set 
     { 
      fieldName = value; 
      NotifyPropertyChanged("FieldName"); 
     } 
    } 

    NotifyPropertyChanged(string propertyName) 
    { 
     if (PropertyChanged != null) 
     { 
      PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); 
     } 
    } 
} 

您的用户控件(视图模型,控制器或后面的代码)代码:

public ObservableCollection<MyXmlObject> MyCollection { get; set; } 

正如我在XAML中提到你只需将集合绑定到ItemsSource

<DataGrid ItemsSource="{Binding MyCollection}" .../> 

现在只有beeing变更的项目才会更新。

+0

我可能错过了一些明显的东西,但是当我将DataGrid的ItemSource从{绑定}更改为{绑定MyCollection}时,所有项目都消失了。 – Brent 2014-10-08 02:25:01

+0

它取决于你的UserControls的DataContext。您必须将集合放到代表UserControls DataContext的类中。例如,如果它是您的UserControl本身的代码尝试设置__DataContext = this; __ – coder0815 2014-10-08 06:15:52

+0

我不确定这是否会工作,因为我已经将XAML中的DataContext设置为“{Binding ElementName = ObjectPanelListBox,路径=的SelectedItem}” – Brent 2014-10-08 17:18:58