ADOBE AFTER EFFECTS: Forum Expressions Tutorials Creative Cloud

expression play once on beat

COW Forums : Adobe After Effects

<< PREVIOUS   •   FAQ   •   VIEW ALL   •   PRINT   •   NEXT >>
marcel ooms
expression play once on beat
on May 16, 2014 at 12:50:46 pm

hello cows,

I'm working on a audio project. We made a cool seperate comp for every sound layer. I now want to automate the sound, so it should play once everytime it hits a certain peak

I thought just using a time remap, and put an 'if/else' expression that would return to frame '0' when it hits the peak would do the trick. I was wrong. It won't continue playing, or it goes to '0' for 1 frame and when it leaves the peak it is back to normal 'time'

I hope it is a little bit clear. Basically I want (in frames)

frame 1.2.3.4.5 1.2.3.4.5. etc
^
(here is the peak of audio)

thanks in advance


Return to posts index

marcel ooms
Re: expression play once on beat
on May 16, 2014 at 12:57:33 pm

in flash language (which doesn't work with timeremap:D)I would say:

if (thisComp.layer("Audio Amplitude").effect("Both Channels")("Slider") > 50)
{
play(once);
}


Return to posts index

Walter Soyka
Re: expression play once on beat
on May 16, 2014 at 1:01:38 pm

If the beat is regular, you could keyframe it once and then use the loopOut expression:

loopOut("cycle");

Otherwise, it's a little more complicated. Expressions are evaluated anew every single frame; they have no memory of what happened during the frame before. Your time remapping logic must control not only when the sound starts, but also its entire continuation and when it ends.

Can you post the expression you started with and we can take a look?

Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index


marcel ooms
Re: expression play once on beat
on May 16, 2014 at 2:03:56 pm

that's a start! thanks. But it is an irregular beat.

so far I have:

t=value;
if(thisComp.layer("Audio Amplitude").effect("Both Channels")("Slider") > 55)
{
t = 0
loopOut("cycle")
}

t

but now it won't run the cycle. When the beats hits 55 it return to 0 (as I want it too) but then I want it to play at normal speed, so timeremap should just be 0 en continue.

instead, because of the t=value, the frame after the beat hits 55 it return to it's original value. So how do I make a value, which at the beginning just gives the normal framerate, but I can tell "when you hit the beat, value = 0 and start over"


Return to posts index

Walter Soyka
Re: expression play once on beat
on May 16, 2014 at 8:18:05 pm

As I mentioned above, expressions are evaluated anew every frame -- they have no "memory" of what the results were on the frame before.

How long is the audio sample? You may have to calculate how long it has been from the current frame to the time the amplitude last hit 55 and have your expression control not just the first frame where the audio hits, but also all the frames it's supposed to play thereafter.

Or it might be quicker just to cut the samples manually in where they belong. Audition would be better suited for than this Ae.

Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index

marcel ooms
Re: expression play once on beat
on May 19, 2014 at 8:40:30 am

Indeed I was hoping for some kind of memory instead of a everyframe check.

The animation is about 10 frames long and the beat too. Can you program something like: when hit 55, play 10 frames. I'm not sure how it works with your second paragraph, but indeed it would be a way to say: play frame 0 when hits 55, thereafter 1 thereafter 2 then 3.... etc, in some way hardcoded instead of just (cycle)

yes it is possible to just set a comp for every beat. But we want o automate it, so with 10 music layers, 2 minutes and at the end even switch the song so we get an totally different animation but with the same elements.

so audition wouldn't work, because we want to make it applicable for every songs (of course with a little bit of tweeking in the AE file) without changing the song


Return to posts index


Walter Soyka
Re: expression play once on beat
on May 19, 2014 at 1:06:49 pm

Gotcha. You'll need logic that controls the entire duration, somewhat like the following untested snippet of code:

sampleDurationFrames = 10; // how long is the animation, or how many frames back should I look?
timeRemapped = -1; // safe value for time remapping in case I'm not supposed to be playing the animation

// loop from the back of the sampling range to the current time, checking to see where I should be in the animation based on the sound
for (i = sampleDurationFrames; i > 0; i--) {
timeBack = time-framesToTime(i);
if (thisComp.layer("Audio Amplitude").effect("Both Channels")("Slider").valueAtTime(timeBack) > 55) timeRemapped = sampleDurationframes-i;
}


Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index

Walter Soyka
Re: expression play once on beat
on May 19, 2014 at 2:22:53 pm

My post above contains at least one error. You'll have to convert the calculated time remapping values back from frames back to time.

Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index

marcel ooms
Re: expression play once on beat
on May 19, 2014 at 7:09:02 pm

Hey walter,

Thanks for your help. I figured out that I had to convert them back, but still the value switched back to its original value as soon as it hits the frame after (in this example) 55. But i've got the feeling we are getting there.

I also tried a different way today. Just copying the animated layer and offsetting it start to everytime the layer hits 55, but this asked for a script i guess, which is even harder (if you're not the programming genius like me). so that plan failed :)

it's really strange that after effects hasn't got an expression like 'nextFrame()' or something, so you can get the value back to 0 and then say 'nextFrame(till frame 20)'


Return to posts index


marcel ooms
Re: expression play once on beat
on May 19, 2014 at 9:17:22 pm

A new idea is just add a slider, and add expression:

numberFrames=60 //frames animation lenght
l = 60/numberFrames
numberCycles = Math.floor(time*l)
i=numberCycles/l;
f= time-i;
f

and find the loop or regular beat and use the slider for all the irregular beats, but the only reason for this solution is because i really can't get your script to work or have any more ideas

why doesn't AE have any kind of expression memory instead of the everyframe check!!!! :(


Return to posts index

Walter Soyka
Re: expression play once on beat
on May 20, 2014 at 12:38:39 am

This is something I could use myself, so I've reworked it a bit:

property = thisComp.layer("Test").transform.opacity; // property to check for threshold crossing
threshold = 70; // threshold which activates playback
maxFrames = 10; // the length of the animation in frames

animationFrame = -1; // the "current frame" of the underlying animation; -1 when not playing

// we need to go back twice as many frames as the animation is, to catch cases where it's already supposed to be playing
// this for loop starts 20 frames back on the timeline, then advances to the current time
// it looks to see if we're playing the animation already; if so, we continue playing
// if not, we check to see if we should start

for (i = maxFrames*2; i >=0; i--) {
// is the animation currently playing? if so, advance its counter
if (animationFrame >= 0) animationFrame++;

// if we've reached the end of the animation, reset it
if (animationFrame >= maxFrames) animationFrame = -1;

// if we're not playing, check for a value that's crossed the threshold and start playing again
if ((animationFrame == -1) && (property.valueAtTime(time-framesToTime(i)) > threshold)) animationFrame = 0;

}

// if the current frame on the timeline is supposed to be playing the animation, play that frame
// otherwise, play frame 0 of the underlying animation
if (animationFrame >= 0) framesToTime(animationFrame) else 0;


Note that I'm using the opacity of a layer called Test to trigger my playback. You'll have to tweak the first couple lines for your own animation.

This also responds to the first value that crosses the threshold to trigger playback, then ignores any other values over the threshold during playback.


[marcel ooms] "why doesn't AE have any kind of expression memory instead of the everyframe check!!!! :("

Instead of thinking of an expression as a program that executes over a composition, think of it as a program that executes on a given frame.

While some tasks like this are a little harder this way, frame-based expressions are extremely flexible and generally desirable for non-accumulating tasks.

Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index

marcel ooms
Re: expression play once on beat
on May 20, 2014 at 7:26:12 am

you nailed it! very nice and with your comment next to it I almost understand the entire process.

thanks a lot, this is far more complicated than I expected and probably never would have gotten this result!

if I find some time tonight I'm gonna try to put an overwrite command in it, so when the animation is playing and the 'beat' reaches the treshold again it will start from frame 0. But that's the next step, this is already exactly what I needed!


ps. I come from a flash background (years ago) so I'm still thinking in frames+language in an actionscript kinda way :)


Return to posts index


Walter Soyka
Re: expression play once on beat
on May 20, 2014 at 12:37:03 pm

[marcel ooms] "if I find some time tonight I'm gonna try to put an overwrite command in it, so when the animation is playing and the 'beat' reaches the treshold again it will start from frame 0. "

Here's a hint: right now, the expression actually avoids "overwriting" on purpose. You don't need to put something in to make it overwrite, you need to take something out. The rest is left as an exercise to the reader.

Note that this may lead to an unexpected result if you have a value that slowly crosses the threshold (i.e., crosses the threshold and stays above it for several frames before coming back down below): the animation will seem to pause on the first frame until the value falls below the threshold, then it will play forward.


[marcel ooms] "ps. I come from a flash background (years ago) so I'm still thinking in frames+language in an actionscript kinda way :)"

I suspect I would be equally frustrated trying to apply my Ae knowledge to Flash!

Walter Soyka
Principal & Designer at Keen Live
Motion Graphics, Widescreen Events, Presentation Design, and Consulting
RenderBreak Blog - What I'm thinking when my workstation's thinking
Creative Cow Forum Host: Live & Stage Events


Return to posts index

<< PREVIOUS   •   VIEW ALL   •   PRINT   •   NEXT >>
© 2017 CreativeCOW.net All Rights Reserved
[TOP]