WPF VisualStateManager - 如何为模板化子项内的属性设置动画

时间:2011-07-13 18:08:25

标签: wpf animation storyboard visualstatemanager

我有一个UserControl,其中包含一个带有自定义ItemsPanel的ItemsControl,其依赖项属性称为“MaxColumns”。我想定义一个VisualState(在UserControl级别),它可以为自定义面板上的“MaxColumns”属性设置动画。

从本质上讲,XAML看起来像:

<Grid x:Name="LayoutRoot">
  <VisualStateManager.VisualStateGroups>
    <VisualStateGroup x:Name="MyCoolState">
      <VisualState x:Name="Normal" />
      <VisualState x:Name="NotNormal">
        <Storyboard>
          <Int32Animation Duration="0"
                          Storyboard.TargetName="Details"
                          Storyboard.TargetProperty="(ItemsControl.ItemsPanel).(local:CoolPanel.MaxColumns)"
                          To="4" />
        </Storyboard>
      </VisualState>
    </VisualStateGroup>
  <VisualStateManager>
  <ItemsControl x:Name="Details">
    <ItemsControl.ItemsPanel>
      <ItemsPanelTemplate>
        <local:CoolPanel x:Name="MyCoolPanel"
                         MaxColumns="1" />
      </ItemsPanelTemplate>
    </ItemsControl.ItemsPanel>
  </ItemsControl>
</Grid>

但是,我不能为我的生活弄清楚动画的正确语法是什么?如果我使用上面显示的语法,我得到错误:“'ItemsPanel'属性不指向路径中的DependencyObject'(0)。(1)'”。我认为这是因为它在技术上指向了ItemsPanelTemplate?

如果我直接在Storyboard.TargetName属性中引用“MyCoolPanel”,则会收到有关Name范围的错误(可能是因为“MyCoolPanel”不在LayoutRoot的名称范围内)。我不知道是否有办法在“TargetName”中限定名称范围?

有人有解决方案吗?似乎 应该可行而不诉诸自定义附加属性的东西?我的意思是,我不反对附加属性,但我觉得你应该能够直接在XAML中做到这一点吗?

1 个答案:

答案 0 :(得分:3)

好的,确实ItemsPanel不是真正的对象,而是用于创建对象的模板。所以从技术上讲,你的参考不会起作用。

我有以下关于实施的内容:

  1. 您在ItemsPanel(无论如何是模板)上设置了一些附加属性,但是在ItemsControl本身上。
  2. 使用CoolPanelRelativeSource FindAncestor的MaxColumns绑定到该附加属性。
  3. 好吧,你可以省略附加属性,然后使用Tag :-)确实,ItemsControl完全由你控制,所以滥用{{1}没有犯罪一点点。

    所以代码就像这样:

    Tag