Creating Storyboard in code behind in WPF

48,700

Solution 1

When working in code, you don't need Storyboard really, just animations for basic things, like you show in your question. I made a little sample to show how easy it works.

This is the complete code behind of the mainwindow:

namespace WpfCSharpSandbox
{
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            WidenObject(150, TimeSpan.FromSeconds(1));
        }

        private void WidenObject(int newWidth, TimeSpan duration)
        {
            DoubleAnimation animation = new DoubleAnimation(newWidth, duration);
            rctMovingObject.BeginAnimation(Rectangle.WidthProperty, animation);
        }
    }
}

This is how the XAML looks like:

<Window x:Class="WpfCSharpSandbox.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Sandbox" Height="350" Width="525">
    <Grid Background="#333333">
        <Rectangle x:Name="rctMovingObject" Fill="LimeGreen" Width="50" Height="50"/>
    </Grid>
</Window>

Put this in a WPF app and see how it works, experiment with it and try other animations/properties.

Solution 2

Adding djerry's comment sample code would look like this:

var anim = new DoubleAnimation {
                                From = 1920, 
                                To = 1, 
                               };

wnd.BeginAnimation(Window.LeftProperty, anim); 

and you would have to have this code in window loaded event handler. Hope this helps.

Solution 3

The question's example code was about animating the Window.Left property and I was looking for exact that case, but the given answer does work for an one-time use-case only.
Specifically: If the animation has been performed and the Window is then moved manually via drag&drop, the same animation procedure will not work again as desired. The animation will always use the end-coordinates of the recent animation run.
So if you moved the window, it will jump back before starting the new animation:

https://imgur.com/a/hxRCqm7

To solve that issue, it is required to remove any AnimationClock from the animated property after the animation is completed.

That is done by using ApplyAnimationClock or BeginAnimation with null as the second parameter:

public partial class MainWindow : Window
{
    // [...]

    private void ButtonMove_Click(object sender, RoutedEventArgs e)
    {
        AnimateWindowLeft(500, TimeSpan.FromSeconds(1));
    }

    private void AnimateWindowLeft(double newLeft, TimeSpan duration)
    {
        DoubleAnimation animation = new DoubleAnimation(newLeft, duration);
        myWindow.Completed += AnimateLeft_Completed;
        myWindow.BeginAnimation(Window.LeftProperty, animation);
    }

    private void AnimateLeft_Completed(object sender, EventArgs e)
    {
        myWindow.BeginAnimation(Window.LeftProperty, null);
        // or
        // myWindow.ApplyAnimationClock(Window.LeftProperty, null);
    }
}

XAML:

<Window x:Class="WpfAppAnimatedWindowMove.MainWindow"
        // [...]
        Name="myWindow">

Result:
https://imgur.com/a/OZEsP6t

See also Remarks section of Microsoft Docs - HandoffBehavior Enum

Share:
48,700

Related videos on Youtube

Raj
Author by

Raj

Updated on July 24, 2022

Comments

  • Raj
    Raj almost 2 years

    The following code is working fine.

    <Window.Triggers>
        <EventTrigger RoutedEvent="Window.Loaded">
            <BeginStoryboard>
                <Storyboard>
                    <DoubleAnimation Duration="0:0:.8" Storyboard.TargetProperty="Left" From="1920" To="0" AccelerationRatio=".1"/>
                </Storyboard>
            </BeginStoryboard>
        </EventTrigger>
    </Window.Triggers>
    

    But in this From and To values are static. I need to pass the values dynamically based system resolution. So i need it to be created in code behind. Is it possible to do ?

    How to convert it to codebehind?

    • Terry
      Terry about 11 years
      Yes, you can create a Storyboard object in code and apply the same properties as you would do in XAML. Everything can be filled in dynamically based on the input you get.
    • Terry
      Terry about 11 years
      Have you tried searching, there are tons of examples on the internet (example: codeproject.com/Articles/23257/…)
    • Raj
      Raj about 11 years
      yeah the same example i went through. trie this Storyboard sb = new Storyboard(); DoubleAnimation da_AngleAnimation = new DoubleAnimation(); Duration duration = new Duration(TimeSpan.FromSeconds(1)); da_AngleAnimation.Duration = duration; da_AngleAnimation.From = 1920; da_AngleAnimation.To = 100; sb.Duration = duration; sb.BeginAnimation(Window.LeftProperty, da_AngleAnimation); Its not working. am i wrong anywhere ?
    • Terry
      Terry about 11 years
      your storyboard is not hooked up to anything, I guess that might be the problem. Also, what are you trying to achieve, if you just want to start an animation and don't repeat, you don't need the object storyboard, you can just use animation which can be triggered on the object you would like to animate (see my answer).
  • Raj
    Raj about 11 years
    I tried this instead of rectangle DoubleAnimation animation = new DoubleAnimation(1920, 100, duration); page.BeginAnimation(Window.LeftProperty, animation); It works fine as per my requirement
  • Terry
    Terry about 11 years
    I just guess the animation you hooked to your storyboard wasn't invoked properly, but by putting this on window it works.
  • M.kazem Akhgary
    M.kazem Akhgary over 7 years
    I want to stop the animation manualy so using storyboard is required :(
  • Luca Ziegler
    Luca Ziegler almost 5 years
    The question is for a storyboard, so this is not an answer
  • Luca Ziegler
    Luca Ziegler almost 5 years
    The question is for a storyboard, so this is not an answer
  • Suresh
    Suresh almost 5 years
    The OP's question title says storyboard but really the question was about how can he set From and To values on his animation dynamically from code-behind. Ths answer addresses that.
  • AsPas
    AsPas almost 3 years
    How is this the accepted answer? OP wants to know how to do a storyboard in code-behind and the answer is (in classic SO fashion) "you don't need to do 'that', do 'this' instead". Cool, but I want to learn how to do 'that', hence the question, specifically asking about 'THAT'.