Transform Loop
Hi team,
this idea came to me after we were struggling to get a tile-able image large enough to transform across the screen in nuke for a shots duration. After a nightmare of switching between textures and offset transformations and retimes I wanted to find a happier solution. After watching some BlinkScript tutorials I set off to find a solution. This is what I came up with.
download here:
http://www.nukepedia.com/blink/transform/transform_loop
Taking a look inside the group there are currently 2 separate blinkscripts, a tile, and a transform node. There are future plans to condense everything into a single blinkscript but for now I wanted to get a working version available.
The scaling is pretty straightforward.
if the values are greater than or equal to 1 use a transformation nodes scale.
if the values are less than 1 use a transformation nodes scale.
The x and y translation are handled by two different blinkscripts. Let’s break down whats going on. in the Y transformation. Taking a look at the intila setup we have..
kernel Transform : ImageComputationKernel<ePixelWise> { Image<eRead, eAccessRandom, eEdgeClamped> src; // the input image Image<eWrite> dst; // the output image // Theses parameter are made available to the user. param: int2 offset; //user controlled transformation // These local variable are not exposed to the user. local: float4 output; //image to apply the transformations to int2 resolution; // hold our imgages resolution
Looking at the main code branch there are 4 main things that we are doing.
We need to get the correct resolution for the input. In theory this could be user controlled, but since we need to be inputting an image into the script it makes more sense to just use that resolution.
We want the user to be able to transform the image in x and y for as long as they need. But we dont actually want to transfrom the image that far. instead we need to get the remainder of the tranformation if we loop over the same resolution over and over.
Once we know all this we can offset our image.
After offsetting the image we will have a blank space same as with a regular transform (If we move 500pixels up then the bottom 500pixels will be black). So we need to add the part of the image that is now outside of the resolution into the newly created blank space.
void init() { //getting the resolution of the source image resolution.x = src.bounds.width(); resolution.y = src.bounds.height(); } void process(int2 pos) { //as we transform we want to 'reset' our transformation back to 0 offset.x = offset.x % resolution.x; offset.y = offset.y % resolution.y ; if (offset.y >= 0){ //formula to offest the image based on output = bilinear( src,(pos.x), (pos.y - offset.y)); //we moved the image but we need to add back in the offset image output = output + bilinear( src,(pos.x), (pos.y + resolution.y - offset.y)); }else{ output = bilinear( src,(pos.x), (pos.y-offset.y)); output = output + bilinear( src,(pos.x), (pos.y - resolution.y - offset.y)); } dst() =output; }
Once we have this we can happily transform forever.