-
Tracking Paint Strokes with Position, Rotation & Scale
I’ve found a number of threads & tutorials about tracking the paint tool in After Effects but I haven’t found anything concrete for tracking position, rotation & scale.
A popular solution is to pick-whip your ‘clone position‘ to the tracker’s ‘position‘ but that doesn’t take into account any offset. Another popular method is to ‘Lock Source Time‘ in the ‘Paint‘ panel but that doesn’t maintain the original grain structure & lighting conditions.
In an effort to solve this I wrote the following expressions. I’m not an expert with expressions but I thought I would share what I came up with so far..
How to use the Expressions:
Paste the expression in both ‘Stroke Options > Clone Position‘ and ‘Transform > Position‘ of your paint stroke.You MUST edit the following 2 variables at the top of the code to customize it to your paint stroke:
1) trackLayer: The name of layer that contains your tracking data. By default it’s ‘Null 1’.
2) paintFrameNum: The frame number where the paint stroke was applied (calculate as if the first frame of your comp is 0).Track: Position
// user inputs
trackLayer = "Null 1";
paintFrameNum = 0;// position variables
livePosition = thisComp.layer(trackLayer).transform.position;
startPosition = livePosition.valueAtTime(paintFrameNum*thisComp.frameDuration)// calculate position difference
livePosDiff = livePosition-startPosition;// set value
value + livePosDiffTrack: Position & Rotation
NOTE: The actual brush doesn’t rotate
// user inputs
trackLayer = "Null 1";
paintFrameNum = 0;// tracker position variables
liveTrack = thisComp.layer(trackLayer).transform.position;
startTrack = thisComp.layer(trackLayer).transform.position.valueAtTime(paintFrameNum*thisComp.frameDuration);// tracker rotation variables
liveRotate = thisComp.layer(trackLayer).transform.rotation;
startRotate = thisComp.layer(trackLayer).transform.rotation.valueAtTime(paintFrameNum*thisComp.frameDuration);// calculate distance between paint stroke & tracker start position
startDistance = length(value , startTrack);// calculate live rotation difference
liveRotDiff = liveRotate - startRotate;// calculate angle between Tracker start position & clone position
startAngle = Math.atan2(value[1] - startTrack[1], value[0] - startTrack[0]) * 180/3.14159265;// set value
radius = startDistance;
angle = startAngle + liveRotDiff;
x = radius*Math.cos(degreesToRadians(angle));
y = radius*Math.sin(degreesToRadians(angle));
centre = liveTrack;
add(centre,[x,y])Track: Position, Rotation & Scale
I haven’t found a solution to accurately apply a track to the position, rotation & scale of a paint stroke. I can factor in the position change relative to the scale of the track but I can’t scale the brush size (only the diameter).I’ve also considered stabilizing the source within its parameters (at its largest scale) and tracking it back in using the clone but there is no parameter for ‘source scale’.
Ideally, in the future we’ll be able to animate/expression the ‘brush size‘ & ‘brush rotation‘ to solve this.
Multiple Paint Strokes:
To apply the expressions across multiple paint strokes you can ‘Copy Expression Only’ on both the ‘Clone Position‘ & ‘Position‘ in your paint stroke and paste it on all of your paint strokes at once. Remember that you may have to change the ‘paintFrameNum‘ & ‘trackLayer‘ variables.Questions:
Has anyone figured out a solution for the scale?
Can the code above be simplified/improved?
How do you track your paint?Mike Sevigny
https://www.torusfx.com