[flocking-users] Play buffer from the beginning

Colin Clark colin at colinclark.org
Wed Jan 15 05:59:03 EST 2014


Hi again Roger,

Yup, that works nicely. Glad you got it working!

If you find yourself need to programmatically fire a trigger at some arbitrary user-defined time, I’m working on an “external trigger” unit generator that will enable this. It’s slightly tricky because in the long run I expect all unit generators to run in a Web Worker for performance reasons, so the only way to send them messages from the main thread will be via calls to .set(). I had imagined that I could just make a unit generator that has a .fire() method on it, but this future constraint means that unit generators can’t, in practice, implement any other methods aside from .gen(), .get(), and .set(). So I’ve got a bit more architectural thinking to do before I can roll it out.

In the meantime, you can use the flock.ugen.valueChangeTrigger unit generator to programmatically send it any value, which will cause it to fire (though this behaviour may change in the future). Here’s an example:

{
  ugen: "flock.ugen.playBuffer",
  buffer: {
    id: "chord",
    url: "../../shared/audio/hillier-first-chord.wav"
  },

  trigger: {
    id: "trig",
    ugen: “flock.ugen.valueChangeTrigger”,
    source: 0.0
  }
}

// When run in the playground, this will trigger whenever the “scope canvas” (top right corner) is clicked.
$("body").click(function () {
    synth.set("trig.source", 1.0); // Any value here should be fine. It'll automatically fire the trigger when it sees that an input was changed.
});

Colin

On Jan 15, 2014, at 5:42 AM, roger pibernat <rogerpibernat at gmail.com> wrote:

> I think I got it:
> 
> var synth = flock.synth({
>     synthDef: {
>         id: "piano",
>         ugen: "flock.ugen.playBuffer",
>         buffer: {
>             id: "chord",
>             url: "data/audio/piano-C3.wav"
>         },
>         trigger: {
>             ugen: "flock.ugen.impulse",
>             freq: 0.1
>         }
>     }
> });
> 
> function playSynth() {
>     console.log("playing synth");
>     synth.input("piano.trigger.phase", 1.0);
>     synth.play();
> }
> 
> function stopSynth() {
>     console.log("reset synth");
>     synth.pause();
> }
> 
> 
> Roger
> 
> (+34) 639 81 26 71
> http://www.rogerpibernat.com
> http://www.wucollective.com
> 
> 
> On Wed, Jan 15, 2014 at 11:38 AM, roger pibernat <rogerpibernat at gmail.com> wrote:
> Awesome Colin!!
> 
> Thanks you soooo much!  You made my day.  
> 
> I'm not quite there, yet, though.  I need to trigger the playBuffer synth from a function.  I guess I need a different ugen in the trigger, then.  What would that be?
> 
> 
> Roger
> 
> (+34) 639 81 26 71
> http://www.rogerpibernat.com
> http://www.wucollective.com
> 
> 
> On Wed, Jan 15, 2014 at 11:25 AM, Colin Clark <colin at colinclark.org> wrote:
> Hi Roger,
> 
> I’ll respond to both of your questions in this email below. Sorry for the delay!
> 
> On Jan 15, 2014, at 4:52 AM, roger pibernat <rogerpibernat at gmail.com> wrote:
> 
> > I'm trying to set the speed of a buffer before playing it with
> >
> >   var synth = flock.synth({
> >         synthDef: {
> >             ugen: "flock.ugen.playBuffer",
> >             buffer: {
> >                 id: "chord",
> >                 url: "data/audio/piano-C3.wav"
> >             }
> >         }
> >  });
> >  function playSynth()
> >     {
> >         synth.set("speed", 0.5);
> >         synth.play();
> >     }
> >
> > but it's not working.  Is this the right syntax?
> 
> Close, but not quite. If you want to set values on a unit generator, you have to give it an “id” first. It’s a bit like assigning it to a variable. So you can just modify your synthDef like this:
> 
> {
>   id: “player”, // <— Give this unit generator a name so you can refer to it in subsequent calls to set()
>   ugen: "flock.ugen.playBuffer”,
>   buffer: {
>     id: "chord",
>     url: "data/audio/piano-C3.wav"
>   }
> }
> 
> And then you can set the speed input like this:
> 
> synth.set(“player.speed”, 0.5); // <— Use the fully-qualified path.
> 
> > On Mon, Jan 13, 2014 at 2:58 PM, roger pibernat <rogerpibernat at gmail.com> wrote:
> > Hi there,
> >
> > I've been trying to play a buffer from the beginning every time I hit a button, but I can't reset it.  If I stop it and hit play again, it keeps running where it stopped.  I'm using readBuffer, because on the demo it works just fine.  How does it work?  Here's my code.
> >
> >     var synth = flock.synth({
> >         synthDef: {
> >             ugen: "flock.ugen.readBuffer",
> >             buffer: {
> >                 id: "chord",
> >                 url: "data/audio/piano-C3.wav"
> >             }
> >             ,
> >             phase: {
> >                 ugen: "flock.ugen.lfSaw",
> >                 freq: (1/4),
> >                 mul: 0.5,
> >                 add: 0.5
> >             }
> >         }
> >     });
> >
> >     function playSynth()
> >     {
> >         console.log("playing synth");
> >         synth.play();
> >     }
> >
> >     function stopSynth()
> >     {
> >         console.log("stopping synth");
> >         synth.pause();
> >     }
> 
> 
> There are two ways to do this. This demo illustrates the simplest way:
> 
> http://flockingjs.org/demos/interactive/html/playground.html#playBufferTrigger
> 
> Play buffer accepts a “trigger” input. A trigger is any signal that crosses from 0 to a positive value and back again. Whenever flock.ugen.playBuffer receives a trigger, it will start at the beginning of the buffer.
> 
> In the case of the demo, the trigger is fired by the flock.ugen.mouse.cursor unit generator. You can set it up like this so it will only trigger when the button clicks:
> 
> {
>   ugen: "flock.ugen.playBuffer",
>   buffer: {
>   id: "chord",
>     url: "../../shared/audio/hillier-first-chord.wav"
>   },
> 
>   trigger: {
>     ugen: “flock.ugen.mouse.click”,
>     options: {
>       target: “#myButton” // <— Any selector is valid here, or a raw DOM element.
>   }
> }
> 
> Alternatively, you could use the flock.ugen.readBuffer unit generator as you were, but reset its phase input to move back to the beginning of the buffer. Here’s an example:
> 
> {
>   ugen: "flock.ugen.readBuffer",
>   buffer: {
>     id: "chord",
>     url: "../../shared/audio/hillier-first-chord.wav"
>   },
>   phase: {
>     id: "phasor”, // <— Give your phasor a name.
>     ugen: "flock.ugen.lfSaw",
>     freq: (1/4),
>     mul: 0.5,
>     add: 0.5
>   }
> }
> 
> function playSynth()
> {
>     console.log("playing synth");
>     synth.set("phasor.phase", 1.0); // This will cause the phase to loop back to the beginning at the next sample generation block.
>     synth.play();
> }
> 
> The readBuffer unit generator is a bit more of a low-level, but it allows precise control over how the buffer is read if you need it. I’d typically use playBuffer unless I was doing some really funky effects with playback speed.
> 
> I hope this helps,
> 
> Colin
> 
> 




More information about the flocking mailing list