Help, please, creating a timed fadeout script


#1

hi all,

i am a scripting newbie, with only very very basic information.

ii want to be able to press a pedal on my foot controller which will smoothly fade out the audio of my looper rackspace over something like 30 seconds to a minute (i’ll figure out the time later).

surprisingly to me, there doesn’t seem to be any way to do this, there’s no plugin i can find. there’s midishaper, but it needs a note input, which i think would be a more complicated script than what i’d like to do.

so here’s what i think i need to do:

i need to define a widget (which will be controlled by my footswitch - for this i’ll create a button and give it a name) - this part i can do!

i need to create a Gain and Balance control and name it - this i can also do.

i need to create a ramp generator that will start at a value of 1 and go to zero over a specified time - this step is very confusing to me. i could do the same, i suppose wth an ADSR (and i see there is something called “StartReleasePhase”), but i’m really stuck figuring out how to do this part.

i need to trigger the generator with the widget - i see a WidgetValueChanged callback

i need to get the value of the generator to control the Gain parameter of the Gain and Balance control.

is anyone willing to help me through this? or…is there a (Mac, AU preferably) plugin somewhere that i haven’t found yet that will do this kind of fadeout for me?

many thanks,

tony


#2

Hi Tony, try this:

var myRamp : Ramp
    TRIGGER : Widget  // Widget that starts the ramp
    VOLUME  : Widget  // Widget that controls audio level
    v_volume : double // Variable to get the current VOLUME level

initialization
 SetGeneratorOneShot(myRamp, true)
end

on WidgetValueChanged(newValue : double) from TRIGGER
 if newValue > 0.5 then
  v_volume = GetWidgetValue(VOLUME)
  
  myRamp.SetGeneratorLength(2000)  // 2000 msec
  SetTimersRunning(true)
  myRamp.EnableGenerator(true)
 end
end

on TimePassing(timeX : integer, amplitudeY : double) from myRamp
 SetWidgetValue(VOLUME, v_volume*(1.0-amplitudeY))
 if GetWidgetValue(VOLUME) < 0.01 then
  // Reset Trigger  
  SetWidgetValue(TRIGGER,0.0)  
 end 
end

#3

Gotta love automation :wink:

@pianopaul what about and easy way to “reverse it back”, so a timed fade IN?
Thanks in advanced :wink:


#4

Try this, you have do define an addition Midi In block (OSC Midi is fine):

var myRamp : Ramp
    TRIGGER : Widget  // Widget that starts the ramp
    VOLUME  : Widget  // Widget that controls audio level
    v_volume : double // Variable to get the current VOLUME level
    TIM : MidiInBlock
    Notes : midiMessage
    Direction : Integer

initialization
 SetGeneratorOneShot(myRamp, true)
 Notes = MakeNoteMessage(C3, 100)
 Direction = 1
end

on WidgetValueChanged(newValue : double) from TRIGGER
 if newValue > 0.5 then
  if Direction == 1 then
    v_volume = GetWidgetValue(VOLUME)
  end  
  
  myRamp.SetGeneratorLength(2000)  // 2000 msec
  SetTimersRunning(true)
  myRamp.EnableGenerator(true)
 end
end

on TimePassing(timeX : integer, amplitudeY : double) from myRamp

 if Direction == 1 then
  SetWidgetValue(VOLUME, v_volume*(1.0-amplitudeY))
 else
  SetWidgetValue(VOLUME, v_volume*amplitudeY)
 end
 
  if amplitudeY  > 0.99 then
   // Reset Trigger  
   SetWidgetValue(TRIGGER,0.0)
   if Direction == 1 then
    Direction = 2
   else
    Direction = 1
   end
  
   if Direction == 2 then
    ScheduleMidiEvent(TIM, Notes, 5000)
   end 
  end
end 

on NoteOnEvent(m : NoteMessage) from TIM
 Print("Hallo")
 SetWidgetValue(TRIGGER, 1.0)
end

#5

many, many thanks for this, paul! i will get this working on my rackspace, and then study it carefully to see why and how it does what it does. so much to learn…

tony


#6

ok…i pasted the script into the script editor for the rackspace, created a button widget and captioned it “TRIGGER” and a slider widget and captioned it “VOLUME”. the button widget responds too the footpedal, and the slider widget is controlling a Gain and Balance block before the output block.

the script compiles successfully, but also gives me a log screen that says:

The widget ‘TRIGGER’ is declared in a script but does not exist in the rackspace called ‘Big Looper’
The widget ‘VOLUME’ is declared in a script but does not exist in the rackspace called ‘Big Looper’

needless to say, it doesn’t run…

and needless to say, i already have questions, but let’s get this running first! thank you so much for your time and help.


#7

WOW!! thats great to have!!
Thanks a lot !!

I also will study so to learn and get a better understanding of scripts in general :wink:


#8

I have it running @tonycore, as you say if you already created the widgets, just hit compile again!


#9

You have to give Script namens for the Widgets!


#10

@tonycore yeah just re-read Captation is one thing - NAME (and then hit enter, so it sticks with it, so to speak)


#11

Got it, i’ve been doing that for Osc control but didn’t realize it was also for scripting. thank you!

now it works, and i can set about figuring out why!


#12

Sorry to ask @tonycore, what looper are you using with GP?


#13

no problem, i am using Augustus Looper by Expert Sleepers. it’s a bit old, but pretty awesome still…i have 3 instances of it in my Big Looper rackspace. it also has a second version that has 2 stereo sends and returns so you can mess with the loop, i’m thinking of setting that up with Loopback and another rackspace.

this is (for me) more soundscape style looping, not rhythmic, but you can use it for rhytmic looping as well.


#14

Thanks for the insight @tonycore , there aren’t that much 64bit loopers; and yeah I also like looping more on the “soundscape style”…


#15

so, here is my revised script, with these changes:

  1. i made the fade 20 seconds

  2. it does not reset the trigger (i do that with my footswitch)

  3. at the end of the fade, it clears the loops in the 3 Augustus Looper plugins by sending a parameter #49 message to them.

     var myRamp : Ramp
         TRIGGER : Widget  // Widget that starts the ramp
         VOLUME  : Widget  // Widget that controls audio level
         v_volume : double // Variable to get the current VOLUME level
         CTRLOOP, LOOP1, LOOP2 : PluginBlock
    
     initialization
      SetGeneratorOneShot(myRamp, true)
     end
    
     on WidgetValueChanged(newValue : double) from TRIGGER
      if newValue > 0.5 then
       v_volume = GetWidgetValue(VOLUME)
       
       myRamp.SetGeneratorLength(20000)  // 20 sec
       SetTimersRunning(true)
       myRamp.EnableGenerator(true)
       
      end 
       if newValue < 0.5 then
       SetWidgetValue(VOLUME,0.7)
      end 
     end
    
     on TimePassing(timeX : integer, amplitudeY : double) from myRamp
      SetWidgetValue(VOLUME, v_volume*(1.0-amplitudeY))
    
      
       if GetWidgetValue(VOLUME) < 0.01 then
       // Clear Loops 
       SetParameter(CTRLOOP,49,1.0) 
       SetParameter(LOOP1,49,1.0) 
       SetParameter(LOOP2,49,1.0)  
       end
      end 
    

i suspect i don’t have to have 3 separate “SetParameter” statements, right? is this not what arrays are for? how would i set that up so i can address all 3 instances of Augustus Looper at once? i tried declaring:

LOOPERS : Array

and then in the initialization statement adding

LOOPERS [CTRLOOP, LOOP1, LOOP2]

but it wouldn’t let me do that.


#16

also - what is the difference between setting a scripting name for a widget in the edit view (as keyman illustrated above), and setting it in the Connections view using the right-click Osc/GScript item? they are obviously different things with different results, but what exactly is the difference? thanks.

and how do you paste your scripts in like that, paul, so they are formatted and look like scripts?

i told you i was a newbie!


#17

Just use the tab - symbol </> and put code inside to get preformatted text :wink:
var myRamp : Ramp
05


#18

thanks! little by little i will learn this stuff…


#19

Well, the following is how it’s supposed to be done but unfortunately, it looks like I forgot to implement arrays of plugin blocks. I’ll fix that ASAP

 var
    CTRLOOP, LOOP1, LOOP2 : PluginBlock
    LOOPERS : PluginBlock Array
  
 Initialization
    LOOPERS = [CTRLOOP, LOOP1, LOOP2]
 End   

#20

Not sure I understand this question. In the former you’re setting a script name for a widget and in the latter you’re setting a script name for a plugin block