Today is Day #11 of the 31 Days of Silverlight, and today we’re going to take an intimate look at animation, and how you do it. We’re going to focus much more on the tools today than the code, which is how most of these tutorials have gone this far. On Day #2, we worked on Silverlight Screen Transitions, and while we had a slight animation in it, we didn’t spend much time talking about how it was created. Today’s post will answer that question.
Introducing Expression Blend
Expression Blend is a tool for making your Silverlight and WPF development vastly simpler. As you may have noticed in the previous examples, we are writing ALL of our XAML by hand. That is certainly not the optimal way to do development. I should be able to drag my shapes around on the canvas, to get them in exactly the right position. That’s where Expression Blend comes in. We’re going to use Blend today to create our animation.
Our solution structure
At this point, you should be familiar with the structure of a Silverlight project, and the accompanying web project that make up our solution. Blend uses these same files. The same solution files, project files, everything. When you work on a project in Blend, you’re working on the same exact files you used in Visual Studio. You’ll see many of the features of Blend show up in Visual Studio 10 as well.
Drawing a car
For this article, we are going to create a car, a road, and some happy little trees. Then, we’re going to make them move in such a way that it appears the car is driving down a road. So let’s start with the car. In Blend, open up your Page.xaml file. By default, and for consistency in my demos, our canvas is 400 x 300. But since you can zoom in and out, size doesn’t matter for once. Since this isn’t a tutorial on being an artist, I’m not going to spend a ton of time making it look nice. I’m going to focus on animating. Here’s our car, visually:
Nothing spectacular to look at, but it will certainly get the job done. Nobody will question that it’s a car, even if it is amateurish. Here’s the XAML that Blend created for me that represents the car. You’ll notice that I’ve grouped certain elements into seperate Canvas elements, and this is because we’re going to have spinning tires, among other movement in this animation.
<UserControl x:Class="SilverlightCarAnimation.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Width="400" Height="300" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d">
<Grid x:Name="LayoutRoot" Background="White">
<Canvas Margin="83.499,104,115.501,84" x:Name="Car">
<Canvas Height="79" x:Name="CarBody" Width="201">
<Rectangle Height="40" Width="86" Canvas.Left="58.501" Fill="#FFFF0000" Stroke="{x:Null}"/>
<Rectangle Fill="#FFFF0000" Stroke="{x:Null}" Height="40" Width="201" Canvas.Top="39" RadiusX="0" RadiusY="0"/>
<Rectangle Height="27" Width="46" Canvas.Left="98.502" Canvas.Top="12" Stroke="{x:Null}" RadiusX="0" RadiusY="0">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF188CB7" Offset="0"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="BackWheel" Width="49" Canvas.Left="14.168" Canvas.Top="62.662">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Canvas.Left="11.333" Canvas.Top="11.672" Fill="#FFBBB9B9" Stroke="{x:Null}"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Canvas.Left="24.333" Canvas.Top="11.339" Fill="#FF000000" Stroke="{x:Null}">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.333" Canvas.Top="11.339">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="FrontWheel" Width="49" Canvas.Left="143.168" Canvas.Top="63">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Fill="#FFBBB9B9" Stroke="{x:Null}" Canvas.Left="11" Canvas.Top="11"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
</Canvas>
</Grid>
</UserControl>
Adding a road
The road, in a static picture would be pretty easy to create. A black rectangle with some yellow dashes on it. However, our car will be driving, so those yellow lines will have to move as well. What I plan to do is make a line of yellow dashes that are twice as wide as my Silverlight app. This way, I can slide it to the left, and when I get to the end, I can just repeat the scrolling from the original position over and over. Here’s a picture of our car on the new road:
Here’s the new XAML:
<UserControl x:Class="SilverlightCarAnimation.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Width="400" Height="300" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d">
<Grid x:Name="LayoutRoot" Background="White">
<Rectangle Height="84" VerticalAlignment="Bottom" Fill="#FF000000" Stroke="{x:Null}" x:Name="Road"/>
<StackPanel Height="24" VerticalAlignment="Bottom" Orientation="Horizontal" Margin="0,0,-448,30" x:Name="LineStripe">
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
</StackPanel>
<Canvas Margin="49,0,150,24" x:Name="Car" VerticalAlignment="Bottom" Height="112">
<Canvas Height="79" x:Name="CarBody" Width="201">
<Rectangle Height="40" Width="86" Canvas.Left="58.501" Fill="#FFFF0000" Stroke="{x:Null}"/>
<Rectangle Fill="#FFFF0000" Stroke="{x:Null}" Height="40" Width="201" Canvas.Top="39" RadiusX="0" RadiusY="0"/>
<Rectangle Height="27" Width="46" Canvas.Left="98.502" Canvas.Top="12" Stroke="{x:Null}" RadiusX="0" RadiusY="0">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF188CB7" Offset="0"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="BackWheel" Width="49" Canvas.Left="14.168" Canvas.Top="62.662">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Canvas.Left="11.333" Canvas.Top="11.672" Fill="#FFBBB9B9" Stroke="{x:Null}"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Canvas.Left="24.333" Canvas.Top="11.339" Fill="#FF000000" Stroke="{x:Null}">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.333" Canvas.Top="11.339">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="FrontWheel" Width="49" Canvas.Left="143.168" Canvas.Top="63">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Fill="#FFBBB9B9" Stroke="{x:Null}" Canvas.Left="11" Canvas.Top="11"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
</Canvas>
</Grid>
</UserControl>
Building some scenery
We’ve got a couple more things to add to this scene to make it complete. A sky, for one, would be useful. After that, I’m going to add a couple of clouds, and a tree. For simplicity’s sake, I’m not going to show you the progressive XAML for each step, instead, here’s what our final scene looks like, as well as the XAML to create it:
<UserControl x:Class="SilverlightCarAnimation.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Width="400" Height="300" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d">
<Grid x:Name="LayoutRoot" Background="White">
<Rectangle Margin="0,0,0,84" Stroke="#FF000000" x:Name="Sky">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF77C4C4"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
<Path Height="82" HorizontalAlignment="Right" VerticalAlignment="Top" Width="140" Fill="#FFFFFFFF" Stretch="Fill" Stroke="#FFCECECE" StrokeThickness="3" Data="M106,0.5 C112.0061,0.49999714 117.15929,4.1516743 119.36052,9.3559399 L119.37662,9.4078083 L120.74696,7.7469482 C123.37094,5.1229649 126.99594,3.4999971 131,3.499999 C136.00508,3.4999971 140.41788,6.0358849 143.02364,9.8929119 L143.02887,9.9025707 L145.35594,8.6394768 C147.0907,7.9057388 148.99797,7.4999971 151,7.4999943 C155.00406,7.4999971 158.62906,9.1229649 161.25305,11.746948 L162,12.652259 L162.74695,11.746948 C165.37094,9.1229649 168.99594,7.4999971 173,7.4999943 C180.00711,7.4999971 185.85335,12.470336 187.20541,19.077738 L187.39322,20.940781 L189.64406,21.639479 C193.54726,23.290394 196.57713,26.601799 197.84811,30.688139 L198.44806,34.656448 L200,34.499996 C208.00813,34.499996 214.5,40.991867 214.5,48.999996 C214.5,51.502537 213.86603,53.857006 212.74992,55.91156 L210.99924,58.375053 L212.10709,58.976372 C215.96411,61.582123 218.5,65.994919 218.5,71 C218.5,75.004066 216.87703,78.629066 214.25305,81.253052 L213.41562,81.943993 L215.02364,83.892914 C216.58708,86.20713 217.5,88.996956 217.5,92 C217.5,100.00813 211.00813,106.5 203,106.5 C197.74466,106.5 193.14232,103.70418 190.59921,99.518776 L190.28737,98.890793 L190.5,101 C190.5,109.00813 184.00813,115.5 176,115.5 C171.99594,115.5 168.37094,113.87703 165.74695,111.25304 L164.98895,110.33434 L164.40079,111.51878 C161.85768,115.70418 157.25534,118.5 152,118.5 C149.99797,118.5 148.0907,118.09425 146.35594,117.36052 L144.84227,116.53892 L144.25305,117.25304 C141.62906,119.87703 138.00406,121.5 134,121.5 C131.99797,121.5 130.0907,121.09426 128.35594,120.36052 L126.15287,119.16473 L124.10709,121.02363 C121.79287,122.58708 119.00305,123.5 116,123.5 C110.99492,123.5 106.58213,120.96411 103.97637,117.10709 L103.00845,115.32383 L101.27191,115.26254 L101.20541,115.92226 C99.85334,122.52966 94.007111,127.5 87,127.5 C78.991875,127.5 72.5,121.00813 72.5,113 L72.575935,112.24673 L72.488472,112.23186 L72.360519,112.64405 C70.159302,117.84832 65.006096,121.5 59,121.5 C54.995934,121.5 51.370934,119.87703 48.746952,117.25304 L47.686768,115.96809 L46.922256,116.20541 C45.97834,116.39857 45.001015,116.5 44,116.5 C37.993904,116.5 32.840702,112.84832 30.639482,107.64405 L29.883694,105.2093 L26.999996,105.5 C19.992887,105.5 14.14666,100.52966 12.79459,93.922256 L12.525257,91.250526 L12.077744,91.205414 C5.4703388,89.85334 0.5,84.007111 0.5,77 C0.5,71.994919 3.0358872,67.582123 6.8929138,64.976372 L8.70366,63.993526 L8.8091211,62.954491 L6.746954,61.253044 C4.1229677,58.629063 2.5,55.004063 2.500001,50.999996 C2.5,42.991867 8.9918709,36.499996 17,36.5 C18.001017,36.499996 18.97834,36.601433 19.922255,36.794582 L22.276466,37.525379 L22.639484,36.355953 C24.840702,31.151674 29.993904,27.499996 35.999996,27.499992 C37.001015,27.499996 37.97834,27.601433 38.922256,27.79459 L39.333214,27.922153 L38.639477,26.644054 C37.905743,24.909294 37.5,23.002029 37.5,21 C37.5,12.991868 43.991871,6.4999971 52,6.4999943 C60.008129,6.4999971 66.5,12.991868 66.5,21 L66.488525,21.113777 L67.688309,20.867964 L67.5,19 C67.5,10.991869 73.991875,4.4999971 82,4.499999 C85.503555,4.4999971 88.716888,5.7425823 91.223343,7.8110962 L92.618721,9.4228325 L92.639481,9.3559399 C94.840706,4.1516743 99.993904,0.49999714 106,0.5 z" x:Name="Cloud1" Margin="0,17,33,0"/>
<Rectangle Height="84" x:Name="Road" VerticalAlignment="Bottom" Fill="#FF000000" Stroke="{x:Null}"/>
<StackPanel Height="24" VerticalAlignment="Bottom" Orientation="Horizontal" Margin="0,0,-448,30" x:Name="LineStripe">
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
</StackPanel>
<Canvas HorizontalAlignment="Left" Margin="8,30,0,84" x:Name="Tree" Width="151">
<Rectangle Height="104" Width="19" Fill="#FF6E4100" Stroke="#FF000000" StrokeThickness="3" Canvas.Left="66" Canvas.Top="82"/>
<Path Width="151" Fill="#FF3FA33D" Stretch="Fill" Stroke="#FF000000" Data="M48,0 C56.284271,0 63.784271,3.3578644 69.213203,8.7867975 L72.336609,12.572392 L73.496292,11.902077 C77.628952,10.011786 81.991112,9 86.5,9.000001 C97.259842,9 107.18409,14.76185 115.14809,24.474262 L117.88708,28.136744 L119.32265,27.357546 C122.9118,25.839466 126.85786,25 131,25.000002 C147.56854,25 161,38.431458 161,55 C161,59.142136 160.16054,63.088203 158.64246,66.677353 L156.6917,70.271347 L160.04605,70.609497 C173.71654,73.406883 184,85.502525 184,100 C184,116.56854 170.56854,130 154,130 L150.82446,129.67987 L151,132 C151,148.56854 137.56854,162 121,162 C114.7868,162 109.01475,160.11121 104.22672,156.87646 L103.91651,156.62053 L100.62505,158.56071 C96.162949,160.7959 91.418785,162 86.5,162 C79.94162,162 73.69368,159.85936 68.010857,155.98825 L66.897095,155.12416 L64.773285,156.87646 C59.985252,160.11121 54.213203,162 48,162 C31.431458,162 18,148.56854 18.000002,132 C18,124.2335 20.951248,117.1563 25.793457,111.82867 L26.981792,110.69574 L23.953953,110.3905 C10.283459,107.59312 0,95.497475 0,81 C0,66.502525 10.283459,54.406883 23.953953,51.609493 L26.906376,51.311863 L26.786798,51.213203 C21.357864,45.784271 18,38.284271 18.000002,30.000002 C18,13.431458 31.431458,0 48,0 z" StrokeThickness="3" Height="113"/>
</Canvas>
<Canvas Height="112" Margin="49,0,150,24" x:Name="Car" VerticalAlignment="Bottom">
<Canvas Height="79" x:Name="CarBody" Width="201">
<Rectangle Height="40" Width="86" Canvas.Left="58.501" Fill="#FFFF0000" Stroke="{x:Null}"/>
<Rectangle Fill="#FFFF0000" Stroke="{x:Null}" Height="40" Width="201" Canvas.Top="39" RadiusX="0" RadiusY="0"/>
<Rectangle Height="27" Width="46" Canvas.Left="98.502" Canvas.Top="12" Stroke="{x:Null}" RadiusX="0" RadiusY="0">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF188CB7" Offset="0"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="BackWheel" Width="49" Canvas.Left="14.168" Canvas.Top="62.662">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Canvas.Left="11.333" Canvas.Top="11.672" Fill="#FFBBB9B9" Stroke="{x:Null}"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Canvas.Left="24.333" Canvas.Top="11.339" Fill="#FF000000" Stroke="{x:Null}">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.333" Canvas.Top="11.339">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="FrontWheel" Width="49" Canvas.Left="143.168" Canvas.Top="63">
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Fill="#FFBBB9B9" Stroke="{x:Null}" Canvas.Left="11" Canvas.Top="11"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24.666" Canvas.Top="11">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
</Canvas>
</Grid>
</UserControl>
Time to start animating
Now that we have all of our XAML elements defined, we can start animating them. The first thing I have decided is that my driving animation will take 15 seconds. This should give me a good amount of time to see the car moving, and get some trees and clouds moving as well. First, you want to actually create the animation, called a StoryBoard. We do this by clicking the “+” symbol on the Objects and Timeline panel.
After you name your timeline (I called mine “Driving”), Blend will be in “recording” mode. What this basically means is that it will be recording the changes you make as part of the animation. You can turn recording on and off by clicking the red circle at the top of the window.
Making the wheels spin
Select the “BackWheel” element from our list of Objects, and click the “Record KeyFrame” button. If you’re not familiar with this button, it looks like this:
Creating a keyframe at Zero seconds basically means that this is the position we want this wheel to start at. Next, move the yellow vertical time marker to the “1” position. This is one second of animation time. Here, click the KeyFrame button again, and then change the RenderTransform angle to 360 degrees. This can be found in the Properties Tab, under the Transform section. After that, click the Play button. (It’s right above the KeyFrame button.) You should see your tire spin one revolution in 1 second. Now make the same animation on the FrontWheel element. You’ve now got two moving wheels on your car. But the car itself doesn’t move yet.
To move the car, we need to select the “Car” object from our list. (Make sure the yellow time slider is back to zero, too.) We want it to move across the screen from left to right. So, create the initial KeyFrame at zero, and then move the slider out to 15 seconds. Here, drag the car to a position off of the right side of the screen. You’re not going to be able to drag it perfectly horizontal, so just make your best effort. We’ll clean up the XAML to correct this. In your XAML, look near the top for a block that looks like this:
<UserControl.Resources>
<Storyboard x:Name="Driving">
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="BackWheel" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[2].(RotateTransform.Angle)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:01" Value="360"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="FrontWheel" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[2].(RotateTransform.Angle)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:01" Value="360"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Car" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.X)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="500"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Car" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.Y)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="-3"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</UserControl.Resources>
You can see that two of the <DoubleAnimationUsingKeyFrames> blocks reference “Car” at their Target. One of them is for the X axis, and the other is for the Y axis. Since we want our car to move only on the X axis, you can completely delete the Y axis block. My X value is 500, but you can make it travel faster or slower by changing this number.
If you click the Play button now, your car should move down the road, tires a-spinning. What you may notice, however, is that the tires only spin for the first second of animation, and then they stop. That’s because we haven’t told them to continue repeating their animation forever. The easiest way to do this is just to edit the XAML, but I’m working in Expression Blend today, so I’ll show you how to do it with just your mouse. If you expand the arrows next to “BackWheel” completely, you will find an “Angle” attribute listed there. Here’s a visual:
If you right-click on this “Angle” attribute, it allows you to “Edit Repeat Count.” You can specify any integer value in this box, but there’s also an infinity button to the right of the box. This means that we want this animation to continue on for as long as our animation is going. Set this value to infinity for both the front and back wheels of our car. While this change will not be reflected when you click the “Play” button, when you build and run the application (F5), your tires will continue to spin. (Animation not starting? That’s because we need to tell the application to start it. In your XAML code-behind, add one line to your startup method:
Driving.Begin();
So there we go. We’ve got a moving car.
Animating the other stuff
The other things I wanted to animate in this little movie are the lines on the road, the tree, and the cloud. I’m going to be using the exact same methods that I used for moving the car, just in the other direction. In order to be appropriate in speed, the tree and the lines will have to move the same speed as the car. This should almost give the effect that there is a cameraman that isn’t quite keeping up with the moving car. Once we get everything moving appropriately, we end up with some XAML that looks something like this:
<UserControl x:Class="SilverlightCarAnimation.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Width="400" Height="300" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d">
<UserControl.Resources>
<Storyboard x:Name="Driving">
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="BackWheel" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[2].(RotateTransform.Angle)" RepeatBehavior="Forever">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:01" Value="360"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="FrontWheel" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[2].(RotateTransform.Angle)" RepeatBehavior="Forever">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:01" Value="360"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Car" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.X)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="500"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Car" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.Y)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="-3"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="LineStripe" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.X)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="-500"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Tree" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.X)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="-500"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Cloud" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.X)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="-147"/>
</DoubleAnimationUsingKeyFrames>
<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="Cloud" Storyboard.TargetProperty="(UIElement.RenderTransform).(TransformGroup.Children)[3].(TranslateTransform.Y)">
<SplineDoubleKeyFrame KeyTime="00:00:00" Value="0"/>
<SplineDoubleKeyFrame KeyTime="00:00:15" Value="11"/>
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</UserControl.Resources>
<Grid x:Name="LayoutRoot" Background="White">
<Rectangle Margin="0,0,0,84" Stroke="#FF000000" x:Name="Sky">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF77C4C4"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
<Path Height="82" HorizontalAlignment="Right" VerticalAlignment="Top" Width="140" Fill="#FFFFFFFF" Stretch="Fill" Stroke="#FFCECECE" StrokeThickness="3" Data="M106,0.5 C112.0061,0.49999714 117.15929,4.1516743 119.36052,9.3559399 L119.37662,9.4078083 L120.74696,7.7469482 C123.37094,5.1229649 126.99594,3.4999971 131,3.499999 C136.00508,3.4999971 140.41788,6.0358849 143.02364,9.8929119 L143.02887,9.9025707 L145.35594,8.6394768 C147.0907,7.9057388 148.99797,7.4999971 151,7.4999943 C155.00406,7.4999971 158.62906,9.1229649 161.25305,11.746948 L162,12.652259 L162.74695,11.746948 C165.37094,9.1229649 168.99594,7.4999971 173,7.4999943 C180.00711,7.4999971 185.85335,12.470336 187.20541,19.077738 L187.39322,20.940781 L189.64406,21.639479 C193.54726,23.290394 196.57713,26.601799 197.84811,30.688139 L198.44806,34.656448 L200,34.499996 C208.00813,34.499996 214.5,40.991867 214.5,48.999996 C214.5,51.502537 213.86603,53.857006 212.74992,55.91156 L210.99924,58.375053 L212.10709,58.976372 C215.96411,61.582123 218.5,65.994919 218.5,71 C218.5,75.004066 216.87703,78.629066 214.25305,81.253052 L213.41562,81.943993 L215.02364,83.892914 C216.58708,86.20713 217.5,88.996956 217.5,92 C217.5,100.00813 211.00813,106.5 203,106.5 C197.74466,106.5 193.14232,103.70418 190.59921,99.518776 L190.28737,98.890793 L190.5,101 C190.5,109.00813 184.00813,115.5 176,115.5 C171.99594,115.5 168.37094,113.87703 165.74695,111.25304 L164.98895,110.33434 L164.40079,111.51878 C161.85768,115.70418 157.25534,118.5 152,118.5 C149.99797,118.5 148.0907,118.09425 146.35594,117.36052 L144.84227,116.53892 L144.25305,117.25304 C141.62906,119.87703 138.00406,121.5 134,121.5 C131.99797,121.5 130.0907,121.09426 128.35594,120.36052 L126.15287,119.16473 L124.10709,121.02363 C121.79287,122.58708 119.00305,123.5 116,123.5 C110.99492,123.5 106.58213,120.96411 103.97637,117.10709 L103.00845,115.32383 L101.27191,115.26254 L101.20541,115.92226 C99.85334,122.52966 94.007111,127.5 87,127.5 C78.991875,127.5 72.5,121.00813 72.5,113 L72.575935,112.24673 L72.488472,112.23186 L72.360519,112.64405 C70.159302,117.84832 65.006096,121.5 59,121.5 C54.995934,121.5 51.370934,119.87703 48.746952,117.25304 L47.686768,115.96809 L46.922256,116.20541 C45.97834,116.39857 45.001015,116.5 44,116.5 C37.993904,116.5 32.840702,112.84832 30.639482,107.64405 L29.883694,105.2093 L26.999996,105.5 C19.992887,105.5 14.14666,100.52966 12.79459,93.922256 L12.525257,91.250526 L12.077744,91.205414 C5.4703388,89.85334 0.5,84.007111 0.5,77 C0.5,71.994919 3.0358872,67.582123 6.8929138,64.976372 L8.70366,63.993526 L8.8091211,62.954491 L6.746954,61.253044 C4.1229677,58.629063 2.5,55.004063 2.500001,50.999996 C2.5,42.991867 8.9918709,36.499996 17,36.5 C18.001017,36.499996 18.97834,36.601433 19.922255,36.794582 L22.276466,37.525379 L22.639484,36.355953 C24.840702,31.151674 29.993904,27.499996 35.999996,27.499992 C37.001015,27.499996 37.97834,27.601433 38.922256,27.79459 L39.333214,27.922153 L38.639477,26.644054 C37.905743,24.909294 37.5,23.002029 37.5,21 C37.5,12.991868 43.991871,6.4999971 52,6.4999943 C60.008129,6.4999971 66.5,12.991868 66.5,21 L66.488525,21.113777 L67.688309,20.867964 L67.5,19 C67.5,10.991869 73.991875,4.4999971 82,4.499999 C85.503555,4.4999971 88.716888,5.7425823 91.223343,7.8110962 L92.618721,9.4228325 L92.639481,9.3559399 C94.840706,4.1516743 99.993904,0.49999714 106,0.5 z" x:Name="Cloud" Margin="0,17,33,0" RenderTransformOrigin="0.5,0.5">
<Path.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Path.RenderTransform>
</Path>
<Rectangle Height="84" x:Name="Road" VerticalAlignment="Bottom" Fill="#FF000000" Stroke="{x:Null}"/>
<StackPanel Height="24" VerticalAlignment="Bottom" Orientation="Horizontal" Margin="0,0,-608,30" x:Name="LineStripe" RenderTransformOrigin="0.5,0.5">
<StackPanel.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</StackPanel.RenderTransform>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
<Rectangle Height="9" Width="40" Fill="#FFFFD300" Stroke="{x:Null}" Margin="0,0,20,0"/>
</StackPanel>
<Canvas HorizontalAlignment="Left" Margin="8,30,0,84" x:Name="Tree" Width="151" RenderTransformOrigin="0.5,0.5">
<Canvas.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Canvas.RenderTransform>
<Rectangle Height="104" Width="19" Fill="#FF6E4100" Stroke="#FF000000" StrokeThickness="3" Canvas.Left="66" Canvas.Top="82"/>
<Path Width="151" Fill="#FF3FA33D" Stretch="Fill" Stroke="#FF000000" Data="M48,0 C56.284271,0 63.784271,3.3578644 69.213203,8.7867975 L72.336609,12.572392 L73.496292,11.902077 C77.628952,10.011786 81.991112,9 86.5,9.000001 C97.259842,9 107.18409,14.76185 115.14809,24.474262 L117.88708,28.136744 L119.32265,27.357546 C122.9118,25.839466 126.85786,25 131,25.000002 C147.56854,25 161,38.431458 161,55 C161,59.142136 160.16054,63.088203 158.64246,66.677353 L156.6917,70.271347 L160.04605,70.609497 C173.71654,73.406883 184,85.502525 184,100 C184,116.56854 170.56854,130 154,130 L150.82446,129.67987 L151,132 C151,148.56854 137.56854,162 121,162 C114.7868,162 109.01475,160.11121 104.22672,156.87646 L103.91651,156.62053 L100.62505,158.56071 C96.162949,160.7959 91.418785,162 86.5,162 C79.94162,162 73.69368,159.85936 68.010857,155.98825 L66.897095,155.12416 L64.773285,156.87646 C59.985252,160.11121 54.213203,162 48,162 C31.431458,162 18,148.56854 18.000002,132 C18,124.2335 20.951248,117.1563 25.793457,111.82867 L26.981792,110.69574 L23.953953,110.3905 C10.283459,107.59312 0,95.497475 0,81 C0,66.502525 10.283459,54.406883 23.953953,51.609493 L26.906376,51.311863 L26.786798,51.213203 C21.357864,45.784271 18,38.284271 18.000002,30.000002 C18,13.431458 31.431458,0 48,0 z" StrokeThickness="3" Height="113"/>
</Canvas>
<Canvas Height="112" Margin="49,0,150,24" x:Name="Car" VerticalAlignment="Bottom" RenderTransformOrigin="0.5,0.5">
<Canvas.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Canvas.RenderTransform>
<Canvas Height="79" x:Name="CarBody" Width="201">
<Rectangle Height="40" Width="86" Canvas.Left="58.501" Fill="#FFFF0000" Stroke="{x:Null}"/>
<Rectangle Fill="#FFFF0000" Stroke="{x:Null}" Height="40" Width="201" Canvas.Top="39" RadiusX="0" RadiusY="0"/>
<Rectangle Height="27" Width="46" Canvas.Left="98.502" Canvas.Top="12" Stroke="{x:Null}" RadiusX="0" RadiusY="0">
<Rectangle.Fill>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FF188CB7" Offset="0"/>
<GradientStop Color="#FFFFFFFF" Offset="1"/>
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
</Canvas>
<Canvas Height="50" x:Name="BackWheel" Width="50" Canvas.Left="14.168" Canvas.Top="62.662" RenderTransformOrigin="0.5,0.5">
<Canvas.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Canvas.RenderTransform>
<Ellipse Height="50" Width="50" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="26" Width="26" Canvas.Left="12" Canvas.Top="12" Fill="#FFBBB9B9" Stroke="{x:Null}"/>
<Rectangle Height="26" Width="2" RenderTransformOrigin="0.5,0.5" Canvas.Left="24" Canvas.Top="12" Fill="#FF000000" Stroke="{x:Null}">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="26" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="24" Canvas.Top="12">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
<Canvas Height="49" x:Name="FrontWheel" Width="49" Canvas.Left="143.168" Canvas.Top="63" RenderTransformOrigin="0.5,0.5">
<Canvas.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform/>
<TranslateTransform/>
</TransformGroup>
</Canvas.RenderTransform>
<Ellipse Height="49.333" Width="49.333" Fill="#FF434343" Stroke="{x:Null}"/>
<Ellipse Height="27" Width="27" Fill="#FFBBB9B9" Stroke="{x:Null}" Canvas.Left="11" Canvas.Top="11"/>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="23.666" Canvas.Top="11.25">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="45"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
<Rectangle Height="27" Width="2" RenderTransformOrigin="0.5,0.5" Fill="#FF000000" Stroke="{x:Null}" Canvas.Left="23.916" Canvas.Top="10.75">
<Rectangle.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="135"/>
<TranslateTransform/>
</TransformGroup>
</Rectangle.RenderTransform>
</Rectangle>
</Canvas>
</Canvas>
</Grid>
</UserControl>
Summary
Relatively quickly, we drew some XAML elements, and animated them to create a driving car scene. We did all of this without really writing any code, and that’s the beauty of Expression Blend in the Silverlight story. You should be able to see my final animation below this paragraph. If it’s not showing up, you can click here to see the Silverlight animation we created. To download the source code for this Silverlight Animation demo, click here.
Leave a Reply