[英]How to Create a Custom DataGrid
All, in this answer https://stackoverflow.com/a/18136371/626442 to a previous question, the answer provided a solution to the problem of my animation not firing. 全部,在对上一个问题的https://stackoverflow.com/a/18136371/626442答案中,答案为我的动画不触发的问题提供了解决方案。 The code was
该代码是
<DataTemplate x:Key="readOnlyCellUpdatedStyle">
<TextBlock Text="{Binding KeyIndex, Mode=TwoWay,NotifyOnTargetUpdated=True}">
<TextBlock.Style>
<Style TargetType="TextBlock">
<Setter Property="Background" Value="White"/>
<Style.Triggers>
<EventTrigger RoutedEvent="Binding.TargetUpdated">
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetProperty="Background.Color"
Duration="0:0:0.3"
From="White"
To="Red"
RepeatBehavior="3x"
AutoReverse="True"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</Style.Triggers>
</Style>
</TextBlock.Style>
</TextBlock>
</DataTemplate>
This fires the animation when I update the KeyIndex
column via the ViewModel. 当我通过ViewModel更新
KeyIndex
列时,这会触发动画。 However, I only want the animation of the cells of the DataGridTextColumn
to animate when the values are updated but they also fire when the DataGrid
is scrolled. 但是,我只希望更新值时对
DataGridTextColumn
单元格的动画进行动画处理,但还可以在滚动DataGrid
时触发它们。 I was suggested 建议我
It may be a better option to create a derived
DataGridTextColumn
with the features you need built in, as usingTargetUpdated
will be pretty much impossible if you are using Virtualization.使用所需的内置功能创建派生的
DataGridTextColumn
可能是一个更好的选择,因为如果您使用的是虚拟化,则几乎不可能使用TargetUpdated
。 But if you made a customDataGridTextColumn
you should be able to get it working.但是,如果您创建了一个自定义的
DataGridTextColumn
,则应该能够使它工作。
How do I create a custom/derived `DataGridTextColumn (I have access to blend too)? 如何创建自定义/派生的DataGridTextColumn(我也可以访问blend)?
I have no idea how to do this and the documentation on this particular concept is sparse. 我不知道如何执行此操作,有关此特定概念的文档很少。
Thanks for your time. 谢谢你的时间。
It turned out to be quite difficult to get this working with Virtualization
when using VirtualizationMode="Recycling"
当使用
VirtualizationMode="Recycling"
时,要使其与Virtualization
使用非常困难
I found a way to get it working by deriving TextBlock
and attaching to the PropertyChanged
event of the bound object. 我找到了一种方法,方法是派生
TextBlock
并将其附加到绑定对象的PropertyChanged
事件。
When the value changes the animation is played, but if you scroll the recycled item does not continue to play the animation. 当值更改时,将播放动画,但是如果滚动,则回收的项目将不会继续播放动画。
This is a pretty rough example but I am sure you can clean up and modify to your needs. 这是一个非常粗糙的示例,但是我相信您可以清理并修改您的需求。
TextBlock: TextBlock的:
public class VirtualizingNotifyTextBlock : TextBlock
{
private INotifyPropertyChanged _dataItem;
private string _propertyName;
public VirtualizingNotifyTextBlock()
: base()
{
this.TargetUpdated += NotifyTextBlock_TargetUpdated;
}
public static readonly RoutedEvent PropertyChangedEvent = EventManager.RegisterRoutedEvent("PropertyChanged", RoutingStrategy.Bubble, typeof(RoutedEventHandler), typeof(VirtualizingNotifyTextBlock));
public static readonly DependencyProperty NotifyDurationProperty = DependencyProperty.Register("NotifyDuration", typeof(int), typeof(VirtualizingNotifyTextBlock), new PropertyMetadata(300));
public static readonly DependencyProperty NotifyRepeatProperty = DependencyProperty.Register("NotifyRepeat", typeof(int), typeof(VirtualizingNotifyTextBlock), new PropertyMetadata(3));
public static readonly DependencyProperty NotifyColorProperty = DependencyProperty.Register("NotifyColor", typeof(Color), typeof(VirtualizingNotifyTextBlock), new PropertyMetadata(Colors.Red));
public Color NotifyColor
{
get { return (Color)GetValue(NotifyColorProperty); }
set { SetValue(NotifyColorProperty, value); }
}
public int NotifyDuration
{
get { return (int)GetValue(NotifyDurationProperty); }
set { SetValue(NotifyDurationProperty, value); }
}
public int NotifyRepeat
{
get { return (int)GetValue(NotifyRepeatProperty); }
set { SetValue(NotifyRepeatProperty, value); }
}
public INotifyPropertyChanged DataItem
{
get { return _dataItem; }
set
{
if (_dataItem != null)
{
Background = new SolidColorBrush(Colors.Transparent);
_dataItem.PropertyChanged -= DataItem_PropertyChanged;
}
_dataItem = value;
if (_dataItem != null)
{
_dataItem.PropertyChanged += DataItem_PropertyChanged;
}
}
}
private void NotifyTextBlock_TargetUpdated(object sender, DataTransferEventArgs e)
{
var binding = this.GetBindingExpression(VirtualizingNotifyTextBlock.TextProperty);
if (binding != null)
{
_propertyName = binding.ResolvedSourcePropertyName;
DataItem = binding.DataItem as INotifyPropertyChanged;
}
}
private void DataItem_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == _propertyName)
{
var animation = new ColorAnimation(NotifyColor, new Duration(TimeSpan.FromMilliseconds(NotifyDuration)));
animation.RepeatBehavior = new RepeatBehavior(NotifyRepeat);
animation.AutoReverse = true;
Background = new SolidColorBrush(Colors.Transparent);
Background.BeginAnimation(SolidColorBrush.ColorProperty, animation);
}
}
}
Xaml: XAML:
<DataTemplate x:Key="readOnlyCellUpdatedStyle">
<local:VirtualizingNotifyTextBlock Text="{Binding KeyIndex, NotifyOnTargetUpdated=True}" NotifyColor="Blue" NotifyDuration="250" NotifyRepeat="4" />
</DataTemplate>
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.