Animating a TextBox.Foreground in WPF

amiry jd picture amiry jd · Aug 24, 2013 · Viewed 15.3k times · Source

Is there anyway to animate a TextBox.ForegroundProperty?

<Color x:Key="NormalColor">#FF666666</Color>
<SolidColorBrush x:Key="NormalBrush" Color="{StaticResource NormalColor}" />

<Color x:Key="MouseOverColor">#FF666666</Color>
<SolidColorBrush x:Key="MouseOverBrush" Color="{StaticResource MouseOverColor}" />

<ControlTemplate x:Key="RegularTextBoxTemplate" TargetType="{x:Type TextBox}">
    <Grid>
        <VisualStateManager.VisualStateGroups>
            <VisualStateGroup x:Name="CommonStates">
                <VisualStateGroup.Transitions>
                    <VisualTransition GeneratedDuration="0:0:0.1"/>
                </VisualStateGroup.Transitions>
                <VisualState x:Name="Normal"/>
                <VisualState x:Name="MouseOver">
                    <Storyboard>
                        <!-- storyboard to animating foreground here... -->
                    </Storyboard>
                </VisualState>
            </VisualStateGroup >
        </VisualStateManager>
        <ScrollViewer x:Name="PART_ContentHost" 
                      BorderThickness="0"
                      IsTabStop="False"
                      Background="{x:Null}"/>
    </Grid>
</ControlTemplate>

<Style x:Key="RegularTextBox" TargetType="{x:Type TextBox}">
    <Setter Property="Foreground" Value="{StaticResource NormalBrush}"/>
    <Setter Property="Template" Value="{StaticResource RegularTextBoxTemplate}"/>
</Style>

My tried storyboards are:

<ColorAnimationUsingKeyFrames Storyboard.TargetName="PART_ContentHost"
                  Storyboard.TargetProperty="(Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames Storyboard.TargetName="PART_ContentHost"
              Storyboard.TargetProperty="(Control.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames Storyboard.TargetName="PART_ContentHost"
          Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames
                  Storyboard.TargetProperty="(Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames
              Storyboard.TargetProperty="(TextBox.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames
              Storyboard.TargetProperty="(Control.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

<ColorAnimationUsingKeyFrames
          Storyboard.TargetProperty="(TextElement.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{StaticResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

None of them work. Any idea? Is it even possible?

Answer

amiry jd picture amiry jd · Aug 25, 2013

Well, thanks to all that were trying to help me, I found my answer. It seems when we set TextBox.Foreground property to a resource, the storyboard cannot animate it. So, the style should be something like this:

<Style x:Key="RegularTextBox" TargetType="{x:Type TextBox}">
    <Setter Property="Foreground">
        <Setter.Value>
            <SolidColorBrush Color="{DynamicResource NormalColor}"/>
        </Setter.Value>
    </Setter>
    <Setter Property="Template" Value="{StaticResource RegularTextBoxTemplate}"/>
</Style>

This was the only problem I had. But there is a note to remember. When we want to target a templated parent in a storyboard, it's not necessary to bind to it. We just need to leave it:

<!-- It's not necessary to set Storyboard.TargetName in storyboard -->
<!-- It will automatically target the TemplatedParent -->
<ColorAnimationUsingKeyFrames
              Storyboard.TargetProperty="(TextBox.Foreground).(SolidColorBrush.Color)">
    <EasingColorKeyFrame KeyTime="0" Value="{DynamicResource MouseOverColor}" />
</ColorAnimationUsingKeyFrames>

This works for me.


Here is a working example.