Tuesday, August 16, 2016

Minim 7. Play A File

An AudioPlayer object is used to play the same mp3 file as in the last example. We have to put the groove.mp3 file in this sketch's data folder.


By pressing any key we can pause audio (if playing) or start (if paused or finished).


# Ex7.pyde
# Based on Java File in Examples: PlayAFile.pde

'''
This sketch demonstrates how to play a file with Minim
using an AudioPlayer. It's also a good example of how
to draw the waveform of the audio. Full documentation
for AudioPlayer can be found at http://
code.compartmental.net/minim/
audioplayer_class_audioplayer.html
For more information about Minim and additional features,
visit http://code.compartmental.net/minim/
'''

add_library('minim')

player = None

def setup():
    size(1024, 200)
    global player
    minim = Minim(this)
    player = minim.loadFile("groove.mp3")
    
def draw():
    background(0)
    stroke(255)
    # draw the waveforms
    # the values returned by left.get() and right.get()
    # will be between -1 and 1, so we need to scale them
    # up to see the waveform. Note that if the file is
    # MONO, left.get() and right.get() will return the
    # same value
    for i in range(player.bufferSize()-1):
        x1 = map(i, 0, player.bufferSize(), 0, width)
        x2 = map(i+1, 0, player.bufferSize(), 0, width)
        line( x1, 50 + player.left.get(i)*50, 
             x2, 50 + player.left.get(i+1)*50 )
        line( x1, 150 + player.right.get(i)*50,
             x2, 150 + player.right.get(i+1)*50)
    posx = map(player.position(), 0, player.length(),
               0, width)
    stroke(0,200,0)
    line(posx, 0, posx, height)
    if player.isPlaying():
        text("Press any key to pause playback.", 10, 20)
    else:
        text("Press any key to start playback.", 10, 20)
        
def keyPressed():
    if player.isPlaying():
        player.pause()
    # if the player is at the end of the file,
    # we have to rewind it before telling it to
    # play again
    elif player.position() == player.length():
        player.rewind()
        player.play()
    else:
        player.play() 

This is the output:


Minim 6. Draw Waveform And Level

The file "groove.mp3" is in the data folder for this sketch.


We draw each 1024 sample buffer as well as the RMS level.


# Ex6.pyde
# Based on Java File in Examples: DrawWaveformAndLevel.pde

'''
This sketch demonstrates how to use the AudioBuffer
objects of an AudioPlayer to draw the waveform and
level of the sound as it is playing. These same 
AudioBuffer objects are available on AudioInput,
AudioOuput, and AudioSample, so the same drawing
code will work in those cases.
'''

add_library('minim')

groove = None

def setup():
    size(1024, 200)
    global groove
    minim = Minim(this)
    groove = minim.loadFile("groove.mp3", 1024)
    groove.loop()
    
def draw():
    background(0)
    stroke(255)
    # draw the waveforms
    # the values returned by left.get() and right.get()
    # will be between -1 and 1, so we need to scale them
    # up to see the waveform. Note that if the file is
    # MONO, left.get() and right.get() will return the
    # same value
    for i in range(groove.bufferSize()-1):
        x1 = map(i, 0, groove.bufferSize(), 0, width)
        x2 = map(i+1, 0, groove.bufferSize(), 0, width)
        line( x1, 50 + groove.left.get(i)*50, 
             x2, 50 + groove.left.get(i+1)*50 )
        line( x1, 150 + groove.right.get(i)*50,
             x2, 150 + groove.right.get(i+1)*50)
    noStroke()
    fill(255,128)
    # the value returned by the level method is the RMS
    # (root-mean-square)
    # value of the current buffer of audio.
    # see: http://en.wikipedia.org/wiki/Root_mean_square
    rect( 0, 0, groove.left.level()*width, 100)
    rect( 0, 100, groove.right.level()*width,100)

This is the output:


Minim 5. Record Audio Output

It is often important to save the audio to disk in a wav file. When 'r' is pressed we save audio to memory, and when 's' is pressed we finally save it to disk.


A sine oscillator is controlled by a sawtooth modulator. The sawtooth is at 4 Hz, and we can see the audio output (shown at bottom), modulates over 0.25 seconds.


# Ex5.pyde
# Based on Java File in Examples: RecordAudioOutput.pde

'''
This sketch demonstrates how to use an AudioRecorder
to record audio to disk. Press 'r' to toggle recording
on and off and the press 's' to save to disk. The
recorded file will be placed in the sketch folder
of the sketch. For more information about Minim and
additional features, visit
http://code.compartmental.net/minim/
'''

add_library('minim')

out = None
recorder = None

def setup():
    size(512, 200)
    global out, recorder
    minim = Minim(this)
    # use the getLineOut method of the Minim object to
    # get an AudioOutput object
    out = minim.getLineOut()
    # create a recorder that will record from the output
    # to the filename specified. The file will be located
    # in the sketch's root folder.
    recorder = minim.createRecorder(out, "myrecording.wav")
    # patch some sound into the output so we have something
    # to record
    wave = Oscil(440, 1.0)
    mod  = Oscil(4.0,  0.25, Waves.SAW)
    mod.offset.setLastValue(0.5)
    mod.patch(wave.amplitude)
    wave.patch(out)
    textFont(createFont("Arial", 12));
    
    
def draw():
    background(0,0,255)
    stroke(255,0,0)
    # draw the waveforms
    for i in xrange(out.bufferSize()-1):
        line(i, 50 - out.left.get(i)*50,
             i+1, 50 - out.left.get(i+1)*50)
        line(i, 150 - out.right.get(i)*50,
             i+1, 150 - out.right.get(i+1)*50)
    if recorder.isRecording():
        text("Currently recording ...", 5, 15)
    else:
        text("Not recording.", 5, 15)
        
def keyReleased():
    if key == 'r':
        # to indicate that you want to start or stop
        # capturing audio data, you must call
        # beginRecord() and endRecord() on the
        # AudioRecorder object. You can start and stop
        # as many times as you like, the audio data
        # will be appended to the end of the buffer,
        # in the case of buffered recording, or to
        # the end of the file, in the case of streamed
        # recording).
        if recorder.isRecording():
            recorder.endRecord()
        else:
            recorder.beginRecord()
    if key == 's':
        # we've filled the file out buffer,
        # now write it to the file we specified
        # in createRecorder in the case of buffered
        # recording, if the buffer is large, this
        # will appear to freeze the sketch for sometime
        # in the case of streamed recording, it will not
        # freeze as the data is already in the file
        # and all that is being done is closing the file.
        # The method returns the recorded audio as an
        # AudioRecording, see the example
        # AudioRecorder >> RecordAndPlayback for more
        # about that
        recorder.save()
        print "Done saving."

This is the output while recording:



The saved file shows a sine wave which changes amplitude:

Monday, August 15, 2016

Minim 4. Create An Instrument

A sine instrument is created which is controlled by a Line UGen which goes from 0.5 to 0 in note's duration.


The class SineInstrument needs out in the noteOn and noteOff methods. Before we can use this class, we have to create the out, the AudioOutput object, which is done in the beginning of setup().


# Ex4.pyde
# Based on Java File in Examples: CreateAnInstrument.pde

'''
This sketch demonstrates how to create synthesized sound
with Minim using an AudioOutput and an Instrument we
define. By using the playNote method you can schedule
notes to played at some point in the future, essentially
allowing to you create musical scores with code. Because
they are constructed with code, they can be either
deterministic or different every time. This sketch
creates a deterministic score, meaning it is the same
every time you run the sketch. For more complex examples
of using playNote check out algorithmicCompExample and
compositionExample in the Synthesis folder. For more
information about Minim and additional features, visit
http://code.compartmental.net/minim/
'''

add_library('minim')

out = None

class SineInstrument(Instrument):
    def __init__(self, frequency):
        # make a sine wave oscillator
        # the amplitude is zero because
        # we are going to patch a Line to it anyway
        self.wave = Oscil(frequency, 0, Waves.SINE)
        self.ampEnv = Line()
        self.ampEnv.patch(self.wave.amplitude)
    def noteOn(self, duration):
        # start the amplitude envelope
        self.ampEnv.activate(duration,0.5,0)
        # attach the oscil to the output so it makes sound
        self.wave.patch(out)
    def noteOff(self):
        # this is called by the sequencer when the
        # instrument should stop making sound
        self.wave.unpatch(out)

def setup():
    size(512, 200)
    global out
    minim = Minim(this)
    # use the getLineOut method of the Minim object to
    # get an AudioOutput object
    out = minim.getLineOut()
    # when providing an Instrument, we always specify
    # start time and duration
    out.playNote(0.0, 0.9, SineInstrument(97.99))
    out.playNote(1.0, 0.9, SineInstrument(123.47))
    # we can use the Frequency class to create
    # frequencies from pitch names
    freq = Frequency.ofPitch("C3").asHz()
    out.playNote(2.0, 2.9, SineInstrument(freq))
    freq = Frequency.ofPitch("E3").asHz()
    out.playNote(3.0, 1.9, SineInstrument(freq))
    freq = Frequency.ofPitch("G3").asHz()
    out.playNote(4.0, 0.9, SineInstrument(freq))
    
    
def draw():
    background(0,0,255)
    stroke(255,0,0)
    # draw the waveforms
    for i in xrange(out.bufferSize()-1):
        line(i, 50 - out.left.get(i)*50,
             i+1, 50 - out.left.get(i+1)*50)
        line(i, 150 - out.right.get(i)*50,
             i+1, 150 - out.right.get(i+1)*50)

This is the output:


Sunday, August 14, 2016

Minim 3. Sequence Sound

The default Sequencer is used to create different notes.


The playnote method of the AudioOutput is used to set different notes to be played at different time offsets.


The comments from the Java file in the Examples folder give more details.


# Ex3.pyde
# Java File in Examples: SequenceSound.pde

'''
This sketch demonstrates how to create synthesized sound with Minim using
an AudioOutput and the default instrument built into an AudioOutput. By
using the playNote method you can schedule notes to be played at some
point in the future, essentially allowing to you create musical scores
with code. Because they are constructed with code, they can be either
deterministic or different every time. This sketch creates a
deterministic score, meaning it is the same every time you run the
sketch. It also demonstrates a couple different versions of the playNote
method. For more complex examples of using playNote check out
algorithmicCompExample and compositionExample in the Synthesis folder.
For more information about Minim and additional features, visit
http://code.compartmental.net/minim/
'''

add_library('minim')

out = None

def setup():
    size(512, 200)
    global out
    minim = Minim(this)
    # use the getLineOut method of the Minim object to
    # get an AudioOutput object
    out = minim.getLineOut()
    # set the tempo of the sequencer
    # this makes the first argument of playNote
    # specify the start time in quarter notes
    # and the duration becomes relative to the length
    # of a quarter note. By default the tempo is 60 BPM
    # (beats per minute). At 60 BPM both start time and
    # duration can be interpreted as seconds.
    # To retrieve the current tempo, use getTempo().
    out.setTempo(80)
    # pause the sequencer so our note play back will
    # be rock solid. If you don't do this, then tiny bits
    # of error can occur since the sequencer is running
    # in parallel with you note queueing.
    out.pauseNotes()
    # given start time, duration, and frequency
    out.playNote(0.0, 0.9, 97.99)
    out.playNote(1.0, 0.9, 123.47)
    # given start time, duration, and note name
    out.playNote(2.0, 2.9, "C3")
    out.playNote(3.0, 1.9, "E3")
    out.playNote(4.0, 0.9, "G3")
    # given start time and note name or frequency
    # (duration defaults to 1.0)
    out.playNote(5.0, "")
    out.playNote(6.0, 329.63)
    out.playNote(7.0, "G4")
    # the note offset is simply added into the start time of
    # every subsequenct call to playNote. It's expressed in beats.
    # To get the current note offset, use getNoteOffset()
    out.setNoteOffset(8.1)
    # because only given a note name or frequency
    # starttime defaults to 0.0 and duration defaults to 1.0
    out.playNote("G5")
    out.playNote(987.77)
    # now we can start the sequencer again to hear our sequence
    out.resumeNotes()
    
def draw():
    background(255,192,128)
    # draw the waveform of the output
    for i in xrange(out.bufferSize()-1):
        line(i, 50 - out.left.get(i)*50,
             i+1, 50 - out.left.get(i+1)*50)
        line(i, 150 - out.right.get(i)*50,
             i+1, 150 - out.right.get(i+1)*50)

This is the output:


Minim 2. Patching an Input

A sine wave modulates the amplitude of a triangle wave (amplitude modulation).


We modulate at a frequency of 2 Hz. The triangle is then sent to out. Notice out is defined as global in setup(), otherwise it will have local scope. Also draw() does not have to know have that it is global, since here it is read-only and global will be searched since there is no local variable by that name.


# Ex2.pyde
# PathingAnInput.pde in Examples

'''
This sketch demonstrates how to create a simple
synthesis chain that involves controlling the
value of a UGenInput with the output of a UGen.
In this case, we patch an Oscil generating a
sine wave into  the amplitude input of an Oscil
generating a triangle wave. The result is known
as amplitude modulation. For more information
about Minim and additional features, visit
http://code.compartmental.net/minim/
'''

add_library('minim')

out = None

def setup():
    size(512, 200)
    global out
    minim = Minim(this)
    # use the getLineOut method of the Minim object to
    # get an AudioOutput object
    out = minim.getLineOut()
    # create a triangle wave Oscil, set to 440 Hz,
    # at 1.0 amplitude. In this case, the amplitude
    # that we construct the Oscil with doesn't matter
    # because we will be patching something to its
    # amplitude input.
    wave = Oscil(440, 1, Waves.TRIANGLE)
    # create a sine wave Oscil for modulating the
    # amplitude of wave
    mod = Oscil(2, 0.4, Waves.SINE)
    # mod patched to wave amplitude input
    mod.patch(wave.amplitude)
    # patch wave to the output
    wave.patch(out)
    # green stroke of 2 width for the draw
    stroke(0,255,0)
    strokeWeight(2)
    
def draw():
    background(255,128,128)
    # draw the waveform of the output
    for i in xrange(out.bufferSize()-1):
        line(i, 50 - out.left.get(i)*50,
             i+1, 50 - out.left.get(i+1)*50)
        line(i, 150 - out.right.get(i)*50,
             i+1, 150 - out.right.get(i+1)*50)

This is the output:


Minim 1. Synthesize Sound

We are using Processing in the Python Mode. Minim is one audio library that may be installed for Processing.


We are using an Oscil UGEN. This repeats at frequency (first argument in constructor). It is set at 440 initially. When the program is running we can change it by moving mouse in x direction.


# Ex1.pyde
# SynthesizeSound.pde in Examples

'''
This sketch demonstrates how to create synthesized
sound with Minim using an AudioOutput and an Oscil.
An Oscil is a UGen object, one of many different
types included with Minim. By using the numbers 1
thru 5, you can change the waveform being used by
the Oscil to make sound. These basic waveforms are
the basis of much audio synthesis. For many more
examples of UGens included with Minim, have a look
in the Synthesis folder of the Minim examples. For
more information about Minim and additional features,
visit http://code.compartmental.net/minim/
'''

add_library('minim')

out = None
wave = None

def setup():
    size(512, 200)
    global out, wave
    minim = Minim(this)
    # use the getLineOut method of the Minim object to
    # get an AudioOutput object
    out = minim.getLineOut()
    print type(out)
    # create a sine wave Oscil, set to 440 Hz, at 0.5
    # amplitude
    wave = Oscil(440,0.5, Waves.SINE)
    # patch the Oscil to the output
    wave.patch(out)
    print type(wave)
    
def draw():
    background(0)
    stroke(255)
    strokeWeight(1)
    # draw the waveform of the output
    for i in xrange(out.bufferSize()-1):
        line(i, 50 - out.left.get(i)*50,
             i+1, 50 - out.left.get(i+1)*50)
        line(i, 150 - out.right.get(i)*50,
             i+1, 150 - out.right.get(i+1)*50)
    # draw the waveform we are using in the oscillator
    stroke(128,0,0)
    strokeWeight(4)
    for i in range(width):
        point(i,height/2-(height*0.49) *
              wave.getWaveform().value(float(i)/ width))

def mouseMoved():
    # usually when setting the amplitude and frequency of
    # an Oscil you will want to patch something to the
    # amplitude and frequency inputs but this is a quick
    # and easy way to turn the screen into an x-y control
    # for them.
    amp = map(mouseY, 0, height, 1, 0)
    wave.setAmplitude(amp)
    freq = map( mouseX, 0, width, 110, 880 )
    wave.setFrequency(freq)
    
def keyPressed():
    if key == '1': wave.setWaveform(Waves.SINE)
    elif key == '2': wave.setWaveform(Waves.TRIANGLE)
    elif key == '3': wave.setWaveform(Waves.SAW)
    elif key == '4': wave.setWaveform(Waves.SQUARE)
    elif key == '5': wave.setWaveform(Waves.QUARTERPULSE)
    
# printouts
# <type 'ddf.minim.AudioOutput'>
# <type 'ddf.minim.ugens.Oscil'>

This is the output after pressing 3 to change Waveform to sawtooth: