Animation

Version 2 (coder, 27/03/2012 16:51)

1 1 admin
h1. Animation
2 1 admin
3 1 admin
{{>toc}} 
4 1 admin
5 1 admin
libavg contains a powerful animation framework that allows you to quickly author time and event-based changes in nodes. Animations can change the values of all numeric node attributes. They can be combined to execute in parallel or in series, they can switch states when some external event occurs, and callbacks can be registered that are called when animations start or stop.
6 1 admin
7 1 admin
> (!) *Note:* (!) 
8 2 coder
> The animation framework is present in libavg since version 0.9. Some earlier (incompatible) animation classes are still present in the namespace anim; they will be removed in future libavg versions.
9 1 admin
10 1 admin
h1. Linear Animations
11 1 admin
12 1 admin
It is very simple to animate node attributes:
13 1 admin
14 1 admin
_anim1.py_
15 1 admin
16 1 admin
<pre><code class="python">
17 1 admin
#!/usr/bin/env python
18 1 admin
# -*- coding: utf-8 -*-
19 1 admin
20 1 admin
from libavg import *
21 1 admin
22 1 admin
def startAnim():
23 1 admin
    animObj.start()
24 1 admin
25 1 admin
player = avg.Player.get()
26 1 admin
canvas = player.createMainCanvas(size=(640,480))
27 1 admin
rootNode = canvas.getRootNode()
28 1 admin
node = avg.WordsNode(pos=(10,10), font="arial",
29 1 admin
        text="Hello World", parent=rootNode)
30 1 admin
31 1 admin
animObj = LinearAnim(node, "x", 2000, 0, 200)
32 1 admin
player.setTimeout(0, startAnim)
33 1 admin
34 1 admin
player.play()
35 1 admin
</code></pre>
36 1 admin
37 2 coder
This creates an animation that moves the node from @x=0@ to @x=200@ over a course of 2000 milliseconds. The framework takes care of updating the position each frame. Point attributes (such as @pos@ and @size@) can be animated in the same way. @LinearAnim@ has a few additional optional parameters, which are described in detail in the [[reference]]. Using this class, you are independent of the framerate: if you change the framerate (maybe because you're running the code on a different computer with a different refresh rate), the animation will still take the same amount of time to complete. It'll just display more or less frames. There is another advantage: If something happens while the animation is running (the user presses a cancel button, for instance), you can just call @animObj.abort()@ and it'll stop dead in it's tracks. The animation framework also makes sure that only one animation per attribute is running at one time. If a second one is started, the first one is aborted.
38 1 admin
39 1 admin
There are convenience functions that handle fading the opacity of nodes called @fadeIn()@ and @fadeOut()@.
40 1 admin
41 1 admin
h1. Easein/out
42 1 admin
43 2 coder
@LinearAnim@ moves the attribute at a constant speed with no accelleration or decelleration. The @EaseInOutAnim@ class encapsulates an animation that proceeds in three phases: ease-in, linear and ease-out. Constructor parameters determine the length of each phase. Start and end speed are zero. Ease-in and ease-out phases have the shape of one quadrant of the sine curve. Less mathematically put: The animation will accelerate and decelerate at the beginning and end and look a lot smoother because of this.
44 1 admin
45 1 admin
h1. ParallelAnim
46 1 admin
47 2 coder
In many cases, you will want to start several animations at once. This can be accomplished using the @ParallelAnim@ class:
48 1 admin
49 1 admin
_anim2.py_
50 1 admin
51 1 admin
<pre><code class="python">
52 1 admin
#!/usr/bin/env python
53 1 admin
# -*- coding: utf-8 -*-
54 1 admin
55 1 admin
from libavg import *
56 1 admin
57 1 admin
def startAnim():
58 1 admin
    animObj.start()
59 1 admin
60 1 admin
player = avg.Player.get()
61 1 admin
canvas = player.createMainCanvas(size=(640,480))
62 1 admin
rootNode = canvas.getRootNode()
63 1 admin
node = avg.WordsNode(pos=(10,10), font="arial", 
64 1 admin
        text="Hello World", parent=rootNode)
65 1 admin
66 1 admin
animObj = ParallelAnim(
67 1 admin
    [LinearAnim(node, "x", 2000, 0, 200),
68 1 admin
     LinearAnim(node, "y", 2000, 0, 10)])
69 1 admin
player.setTimeout(0, startAnim)
70 1 admin
71 1 admin
player.play()
72 1 admin
</code></pre>
73 1 admin
74 1 admin
The example code moves the node down and to the right over a course of 2 seconds (Note that in this case, just running a @LinearAnim@ on the pos attribute of the node would have been enough). Calling @abort()@ on a @ParallelAnim@ will stop all child animations. @ParallelAnim@ is sometimes useful on its own, but it's really powerful in combination with @StateAnim@.
75 1 admin
76 1 admin
h1. StateAnim
77 1 admin
78 1 admin
More complex animations can be scripted using @StateAnim@. Objects of this class contain a number of animations (so-called "states") that can be executed in an arbitrary sequence. At most one of these animations is active at once. The end of one animation can trigger the start of another one, and states can be set from a python script. A simple use for a @StateAnim@ is as a predetermined sequence of animations, but animations that take different routes depending on user input events are also possible. There is support for debugging animation states by calling @StateAnim.setDebug(True)@. This causes all state changes to be dumped to the console.
79 1 admin
80 2 coder
To make sure there are no discontinuities between two states, @Anim.start()@ has an optional parameter @keepAttr@. If this is set to True, the attribute is not changed at the beginning of the animation and the animation runs only for an appropriate part of the time that the duration parameter specifies. So, suppose that in @anim2.py@ above, @start(True)@ is called and @x=50@ before the animation starts. Since this is one-quarter into the range 0-200, the animation will run for 1500 ms (=2000*0.75) and the node will move from 50 to 200 in this time.
81 1 admin
82 1 admin
Note that changing the state of a @StateAnim@ during an animation callback is not supported. An attempt to do so is silently ignored.
83 1 admin
84 1 admin
h1. Other Animations
85 1 admin
86 1 admin
@WaitAnim@ does nothing for a predetermined amount of time. @ContinuonsAnim@ continually changes one attribute and doesn't stop by itself.