// adding some controlled randomness throughout... // patch SqrOsc s => LPF f => ADSR e => JCRev r => dac; // not heard SinOsc lfo => blackhole; // set env params e.set( 10::ms, 5::ms, .5, 20::ms ); // close the env to start with e.keyOff(); // "ketchup" .025 => r.mix; // gain .5 => r.gain; // quarter note 200::ms => dur quarter; // spork sweep as concurrent process spork ~ sweep(); // "chroma" [ 0, 2, 4, 7, 9 ] @=> int foo[]; // seed the random number generator for reproducible results // Std.srand( 91 ); // go while( true ) { // play repeat( Std.rand2( 1, 10 ) ) { // decide if( maybe && maybe ) { // play from pitch class array play( 36 + Std.rand2(0,3)*12 + foo[Std.rand2(0,foo.size()-1)], .8, quarter ); } else { // play other stuff play( Std.rand2( 48, 84 ), .8, quarter/2 ); play( Std.rand2( 48, 84 ), .8, quarter/2 ); } } // rest quarter * Std.rand2(0, 3) => now; } // play fun void play( float pitch, float velocity, dur T ) { // open the env pitch => Std.mtof => s.freq; // start the attack e.keyOn(); // reset lfo; NOTE: play with this for different attacks too Std.rand2f(0, .1) => lfo.phase; // wait T-e.releaseTime() => now; // close the env e.keyOff(); // let it release e.releaseTime() => now; } // sweep fun void sweep() { // NOTE: change this to change sweep rate 3.2 => lfo.freq; // NOTE: change this to change filter Q 4 => f.Q; // go! while( true ) { // sweep (becareful to stay in valid frequency ranges 500 + (lfo.last()+1)/2*2000 => f.freq; // advance time 10::ms => now; } }