每当DataGrid获取更多行或删除一些行时,我希望重新计算内容。我尝试使用Loaded
事件,但只触发了一次。
我找到了AddingNewItem
,但在添加之前就已经解雇了。我之后需要做的事情。
还有LayoutUpdated
,它有效,但我担心使用它并不明智,因为它经常用于我的目的。
答案 0 :(得分:9)
如果你的DataGrid
被绑定了,我想到了两种方法。
您可以尝试获取DataGrid.ItemsSource
集合,并订阅其CollectionChanged
事件。这只有在你知道它最初是什么类型的集合时才有效。
// Be warned that the `Loaded` event runs anytime the window loads into view,
// so you will probably want to include an Unloaded event that detaches the
// collection
private void DataGrid_Loaded(object sender, RoutedEventArgs e)
{
var dg = (DataGrid)sender;
if (dg == null || dg.ItemsSource == null) return;
var sourceCollection = dg.ItemsSource as ObservableCollection<ViewModelBase>;
if (sourceCollection == null) return;
sourceCollection .CollectionChanged +=
new NotifyCollectionChangedEventHandler(DataGrid_CollectionChanged);
}
void DataGrid_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
// Execute your logic here
}
另一种解决方案是使用事件系统,例如Microsoft Prism的EventAggregator
或MVVM Light Messenger
。这意味着您的ViewModel
会在绑定集合发生更改时广播DataCollectionChanged
事件消息,并且您的View
会订阅接收这些消息并在任何时候执行您的代码。
使用EventAggregator
// Subscribe
eventAggregator.GetEvent<CollectionChangedMessage>().Subscribe(DoWork);
// Broadcast
eventAggregator.GetEvent<CollectionChangedMessage>().Publish();
使用Messenger
//Subscribe
Messenger.Default.Register<CollectionChangedMessage>(DoWork);
// Broadcast
Messenger.Default.Send<CollectionChangedMessage>()
答案 1 :(得分:2)
DataGrid.LoadingRow(object sender, DataGridRowEventArgs e)
怎么样?
卸载相同。
DataGrid.UnLoadingRow(object sender, DataGridRowEventArgs e)
?
答案 2 :(得分:2)
您是否尝试过MVVM方法并绑定到Observable集合?
public ObservableCollection<Thing> Items{
get { return _items; }
set{ _items = value; RaisePropertyChanged("Items"); // Do additional processing here
}
}
因此,您可以观看添加/删除项目而不必与UI绑定?
答案 3 :(得分:0)
如果你想使用ObservableCollection并获得有关添加或其他操作的通知,最好的方法是使用INotifyCollectionChanged
var source = datagrid.ItemsSource as INotifyCollectionChanged;
因为,当您要打开ObservableCollection<MyClass>()
时,您必须写出极具吸引力的MyClass(不是ObservableCollection<ParentOfMyClass>
())
答案 4 :(得分:0)
如果您愿意,可以像其他人在此处描述的那样沿着RowUnloading
路线前进,但请注意,每当一行失去焦点时,此事件也会触发。
然而,通过四处游戏,我发现当删除一行时,网格的SelectedItem
属性为null,而CurrentItem
属性不为null,到目前为止我只看到了这个组合已删除的行,(虽然我不能保证我没有错过异国情况......但是对于离开行的基本情况我到目前为止还没有看到过。)
因此,何时可以使用以下代码仅过滤已删除的行:
private void CategoriesGrid_UnloadingRow(object sender, DataGridRowEventArgs e)
{
if (((DataGrid)sender).SelectedItem != null || ((DataGrid)sender).CurrentItem == null)
{
return;
}
// The rest of your code goes here
}
答案 5 :(得分:-1)
取决于&#34;事物&#34;如果要重新计算,可以考虑使用ScrollViewer.ScrollChanged附加事件。这可以在XAML中设置如下:
<DataGrid
...
ScrollViewer.ScrollChanged="control_ScrollChanged">
ScrollChangedEventArgs对象具有各种属性,可用于计算布局和滚动位置(范围,偏移,视口)。请注意,使用默认虚拟化设置时,这些通常以行/列数量来衡量。
答案 6 :(得分:-1)
我一直在寻找解决方案,我找到了完美的事件来处理这个事件,这个事件叫做 UnloadingRow
<DataGrid ....
UnloadingRow="DataGrid_UnloadingRow">
...
</DataGrid>
在你的C#代码中,你得到这个
private void ProductsDataGrid_UnloadingRow(object sender, DataGridRowEventArgs e)
{
MyObject obj = (MyObject)e.Row.Item; // get the deleted item to handle it
// Rest of your code ...
// For example : deleting the object from DB using entityframework
}