cm-incudine extends common music 2 (the common lisp port of common music) with realtime capabilities using the incudine realtime system by Tito Latini. Currently realtime MIDI, FUDI, OSC and any function call are supported. Note: incudine currently only works with sbcl and you will need either a working JACK, or PortMidi setup.
The Common Lisp package depends on
As all the code is evaluated within the :cm
package and exported
from there, code evaluation should take place within the :cm
package as well.
Realtime processes can be invoked by either using the events
function with an incudine-stream or *rts-out*
as second argument
or the sprout
function. The processes now also support realtime
FUDI messages in addition to OSC and MIDI messages.
********************************************************************** Copyright (c) 2018 Orm Finnendahl <orm.finnendahl@selma.hfmdk-frankfurt.de> Revision history: See git repository. This program is free software; you can redistribute it and/or modify it under the terms of the Gnu Public License, version 2 or later. See https://www.gnu.org/licenses/gpl-2.0.html for the text of this agreement. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. **********************************************************************
You will need a system that has a working sbcl setup. In addition you will need to setup JACK (for Linux), or PortMidi (for Windows, OSX or a Linux system running PulseAudio).
First get all Common Lisp components:
Using a common lisp with quicklisp installed, copy all the folders of the prerequsites into the local-projects subfolder of your local quicklisp installation folder (default is <home>/quicklisp/local-projects).
First start JACK, then sbcl and evaluate the following:
(ql:quickload "cm-incudine")
(cm:rts)
The last command automatically changes into the :cm
package,
starts the incudine realtime thread, adds audio ports and MIDI
ports to jack.
To send realtime MIDI messages to your midi output you can use
output
, events
or sprout
. Before testing the following code
make sure some MIDI synth (e.g. QSynth) is started and connected to
the incudine midi-out port (e.g. using the QjackCtl program).
(output (new midi))
(events
(loop for x below 10
collect (new midi :time (* x 0.5) :keynum (between 60 71)))
*rts-out*)
(sprout
(loop for x below 10
collect (new midi :time (* x 0.5) :keynum (between 60 71))))
(events
(process
repeat 5
output (new midi :time (now) :keynum (between 60 71))
wait 0.5)
*rts-out*)
(sprout
(process
repeat 5
output (new midi :time (now) :keynum (between 60 71))
wait 0.5))
Sending to Pure Data requires to first start pd and open or create
a patch containing a [netreceive 3012]
object. For testing
purposes a [print]
object connected to the netreceive’s left
outlet can be used. In this case watch the messages appearing in
pd’s post window, when sending FUDI messages from cm to pd using
the code below.
(fudi-open-default :host "127.0.0.1" :port 3012 :direction :output)
(sprout
(process
repeat 2
output (new fudi :time (now) :message '(1 2 3 4))
wait 1))
Receiving FUDI also works after opening the respective stream with
(fudi-open-default :host "127.0.0.1" :port 3011 :direction :input)
Please refer to the common music docs for handling input events and establishing receivers.
Sending OSC messages is similar to sending FUDI messages except that OSC requires argument type information in addition to the message itself.
(osc-open-default :host "127.0.0.1" :port 3003 :direction :output)
(sprout
(process
repeat 2
output (new osc :time (now) :types "iiii" :message '(1 2 3 4))
wait 1))
receiving OSC also works after opening the respective stream with
(osc-open-default :host "127.0.0.1" :port 3004 :direction :input)
Please refer to the common music docs for handling input events and establishing receivers.
The default time format is :sec but can also be set to :sample or :ms
with the function set-time-format
.
The functions at
and now
are wrappers for the same incudine
functions which automatically translate from/to the current
time-format.
For other usage examples see the file src/cm-incudine-examples.lisp
.
Orm Finnendahl 2017/18