Ipo Curves have a great feature: they can be driven. This means that their “time” factor is no more controlled by the global Blender time, but rather by “something else” – in fact, either a transform property of an object or bone, or a small Python function. In other words, it is as if the object/bone/Python function controlled the green cursor, only for this driven Ipo curve.
So you can e.g. use the X location of a driver to control the colors (RGB curves) of a material, use the rotation of a driver to control the scale of an object, use the scale of a driver to control the shape (through shape keys Ipos) of a mesh/curve/etc., use a python function to control a constraint’s influence, and much much more…
One key usage of drivers is in character animation: for example, you can add object drivers to the relative shape keys of a face. Then, you manipulate the expressions of your character just by moving these drivers objects (which are set unrenderable, of course!). A bit like using the NLA, but even more friendly! See this tutorial.
Whatever type of driver you use, there are some common points to be noted:
- A driven Ipo curve is no more controlled by time (yes, we insist, but it’s very important to understand this). It’s rather its driver’s property changes that control where along the X axis of the curve its value is to be taken (i.e. the curve now maps the driver’s property value to the curve’s property value).
- A driven Ipo is materialized in the Ipo Curve Editor by a small black dot inside its colored rectangle, in the right list area.
- An Ipo curve can be driven even it is not defined (if it doesn’t “exist”). In this case, Blender assumes a one-to-one mapping (i.e. a linear curve with a unitary gradient). So it is as if the driver’s value is directly applied to the controlled Ipo value.
- A driver is set and controlled in the Transform Properties panel (N, in a Ipo Curve Editor window) of the driven Ipo curve.
- Even though it might seem obvious, there can be only one driver per Ipo curve!
Object drivers are objects that control Ipo curves through their transform properties – hence, one driver can control separately up to nine curves (the three components of its location, rotation and scale).
To set up an object driver:
- Select the curve you want to drive (remember that it doesn't have to exist to be drivable…).
- Show its Transform Properties panel (N).
- Click on the Add Driver button, to the top.
- In the OB field that appears, enter the name of the chosen driver object.
- Unless your driver is an armature, you have only one choice in the Driver type drop-down list, Object.
- Finally, select in the second drop-down list the property you want to drive your Ipo curve (Loc X, Scale Z, etc.).
Now, your Ipo curve is no more directly controlled by the time, but rather by the value of the property you chose. Note that if it is a rotation one, the X-axis of the main area of the Ipo Curve Editor turns – quite logically! – to degrees values. Else (location and scale), the values are in Blender Units.
Note that the space in which the driver’s properties are evaluated is the local one (i.e. parent’s transformations have no effect).
In this example, we are going to control the size of the well-known monkey head (
Suzanne) with the Y-location of the
Empty driver. So, we Add Driver to the three ScaleX, ScaleY and ScaleZ Ipos of the
Suzanne object (as usual, if there is no Ipo datablock yet, it is automatically created). Note that for now, there is no Ipo curves, so Blender applies a one-to-one mapping, as if there was virtual unitary gradient linear curves (materialized as yellow dashed lines in the pictures below). This also illustrates that you can use the same driver property (here, the Y location) for several different driven Ipos…
|Note that the Ipo Curve Editor window is pinned to |
Now, we can use curves on driven Ipos to get more complex behavior than the basic one-to-one mapping. Below, we have the same scene as above, but the ScaleY Ipo now has a pseudo-sinusoidal curve, oscillating between 1.0 and -1.0 values on a one-frame period, created with three control points and the Cyclic extrapolation (E). This means that, while the X and Z components of
Suzanne’s scale are still directly controlled by the Y location of
Empty, the Y scale component now cyclically varies between 1.0 and -1.0, as the following pictures illustrate.
|Note that the Ipo Curve Editor window is pinned to |
- A tutorial showing how to use drivers to control the shape keys of a face.
Bone drivers are nearly the same as object ones.
You set up a bone driver by entering in the OB field an armature’s name, and then selecting the Pose option in the Driver type drop-down list. Then enter the bone’s name in the BO field that appears, and select its property to be used.
Note the following specificities:
- The transformations are evaluated in the bone’s space (i.e. parent bone’s transformations, as well as whole object’s ones, have no effects).
- When using the rotation as driver property, you’ll find a limitation: the evaluated bone’s rotation is always mapped into a
[-180°, 180°[range (which means that if you e.g. rotate your bone over the 180° value, the driven object will “jump back” to its -180° X-Ipo-curve-position…).
- You have an extra driver property: Rotation Difference takes the name of another bone, and uses as driver the angle’s value between the two bones.
Python Ipo Drivers
Python Ipo drivers (or “pydrivers” for short) allow you to use one-line Python expressions as input for a channel, instead of using a property of another object, like standard Ipo drivers do. An expression in programming is any combination of symbols that can be evaluated to a definite value.
To set up a pydriver, once you clicked on the Add Driver button, enable the small “python” button to the left of the OB field – it will then turn into a standard text field where you can type your Python expression.
These drivers open up many interesting possibilities: you can use mathematical functions and more general programming to drive object animations. The only restriction is that the pydriver expression itself must return a real number when evaluated, and not e.g. a string or something else.
Examples would be using sines or cosines to make objects oscillate around a given point, or using random values at each animation frame to change some material attribute, like diffuse rgb, alpha, etc.
Note that pydriver evaluation is equivalent to what the builtin
eval() function does, with the restriction that pydriver expressions must return real numbers (any type of number that can be automatically cast to a float).
We’ve already told the basics: there is a text field where you can type an expression in Python. Here are some examples of valid expressions:
- Any real value:
- Expressions with numbers and operators:
4.5 + 8.9 * 7.0 - (2 / 3.0)
- Expressions also with variables:
math.pi * 2 + 5.0
- Available data:
Blender.Get("curframe") # the current animation frame
- A little math:
math.sin(Blender.Get("curframe")) # the sine of the current frame
- Using the animated (driven) object, available as
self.LocX * 10
Builtin resources and aliases
Pydrivers use their own global dictionary that is cached and only gets recreated when any expression fails. In this dictionary, a few modules are pre-imported, so that they can be used inside pydriver expressions.
To save typing and keep expressions smaller, we’ve added aliases for each module: Blender can be referenced as “
- All from
m.cos(m.pi * b.Get("curframe") / n.random())
Aliases were also added for a few commonly needed data:
ob(name)is equivalent to
me(name)is equivalent to
ma(name)is equivalent to
ob("Cube").LocX + ob("Lamp").RotZ
The pydrivers.py Blender text
Besides the above modules, if there’s a Blender text buffer called “
pydrivers.py” loaded in the Text Editor, it’s also imported:
This allows users to create their own functions and add their own variables without the restriction of the one-line Python expression. For example, if your pydrivers.py text looks like this:
myvar = 10.0
# do something fancy here
You can access both
myfunction inside any expression:
p.myvar * p.myfunction(2) - 1
Note: if you make updates to the
pydrivers.py text, go to the Ipo Curve Editor window and click in any pydriver’s text input box (in the Transform Properties panel), then click out of it or press ↵ Enter, to force reloading the
pydrivers.py module and to update all pydrivers at once.
Let’s say we want to give our
Suzanne a perfect two BU radius circle movement in the (XY) plane. This is not easy to achieve with standard Ipo curves, as you have to create perfect sinusoidal ones (for those who lost their math, a perfect circle in a Cartesian plane is obtained with
x = sin(t) and
y = cos(t)…). So let’s use Python drivers:
math functions take as input a radian value (i.e. a cycle takes
2π frames to complete), and output a value in range
[-1.0, 1.0]. So, to get a 2BU radius circle fully walked in 50 frames (two seconds in PAL videos), we have to use the following Python expression:
- For LocX:
2.0 * math.sin(Blender.Get("curframe")*math.pi/25)
- For LocY:
2.0 * math.cos(Blender.Get("curframe")*math.pi/25)
Suzanne will go in endless circles around the world’s origin (if you want to make it turn around another point, just add an offset to the above expressions, or drive dLoc… Ipos…).
- In the above example, we did not use Ipo curves.
- You can also get a perfect circular movement by using a NURBS circle curve as a path…
- The Blender 2.49 Python API reference and the chapter on extending Blender with Python.
- Python and its documentation.
- This might be a good hunting ground for those looking for functions to try with pydrivers: http://functions.wolfram.com/ (newcomers are recommended to start with elementary ones, specially trigonometric).
- Finally, the patch tracker entry, with patch and sample .blend files for pydrivers: right here.