Activity › Forums › Adobe After Effects › expression play once on beat
-
expression play once on beat
Posted by Marcel Ooms on May 16, 2014 at 12:50 pmhello 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
Walter Soyka replied 11 years, 12 months ago 2 Members · 12 Replies -
12 Replies
-
Marcel Ooms
May 16, 2014 at 12:57 pmin flash language (which doesn’t work with timeremap:D)I would say:
if (thisComp.layer(“Audio Amplitude”).effect(“Both Channels”)(“Slider”) > 50)
{
play(once);
} -
Walter Soyka
May 16, 2014 at 1:01 pmIf 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 -
Marcel Ooms
May 16, 2014 at 2:03 pmthat’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”
-
Walter Soyka
May 16, 2014 at 8:18 pmAs 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 -
Marcel Ooms
May 19, 2014 at 8:40 amIndeed 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
-
Walter Soyka
May 19, 2014 at 1:06 pmGotcha. 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 -
Walter Soyka
May 19, 2014 at 2:22 pmMy 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 -
Marcel Ooms
May 19, 2014 at 7:09 pmHey 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)’
-
Marcel Ooms
May 19, 2014 at 9:17 pmA 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;
fand 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!!!! 🙁
-
Walter Soyka
May 20, 2014 at 12:38 amThis 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 framesanimationFrame = -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 startfor (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
Reply to this Discussion! Login or Sign Up