Skip to main content
Participating Frequently
November 16, 2019
Answered

Namespaces in Expressions

  • November 16, 2019
  • 4 replies
  • 657 views

Hi: I'm learning how to use expressions, and as a start, I wrote an expression to "bounce" the scale of a shape (a circle) from the starting default (100%) down to 0 over a range defined by a marker. To do this, I wrote the following code (in an external file aeprocs.jsx):

"cdexp":function(timeNow,vNow,layer,tag,final)
// Exponentially-damped decay from initial default down to "final" value over
// a time range defined by the marker identified by "tag"
{
  k1 = -3.0;
  omega = 5.0;
  markStart = layer.marker.key(tag).time;
  markEnd = markStart + layer.marker.key(tag).duration;
  if(timeNow < markStart)
  {
    nv = vNow[0];
  }
  else if(timeNow > markEnd)
  {
    nv = final;
  }
  else
  {
    delta = timeNow - markStart;
    nv = vNow[0]*(Math.exp(k1*delta) * Math.cos(omega*delta));
  }
  return [nv,nv];
}

I can now invoke this to make a "bounce down to 0" effect on the scale property of any 2D object in my composition by writing the following expression:

lib = footage("aeprocs.jsx").sourceData;
lib.cdexp(time,value,thisLayer,"1",0);

Now a couple of questions:

  1. It is cumbersome to include the first statement (above, "lib = . . .") in every expression where I use this. Is there a way to insert "lib" into the global namespace so it can be defined once and used everywhere in the composition?
  2. The code as written here assumes a 2-dimensional property (scale in this case). Is there a way to "template" this code so I can write one bit of code which can then be used for 1D properties (e.g. opacity) or 2D properties (e.g. scale or position), or - for that matter - properties with other dimensions (e.g. color)?

Thanks.

 

This topic has been closed for replies.
Correct answer Mylenium

The answer to your second question is basically no. AE's properties are all over the place in terms of value ranges and data types so whatever prototype function you dream up would be a hunky and clunky monstrosity whose own evaluation would consume so many evaluation cycles before getting to the actual expression that it's simply not worth it. Things would slow down to a crawl. You'd do better to define explicit separate functions fore each property stream type and call them up directly. This is even more advisable since AE's expression engine doesn't produce sensible alerts in the majority of cases and you'd be forever chasing ghosts if your expression for some reason doesn't work without producing a warning. That, BTW, is also the major flaw of using code libraries. Functions tend to interact in the weirdest way once combined due to how AE handles this stuff and often the hassle just isn't worth it.

 

Mylenium

4 replies

Martin_Ritter
Legend
November 25, 2019

This might be off-topic, but why are you writing expression as .jsx?

 

This seems terrible when it comes to editing and bug-fixing. You can put the code just into the proberty and if you write it universal (thisComp, thisLayer, if *marker exits*, try... catch and so on), you can literally copy&paste it into any proberty of any layer.

 

OR

 

You go the scripting way you already started and make an actually gui script for AE. There you can have a button and the functionality to add the expression to the selected probertiy (or proberties) and that's it.

 

What you have now looks like the sum of the disadvantages of both approaches - but maybe I'm missing something. Enlightenment is highly appreciated.

 

*Martin

Nathan Lovell_52
Inspiring
November 25, 2019

Additionally, you can normalise this external function to be compatible with the jsx code! There are plenty of built in Math methods that will allow you to convert and do math calculations. I would definitely stick to using built in methods, and creating your own functions, unless it is a jsx function that would already be comptible. Adobe scripting is very depreciated, so it is best practise to keep it as simplistic as possible!

Mylenium
MyleniumCorrect answer
Legend
November 17, 2019

The answer to your second question is basically no. AE's properties are all over the place in terms of value ranges and data types so whatever prototype function you dream up would be a hunky and clunky monstrosity whose own evaluation would consume so many evaluation cycles before getting to the actual expression that it's simply not worth it. Things would slow down to a crawl. You'd do better to define explicit separate functions fore each property stream type and call them up directly. This is even more advisable since AE's expression engine doesn't produce sensible alerts in the majority of cases and you'd be forever chasing ghosts if your expression for some reason doesn't work without producing a warning. That, BTW, is also the major flaw of using code libraries. Functions tend to interact in the weirdest way once combined due to how AE handles this stuff and often the hassle just isn't worth it.

 

Mylenium

Roland Kahlenberg
Legend
November 17, 2019
Very Advanced After Effects Training | Adaptive &amp; Responsive Toolkits | Intelligent Design Assets (IDAs) | MoGraph Design System DEV
Participating Frequently
November 25, 2019

I'd already seen this tutorial, which showed me how to set up functions in a .jsx file in the first place. However, it doesn't address the issue of how to avoid having to include a "lib . . ." statement in every place where I want to use a function in "lib". What I would like to do is to get "lib" into the namespace for the composition, and then just have a line like "lib.myfunc_nn(args)" each place I want to invoke a function in the library.