Newbie: Setting Countdown for Amp

Dear SC Community,

I am controlling a ~synth with OSC messages and i want to achieve, that the synth only sounds when receiving OSC messages. The messages will arrive about two times a second. My idea was to implement a timer that starts from 5 sec. When it reaches 0 amp will turn to 0. Otherwise it should be 0.2. When the OSC messsage arrives, the timer should be setted again to 5. If the timer runs out and the amp is on 0 a new OSC message should turn it on again (and ofc set the timer to 5).
Unfortunately I am not able to implement that. I tried with Timer.ar and with SystemClock.sched but still I could not change the amp with it. Does anyone have an idea how this could be implemented?

(

~synth = {arg freq=250, der=0.5, f,  amp = 0.2, t;
	t=3;

	SystemClock.sched(t, {~synth.set(\amp, 0);});



	(
	((SinOsc.ar(freq, mul:amp!2) +
		SinOsc.ar(freq, mul:amp!2))
		
		)* SinOsc.ar(freq,mul:0.2!2)
	)




}.play;
)


(
//an OSC listener that sends set messages


OSCdef.new('OSClistenerNEW', {
	arg msg;
	var t;


	~synth.set(\t, 10);


	
}, '/OSC');

)

Thanks in advance and kind regards,
Leon

If I understand your requirement correctly, you will probably want to use a slightly different approach: create a new synth for every note (every received OSC msg), and in that synth’s SynthDef use an envelope to modulate amplitude over time, and use a DoneAction so that Synths clean up after themselves instead of staying around and clogging up the memory.

Thank you for your suggestion. I feel like I am closer but I cant use an Ugen for .set, therefore I cant use the envelope in one Synthdef to control another synth.
Or is there anyway around that?

kind regards

From your reply it seems I have no idea what you are trying to accomplish. Sorry :frowning:

What I originally understood is that you want:

  • you receive an OSC msg in supercollider
  • this OSC msg triggers a note that lasts for 10 seconds (or some amount of seconds that is part of the OSC msg data)

In that case, in your OSC handler, each time you receive an OSC msg you should instantiate a Synth for a single note (and if needed, you can pass the duration of the note as a parameter of the SynthDef and use that in an envelope to change the amplitude over time).

But now you mention controlling synths from other synths. I’m not sure what behavior you are trying to get.

Maybe you have a single sound that sounds infinitely long, but you want to silence it from time to time? In that case you can use .set to set the amp argument (which you have to add and use in the SynthDef used to generate the infinite sound) and if you don’t want the amplitude to change immediately, you can use a Lag or VarLag UGen in the SynthDef.

But maybe you still want something else, and I honestly have no clue what it could be.

If I’m understanding correctly, this could be done simply with an envelope and a trigger input. I’ll also add a second envelope for a smooth release when you want to delete the synth. (EDIT: First time, I omitted the ‘gate’ argument, fixed now.)

SynthDef(\alivetrig, { |out, freq = 440, t_trig = 1, gate = 1, aliveTime = 5, amp = 0.2|
    var aliveEg = EnvGen.kr(Env([0, 1, 1, 0], [0.01, aliveTime, 0.02]), t_trig);
    var endEg = EnvGen.kr(Env.asr(0.01, 1, 0.02), gate, doneAction: 2);
    var sig = SinOsc.ar(freq * [1, 1.008]);
    Out.ar(out, sig * (amp * aliveEg * endEg));
}).add;

The OSC responder should do mySynth.set(\t_trig, 1) to reset the timer.

This will not delete the synth if the 5 second timer expires, but the original problem spec didn’t say anything about that, so let’s see if the simple way is enough.

hjh