在动画期间或之后未调用 WPF InvalidateMeasure
我有一个具有以下 ListBoxItem 样式的自定义列表框。它包含一些动画,用于在鼠标悬停在 ListBoxItem 上时缩放 ListBoxItem。
<Style x:Key="notesListBoxStyle" TargetType="{x:Type ListBoxItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<Grid x:Name="gridItem"
Background="LemonChiffon"
Height="100"
Width="100"
RenderTransformOrigin="{TemplateBinding RenderTransformOrigin}">
<Grid.RenderTransform>
<ScaleTransform ScaleX="1.0"
ScaleY="1.0"/>
</Grid.RenderTransform>
<Grid.LayoutTransform>
<RotateTransform Angle="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBoxItem}, AncestorLevel=1}, Converter={StaticResource listIndexConverter}, ConverterParameter='Rotate'}"/>
</Grid.LayoutTransform>
<Border BorderBrush="DarkGoldenrod" BorderThickness="2" Margin="2">
<ContentPresenter HorizontalAlignment="Stretch"
SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
VerticalAlignment="Stretch"/>
</Border>
</Grid>
<ControlTemplate.Triggers>
<EventTrigger RoutedEvent="ListBoxItem.MouseEnter">
<BeginStoryboard Name="showItemStoryboard">
<Storyboard >
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="RenderTransform.ScaleX"
From="1.0"
To="1.5"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="RenderTransform.ScaleY"
From="1.0"
To="1.5"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="Width"
From="100"
To="400"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="Height"
From="100"
To="200"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="LayoutTransform.Angle"
To="0"
Duration="0:0:0.3"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="ListBoxItem.MouseLeave">
<StopStoryboard BeginStoryboardName="showItemStoryboard"/>
</EventTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
我有自己的 ListBox 的 MeasureOverride 实现,它被调用,一切都很好,除了在缩放 ListBoxItem 之前不会调用 MeasureOverride,因此它请求的大小比所需的小得多。
我尝试在动画完成后在 ListBox 上调用 InvalidateMeasure,但未触发 MeasureOverride 方法。目前我正在 ControlTemplate 中的网格上应用动画,这是否导致 MeasureOverride 不被调用?如何在控件本身上应用相同的动画?
I have a custom ListBox whith the following ListBoxItem style. It contains a few animations to scale the ListBoxItem when the mouse hovers over it.
<Style x:Key="notesListBoxStyle" TargetType="{x:Type ListBoxItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<Grid x:Name="gridItem"
Background="LemonChiffon"
Height="100"
Width="100"
RenderTransformOrigin="{TemplateBinding RenderTransformOrigin}">
<Grid.RenderTransform>
<ScaleTransform ScaleX="1.0"
ScaleY="1.0"/>
</Grid.RenderTransform>
<Grid.LayoutTransform>
<RotateTransform Angle="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBoxItem}, AncestorLevel=1}, Converter={StaticResource listIndexConverter}, ConverterParameter='Rotate'}"/>
</Grid.LayoutTransform>
<Border BorderBrush="DarkGoldenrod" BorderThickness="2" Margin="2">
<ContentPresenter HorizontalAlignment="Stretch"
SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
VerticalAlignment="Stretch"/>
</Border>
</Grid>
<ControlTemplate.Triggers>
<EventTrigger RoutedEvent="ListBoxItem.MouseEnter">
<BeginStoryboard Name="showItemStoryboard">
<Storyboard >
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="RenderTransform.ScaleX"
From="1.0"
To="1.5"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="RenderTransform.ScaleY"
From="1.0"
To="1.5"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="Width"
From="100"
To="400"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="Height"
From="100"
To="200"
Duration="0:0:0.3"/>
<DoubleAnimation Storyboard.TargetName="gridItem"
Storyboard.TargetProperty="LayoutTransform.Angle"
To="0"
Duration="0:0:0.3"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="ListBoxItem.MouseLeave">
<StopStoryboard BeginStoryboardName="showItemStoryboard"/>
</EventTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
I have my own implementation of MeasureOverride for my ListBox which gets called and all is well, except that MeasureOverride is not called before the ListBoxItem is scaled, so it requests a much smaller size than is required.
I have tried calling InvalidateMeasure on my ListBox after the animation is completed but the MeasureOverride method is not fired. At the moment I am applying the animations on the Grid in my ControlTemplate, Is this what is causing MeasureOverride to not be called? How do I apply the same animations on the control itself?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
RenderTransform 修改元素的外观,但在布局过程完成后应用。这意味着使用 RenderTransform 不会产生布局过程。
请改用 LayoutTransform。它确实会影响测量...
希望这有帮助,
干杯,Anvaka
RenderTransform modifies the appearance of the element but is applied after the layout pass is complete. That means using a RenderTransform does not incur a layout pass.
Instead, use LayoutTransform. It does affects measure...
Hope this helps,
Cheers, Anvaka