Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

WPF Animation not working on "fast" property change

Tags:

c#

mvvm

wpf

xaml

I am having trouble making an animation work in WPF with DataTriggers when the property binded is changes "fast". The animation is a simple flash of an element. My problem is even after a long time searching on the internet, i can't figure out a way to explain why toggling the property ON and OFF in 2 consecutives lines doesn't work, but if the thread sleeps 1ms it does. I tried inserting other instructions to "waste" some time but it doesn't work either.

Here is the property in question in the viewmodel:

private bool m_activateFlash;
    public bool ActivateFlash
    {
        get { return m_activateFlash; }
        set
        {
            SetPropertyBackingField(ref m_activateFlash, value);
        }
    }

Here is the XAML :

<DataTemplate x:Key="JobTemplate" DataType="viewModel:JobViewModel">
    <Border Margin="8,4,8,4" BorderThickness="1" BorderBrush="{StaticResource BorderBrush}" Background="{StaticResource JobBackgroundBrush}">
        <Border.Resources>
            <Storyboard x:Key="Blink">
                <ColorAnimation  Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)" FillBehavior="Stop" 
                                 Duration="0:0:0.4" To="{StaticResource JobBackgroundFlash}" RepeatBehavior="3x" AutoReverse="True"/>
            </Storyboard>
        </Border.Resources>
        <Border.Style>
            <Style TargetType="Border">
                <Style.Triggers>
                    <DataTrigger Binding="{Binding ActivateFlash, NotifyOnTargetUpdated=True}" Value="True">
                        <DataTrigger.EnterActions>
                            <BeginStoryboard Storyboard="{StaticResource Blink}" Name="BeginBlinkStoryBoard"/>
                        </DataTrigger.EnterActions>
                    </DataTrigger>
                </Style.Triggers>
            </Style>
        </Border.Style>
        [....]

And finally here is where it is causing me problems in the viewmodel :

    private void TriggerFlash()
    {
        ActivateFlash = true;
        System.Threading.Thread.Sleep(1); // HACK DOESN'T WORK WITHOUT THIS LINE
        ActivateFlash = false;
    }

I looked up EventTriggers as maybe a way to circumvent the issue, but I feel DataTrigger is the logical way to achieve what i want. Any help is really appreciated :) EDIT It appears i wasnt invoking Trigger flash on the main thread. Simply calling Dispatcher.Invoke(...) solved the problem

Thanks

Adam

like image 854
Picnic8 Avatar asked Nov 16 '25 22:11

Picnic8


1 Answers

Yeah, if you do:

ActiveFlash = true;
ActiveFlash = false;

You aren't going to see anything on the screen because the UI is on the main thread and it hasn't had time to paint before the value is changed. Toggling the value happens so fast that you aren't going to see anything on the screen.

I believe and somebody can correct me if I'm wrong, but I believe that WPF batches repaints behind the scenes for performance, so you're just stomping over yourself.

like image 96
SledgeHammer Avatar answered Nov 18 '25 12:11

SledgeHammer



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!