Dela via


Översikt över tekniker för egenskapsanimering

Det här avsnittet beskriver de olika metoderna för att animera egenskaper: storyboards, lokala animeringar, klockor och animeringar per bildruta.

Förutsättningar

För att förstå det här avsnittet bör du känna till de grundläggande animeringsfunktionerna som beskrivs i översikten över animering.

Olika sätt att animera

Eftersom det finns många olika scenarier för att animera egenskaper tillhandahåller WPF flera metoder för att animera egenskaper.

För varje metod anger följande tabell om den kan användas per instans, i format, i kontrollmallar eller i datamallar. om den kan användas i XAML; och om metoden gör att du kan styra animeringen interaktivt. "Per instans" refererar till tekniken för att tillämpa en animering eller storyboard direkt på instanser av ett objekt, i stället för i en formatmall, kontrollmall eller datamall.

Animeringsteknik Scenarier Stödjer XAML Interaktivt kontrollerbar
Storyboard animering Per instans Style, ControlTemplate, DataTemplate Ja Ja
Lokal animering Per instans Nej Nej
Klockanimering Per instans Nej Ja
Animering per bildruta Per instans Nej Inte tillgänglig

Storyboard-animeringar

Använd en Storyboard när du vill definiera och tillämpa dina animeringar i XAML, interaktivt styra dina animeringar när de har startat, skapa ett komplext träd med animeringar eller animera i en Style, ControlTemplate eller DataTemplate. För att ett objekt ska animerats av en Storyboardmåste det vara en FrameworkElement eller FrameworkContentElement, eller så måste det användas för att ange en FrameworkElement eller FrameworkContentElement. Mer information finns i översikten över Storyboards.

En Storyboard är en särskild typ av container Timeline som innehåller målinformation för de animeringar som den innehåller. Om du vill animera med en Storyboardslutför du följande tre steg.

  1. Deklarera en Storyboard och en eller flera animeringar.

  2. Använd egenskaperna TargetName och TargetProperty för att ange målobjektet och egenskapen för varje animering.

  3. (Endast kod) Definiera en NameScope för en FrameworkElement eller FrameworkContentElement. Registrera namnen på objekten som ska animeras med hjälp av FrameworkElement eller FrameworkContentElement.

  4. Börja Storyboard.

Om du påbörjar en Storyboard tillämpas animeringar på de egenskaper som de animerar och startar dem. Det finns två sätt att starta en Storyboard: du kan använda metoden Begin som tillhandahålls av klassen Storyboard, eller så kan du använda en BeginStoryboard åtgärd. Det enda sättet att animera i XAML är att använda en BeginStoryboard åtgärd. En BeginStoryboard-åtgärd kan användas i en EventTrigger, egenskap Trigger, eller en DataTrigger.

I följande tabell visas de olika områden där varje Storyboard-börjarteknik stöds: per instans, formatmall, kontrollmall och datamall.

Storyboard har börjat använda... Per instans Stil Kontrollmall Datamall Exempel
BeginStoryboard och en EventTrigger Ja Ja Ja Ja Animera en egenskap med hjälp av en berättelsebräda-
BeginStoryboard och en egendom Trigger Nej Ja Ja Ja utlösa en animering när ett egenskapsvärde ändras
BeginStoryboard och en DataTrigger Nej Ja Ja Ja Så här utlöser du en animering när data ändras
Begin metod Ja Nej Nej Nej Animera en egenskap med hjälp av en berättelsebräda-

Mer information om Storyboard objekt finns i Storyboards Overview.

Lokala animeringar

Lokala animeringar är ett bekvämt sätt att animera en beroendeegenskap för alla Animatable objekt. Använd lokala animeringar när du vill tillämpa en enda animering på en egenskap och du inte behöver styra animeringen interaktivt när den har startats. Till skillnad från en Storyboard animering kan en lokal animering animera ett objekt som inte är associerat med en FrameworkElement eller en FrameworkContentElement. Du behöver inte heller definiera en NameScope för den här typen av animering.

Lokala animeringar kan endast användas i kod och kan inte definieras i format, kontrollmallar eller datamallar. En lokal animering kan inte styras interaktivt när den har startats.

Utför följande steg för att animera med hjälp av en lokal animering.

  1. Skapa ett AnimationTimeline objekt.

  2. Använd BeginAnimation-metoden för det objekt som du vill animera för att tillämpa AnimationTimeline på den egenskap som du anger.

I följande exempel visas hur du animerar bredden och bakgrundsfärgen för en Button.

/*

   This sample demonstrates how to apply non-storyboard animations to a property.
   To animate in markup, you must use storyboards.

*/

using namespace System;
using namespace System::Windows;
using namespace System::Windows::Navigation;
using namespace System::Windows::Media;
using namespace System::Windows::Media::Animation;
using namespace System::Windows::Shapes;
using namespace System::Windows::Controls;


namespace Microsoft {
   namespace Samples {
      namespace Animation {
         namespace LocalAnimations {
            // Create the demonstration.
            public ref class LocalAnimationExample : Page {

            public: 
               LocalAnimationExample ()
               {
                  WindowTitle = "Local Animation Example";
                  StackPanel^ myStackPanel = gcnew StackPanel();
                  myStackPanel->Margin = Thickness(20);

                  // Create and set the Button.
                  Button^ aButton = gcnew Button();
                  aButton->Content = "A Button";

                  // Animate the Button's Width.
                  DoubleAnimation^ myDoubleAnimation = gcnew DoubleAnimation();
                  myDoubleAnimation->From = 75;
                  myDoubleAnimation->To = 300;
                  myDoubleAnimation->Duration = Duration(TimeSpan::FromSeconds(5));
                  myDoubleAnimation->AutoReverse = true;
                  myDoubleAnimation->RepeatBehavior = RepeatBehavior::Forever;

                  // Apply the animation to the button's Width property.
                  aButton->BeginAnimation(Button::WidthProperty, myDoubleAnimation);

                  // Create and animate a Brush to set the button's Background.
                  SolidColorBrush^ myBrush = gcnew SolidColorBrush();
                  myBrush->Color = Colors::Blue;

                  ColorAnimation^ myColorAnimation = gcnew ColorAnimation();
                  myColorAnimation->From = Colors::Blue;
                  myColorAnimation->To = Colors::Red;
                  myColorAnimation->Duration = Duration(TimeSpan::FromMilliseconds(7000));
                  myColorAnimation->AutoReverse = true;
                  myColorAnimation->RepeatBehavior = RepeatBehavior::Forever;

                  // Apply the animation to the brush's Color property.
                  myBrush->BeginAnimation(SolidColorBrush::ColorProperty, myColorAnimation);
                  aButton->Background = myBrush;

                  // Add the Button to the panel.
                  myStackPanel->Children->Add(aButton);
                  this->Content = myStackPanel;
               };
            };
         }
      }
   }
}
/*

   This sample demonstrates how to apply non-storyboard animations to a property.
   To animate in markup, you must use storyboards.

*/

using System;
using System.Windows;
using System.Windows.Navigation;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.Windows.Controls;

namespace Microsoft.Samples.Animation.LocalAnimations
{

    // Create the demonstration.
    public class LocalAnimationExample : Page
    {

        public LocalAnimationExample()
        {

            WindowTitle = "Local Animation Example";
            StackPanel myStackPanel = new StackPanel();
            myStackPanel.Margin = new Thickness(20);

            // Create and set the Button.
            Button aButton = new Button();
            aButton.Content = "A Button";

            // Animate the Button's Width.
            DoubleAnimation myDoubleAnimation = new DoubleAnimation();
            myDoubleAnimation.From = 75;
            myDoubleAnimation.To = 300;
            myDoubleAnimation.Duration =  new Duration(TimeSpan.FromSeconds(5));
            myDoubleAnimation.AutoReverse = true;
            myDoubleAnimation.RepeatBehavior = RepeatBehavior.Forever;

            // Apply the animation to the button's Width property.
            aButton.BeginAnimation(Button.WidthProperty, myDoubleAnimation);

            // Create and animate a Brush to set the button's Background.
            SolidColorBrush myBrush = new SolidColorBrush();
            myBrush.Color = Colors.Blue;

            ColorAnimation myColorAnimation = new ColorAnimation();
            myColorAnimation.From = Colors.Blue;
            myColorAnimation.To = Colors.Red;
            myColorAnimation.Duration =  new Duration(TimeSpan.FromMilliseconds(7000));
            myColorAnimation.AutoReverse = true;
            myColorAnimation.RepeatBehavior = RepeatBehavior.Forever;

            // Apply the animation to the brush's Color property.
            myBrush.BeginAnimation(SolidColorBrush.ColorProperty, myColorAnimation);
            aButton.Background = myBrush;

            // Add the Button to the panel.
            myStackPanel.Children.Add(aButton);
            this.Content = myStackPanel;
        }
    }
}
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'''This sample demonstrates how to apply non-storyboard animations to a property.
'''To animate in markup, you must use storyboards.
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

Imports System.Windows
Imports System.Windows.Navigation
Imports System.Windows.Media
Imports System.Windows.Media.Animation
Imports System.Windows.Shapes
Imports System.Windows.Controls

Namespace Microsoft.Samples.Animation.LocalAnimations

    ' Create the demonstration.
    Public Class LocalAnimationExample
        Inherits Page

        Public Sub New()

            WindowTitle = "Animate Property Example"
            Dim myStackPanel As New StackPanel()
            myStackPanel.Margin = New Thickness(20)

            ' Create and set the Button.
            Dim aButton As New Button()
            aButton.Content = "A Button"

            ' Animate the Button's Width.
            Dim myDoubleAnimation As New DoubleAnimation()
            myDoubleAnimation.From = 75
            myDoubleAnimation.To = 300
            myDoubleAnimation.Duration = New Duration(TimeSpan.FromSeconds(5))
            myDoubleAnimation.AutoReverse = True
            myDoubleAnimation.RepeatBehavior = RepeatBehavior.Forever

            ' Apply the animation to the button's Width property.
            aButton.BeginAnimation(Button.WidthProperty, myDoubleAnimation)

            ' Create and animate a Brush to set the button's Background.
            Dim myBrush As New SolidColorBrush()
            myBrush.Color = Colors.Blue

            Dim myColorAnimation As New ColorAnimation()
            myColorAnimation.From = Colors.Blue
            myColorAnimation.To = Colors.Red
            myColorAnimation.Duration = New Duration(TimeSpan.FromMilliseconds(7000))
            myColorAnimation.AutoReverse = True
            myColorAnimation.RepeatBehavior = RepeatBehavior.Forever

            ' Apply the animation to the brush's Color property.
            myBrush.BeginAnimation(SolidColorBrush.ColorProperty, myColorAnimation)
            aButton.Background = myBrush

            ' Add the Button to the panel.
            myStackPanel.Children.Add(aButton)
            Me.Content = myStackPanel
        End Sub
    End Class
End Namespace

Klockanimeringar

Använd Clock objekt när du vill animera utan att använda en Storyboard och du vill skapa komplexa tidsträd eller interaktivt styra animeringar när de har startats. Du kan använda klockobjekt för att animera en beroendeegenskap för alla Animatable objekt.

Du kan inte använda Clock-objekt direkt för att animera i stilar, kontrollmallar eller datamallar. (Systemet för animering och tidsinställning använder faktiskt Clock objekt för att animera format, kontrollmallar och datamallar, men det måste skapa dessa Clock objekt åt dig från en Storyboard. Mer information om relationen mellan Storyboard objekt och Clock objekt finns i Översikt över animerings- och tidsschemasystem.)

Om du vill tillämpa en enda Clock på en egenskap slutför du följande steg.

  1. Skapa ett AnimationTimeline objekt.

  2. Använd metoden CreateClock för AnimationTimeline för att skapa en AnimationClock.

  3. Använd metoden ApplyAnimationClock för det objekt som du vill animera för att tillämpa AnimationClock på den egenskap som du anger.

I följande exempel visas hur du skapar en AnimationClock och tillämpar den på två liknande egenskaper.

/*
    This example shows how to create and apply
    an AnimationClock.
*/

using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;
using System.Windows.Shapes;
using System.Windows.Media.Animation;

namespace Microsoft.Samples.Animation.TimingBehaviors
{
    public class AnimationClockExample : Page
    {

        ScaleTransform myScaleTransform;

        public AnimationClockExample()
        {

            this.WindowTitle = "Opacity Animation Example";
            this.Background = Brushes.White;
            StackPanel myStackPanel = new StackPanel();
            myStackPanel.Margin = new Thickness(20);

            // Create a button that with a ScaleTransform.
            // The ScaleTransform will animate when the
            // button is clicked.
            Button myButton = new Button();
            myButton.Margin = new Thickness(50);
            myButton.HorizontalAlignment = HorizontalAlignment.Left;
            myButton.Content = "Click Me";
            myScaleTransform = new ScaleTransform(1,1);
            myButton.RenderTransform = myScaleTransform;

            // Associate an event handler with the
            // button's Click event.
            myButton.Click += new RoutedEventHandler(myButton_Clicked);

            myStackPanel.Children.Add(myButton);
            this.Content = myStackPanel;
        }

        // Create and apply and animation when the button is clicked.
        private void myButton_Clicked(object sender, RoutedEventArgs e)
        {

            // Create a DoubleAnimation to animate the
            // ScaleTransform.
            DoubleAnimation myAnimation =
                new DoubleAnimation(
                    1, // "From" value
                    5, // "To" value
                    new Duration(TimeSpan.FromSeconds(5))
                );
            myAnimation.AutoReverse = true;

            // Create a clock the for the animation.
            AnimationClock myClock = myAnimation.CreateClock();

            // Associate the clock the ScaleX and
            // ScaleY properties of the button's
            // ScaleTransform.
            myScaleTransform.ApplyAnimationClock(
                ScaleTransform.ScaleXProperty, myClock);
            myScaleTransform.ApplyAnimationClock(
                ScaleTransform.ScaleYProperty, myClock);
        }
    }
}
'
'    This example shows how to create and apply
'    an AnimationClock.
'


Imports System.Windows
Imports System.Windows.Controls
Imports System.Windows.Media
Imports System.Windows.Shapes
Imports System.Windows.Media.Animation


Namespace Microsoft.Samples.Animation.TimingBehaviors
    Public Class AnimationClockExample
        Inherits Page

        Private ReadOnly myScaleTransform As ScaleTransform

        Public Sub New()

            WindowTitle = "Opacity Animation Example"
            Background = Brushes.White
            Dim myStackPanel As New StackPanel With {
                .Margin = New Thickness(20)
            }

                ' Create a button that with a ScaleTransform.
                ' The ScaleTransform will animate when the
                ' button is clicked.
            Dim myButton As New Button With {
                .Margin = New Thickness(50),
                .HorizontalAlignment = HorizontalAlignment.Left,
                .Content = "Click Me"
            }
            myScaleTransform = New ScaleTransform(1,1)
            myButton.RenderTransform = myScaleTransform


            ' Associate an event handler with the
            ' button's Click event.
            AddHandler myButton.Click, AddressOf myButton_Clicked

            myStackPanel.Children.Add(myButton)
            Content = myStackPanel
        End Sub

        ' Create and apply and animation when the button is clicked.
        Private Sub myButton_Clicked(sender As Object, e As RoutedEventArgs)

            ' Create a DoubleAnimation to animate the
            ' ScaleTransform.
            Dim myAnimation As New DoubleAnimation(1, 5, New Duration(TimeSpan.FromSeconds(5))) With {
                .AutoReverse = True
            } ' "To" value -  "From" value

            ' Create a clock the for the animation.
            Dim myClock As AnimationClock = myAnimation.CreateClock()

            ' Associate the clock the ScaleX and
            ' ScaleY properties of the button's
            ' ScaleTransform.
            myScaleTransform.ApplyAnimationClock(ScaleTransform.ScaleXProperty, myClock)
            myScaleTransform.ApplyAnimationClock(ScaleTransform.ScaleYProperty, myClock)
        End Sub
    End Class
End Namespace

Om du vill skapa ett tidsträd och använda det för att animera egenskaper slutför du följande steg.

  1. Använd ParallelTimeline- och AnimationTimeline-objekt för att skapa tidsträdet.

  2. Använd CreateClock för roten ParallelTimeline för att skapa en ClockGroup.

  3. Iterera genom Children i ClockGroup och tillämpa dess underordnade objekt Clock. För varje AnimationClock underordnad använder du metoden ApplyAnimationClock för det objekt som du vill animera för att tillämpa AnimationClock på den egenskap som du anger

Mer information om klockobjekt finns i Översikt över animerings- och tidsschemasystem.

Per-Frame animering: Kringgå animerings- och tidsschemat

Använd den här metoden när du helt behöver kringgå WPF-animeringssystemet. Ett scenario för den här metoden är fysikanimationer, där varje steg i animeringen kräver att objekt omberäknas baserat på den senaste uppsättningen objektinteraktioner.

Animeringar per bildruta kan inte definieras i format, kontrollmallar eller datamallar.

Om du vill animera bildruta för bildruta registrerar du dig för den Rendering händelsen för objektet som innehåller de objekt som du vill animera. Den här händelsehanterarmetoden anropas en gång per bildruta. Varje gång WPF konverterar beständiga återgivningsdata i det visuella trädet till kompositionsträdet anropas händelsehanterarmetoden.

I händelsehanteraren utför du de beräkningar som krävs för animeringseffekten och anger egenskaperna för de objekt som du vill animera med dessa värden.

För att få presentationstiden för den aktuella bildrutan kan EventArgs som är associerad med den här händelsen omvandlas till RenderingEventArgs, vilket ger en RenderingTime-egenskap som du kan använda för att få den aktuella bildrutans renderingstid.

Mer information finns på sidan Rendering.

Se även