Getting Started with
Expressions in After Effects
These notes are from a series of motion media classes I taught at SCAD/Atlanta.
What are Expressions?
Expressions are a tiny piece of code that you can put on any parameter of a layer which allows you to control the value of that parameters (transforms, effect settings, etc.) by using a scripting language based on JavaScript. Expressions allow you to establish links betweens different parameters, as an aid to animation. In addition, you can use After Effects-specific functions to help you create these animations.
Remember, no matter what an expression is doing, no matter how complicated it appears, all it produces at the very end is a value (a number, generally).
Usefulness of Expressions
Expressions let you animate things according to rules you set up.
Want to make a layer change transparency as it gets further away from the camera? Want a shape to to change length according to the amplitude of your audio? Do you want a particle system to follow a null which is parented to another object? Expressions will do this for you.
Writing an Expression
To start writing an expression, option-click (alt-click in Windows) on the stopwatch of any animatable parameter. Option-clicking again on the stopwatch deletes the expression.
The expression starts with a default value that just means “what ever my value was to start with.” You will replace this text with your expression. The easiest way to get the syntax (the proper form, the word order...) of an expression correct is to use the expression’s pickwhip to select which parameter will drive this expression.
For example, if you want a layer’s opacity controlled by another layer’s rotation, create the expression on the first layer’s opacity channel, and then pickwhip to the second layer’s rotation. After Effects helps you out by writing:
thisComp.layer(“layer name here").transform.rotation
Using the pickwhip avoids any spelling or punctuation errors you might make if you were typing this in manually.
Multi-dimensional values
That value generated by an expression can be one dimensional, like 2D rotation or opacity, or two dimensional like 2D transforms or scaling, or three dimensional like 3D transforms, rotation or scaling.
The final result of an expression should have the correct number of dimensions, either a single number for a one-dimensional value or a bracketed, comma-separated list (an array) for a multi-dimensional value.
Examples:
One dimensional: 15
Two dimensional: [x,y]
Three dimensional: [x,y,z]
This means that if you want to refer to the y position of a layer, you should use:
thisComp.layer("somelayer").transform.position[1]
Remember that the dimensions start counting with 0 (they’re “0-indexed”), so 1 is the second item.
Accessing Parts of a Multi-dimensional Array
If you want to access the individual components of a multi-dimensional array, use bracket notation to indicate which value you want.
In the example:
thisComp.layer("some layer").transform.position
the value returned is an array that represents the position of a 2D layer (a 2 dimensional value, including both x and y coordinates). To access just the x position (as above) just put [0] after everything else.
Like this:
thisComp.layer("some layer").transform.position[0]
Note that numbering in expressions, like JavaScript, is zero based, meaning the first value is accessed with [0], the second with [1], and so on.
Variables
It is often useful to put temporary values into placeholders called variables. It’s just a name that holds a value. Think of them as a way to avoid writing a long description of what you’re linking to every time. So instead of writing
thisComp.layer("some layer").transform.position[0]”
every time, you can assign it to a variable like this:
xPos=thisComp.layer("some layer").transform.position[0]
Then when you need to refer to the x position of the layer named “some layer” in the future, you can just use “xPos.” While you can name variables anything you want (i.e “fred” or “wilma”), you should use common sense naming like “x_scale” or “y_rot” whenever possible.
Functions
Functions are like a tiny program, a series of commands, or a magic black box. You give it some information (parameters) and it spits out a result (a value). There are several useful built-in functions in After Effects, accessed from the expression drop-down menu.
The general form of any function is:
Function(parameter, parameter, etc.)
Example Functions:
loopOut(“pingpong”)
– loops the existing keyframes in a timeline, oscillating back and forth.
loopOut(“cycle”)
– loops the existing keyframes in a timeline, forward, and then returning to the first keyframe to repeat again.
wiggle(frequency, magnitude)
- creates a series of random values, evaluating according to “frequency,” and within the magnitude value. Returns the right dimension of values according to which parameter it’s applied to.
Special words used in Expressions
time
– resolves to the current time on the timeline, in seconds. This is a constantly increasing value, and can be used to make any parameter (position, rotation, etc.) increase over time.
value
– the current value of the parameter you’re controlling, before expressions. This can be a multi-dimensional value (technically, an “array”), depending on what the parameter is. This means if you want to refer to the y position of a layer’s default value, you should use: value[1].
index
- The number of the layer the expression is applied to.
Changing (scaling) values
Sometimes you have one range of values that needs to be scaled to a second range, in order to be useful. Once you get access to a value, you can alter it, using common (and advanced) math methods. At the simplest level, you can add, subtract, multiply or divide the value , by using common math operators (+-*/).
For example:
thisComp.layer(“layer name here").transform.rotation*10
(multiplies the value ten times)
thisComp.layer(“another layer").transform.opacity/2
(divides the value in half)
But what if you want to remap the first range of values into a second range? For instance, you might want a wheel to rotate a full turn as it moves horizontally, or you want to scale transparency (from 0-100) by linking it to screen position (x position going from, say, 0-720 pixels).
Using linear()
There’s a function (see below) that will let you scale one set of values to another range of values, in a linear fashion.
linear(t, tMin, tMax, value1, value2)
- scales an input (t) from an initial range (tMin to tMax) to a remapped range (value1 to value2).
So, using our example of linking a layers’s x position to opacity, you might do this:
//put the x position value in a variable for convenience
input=thisComp.layer("some layer").transform.position[0];
//remap the incoming values from 0-720 to 0-100
linear(input,0,720,0,100)
Some Basic Rules/Suggestions
- Variable names cannot have spaces in them, or start with a number.
- Multi-line expressions require a semicolon at the end of each line.
- Numbering in an array starts at 0, so the first item is [0], the second is [1], etc.
- Make sure you supply the correct number of dimensions for the parameter you’re controlling.
- Expressions control the value of the parameter they’re applied to. An expression controlling opacity cannot directly control position. Put the expression on the position channel in order to control that parameter.
- Expressions are case-sensitive. Be careful of spelling errors.
Good reference pages - Motionscript.com and http://jjgifford.com/expressions/basics/