1

[1,2,3].do { /* how to wait 1s here? */ }

I am learning supercollider. I have found the SimpleNumber.wait function, but I soon learned that it doesn't work within "normal" functions, only within some "different" kind of functions called Routines.

I deliberately stopped right there to ask the question: is there a simple way to pause for a given amount of time within each iteration of the someArray.do construct? By "simple way" I mean something that won't require learning a dozen new concepts and going through a paradigm shift.

NOTE WELL: I know that I will eventually need to learn the whole huge book about Routines, Tasks and other sequencing mechanisms in supercollider, but for now I just want to play "Mary Had A Little Lamb" and call it a noob's day, without having to learn all of that before I can make anything at all happen.

Is this possible?

Szczepan Hołyszewski
  • 2,707
  • 2
  • 25
  • 39

1 Answers1

5

A Routine is required to use .wait / .yield functionality. When you call e.g. 3.wait, you're telling a Clock somewhere to wait for 3 seconds, and then continue things from where you left off. In order to do this, you need to be communicating with a clock, and you need something that can be stopped and started (a Routine executing some function).

The complete syntax for what you're trying to do would be:

Routine({
   [1, 2, 3].do {
      |n|
      n.postln;
      1.wait;
   }
}).play(AppClock);

The above creates a Routine with a function (your 1, 2, 3 loop), and then plays it on a clock (AppClock, the standard clock).

However, the .fork method on functions is a shorthand for doing the above (i.e. creating a Routine and playing it):

{
   [1, 2, 3].do {
      |n|
      n.postln;
      1.wait;
   }
}.fork();
scztt
  • 1,053
  • 8
  • 10