Performance
The performance layer is session-view style: tracks persist, clips launch on them, scenes launch sets of clips. Arrangements sequence the same structures for offline renders.
Tracks
Section titled “Tracks”A track has parameters, default instrument, note effects, audio effects, sends, and a mixer. In each stage, it is that stage’s input.
track bass(tone: hz = 2khz) { instrument = pluck(bright: 0.4) notes = it.thin(10%) out = it.drive(amount: 0.2).lpf(cutoff: tone) space += out.gain(-14db)}- Tracks with an instrument play plain note patterns (MIDI-clip style).
- Tracks are created on first use.
- Mixer:
gain,pan,mute,solo;with(quantize: ...)for launch quantization. - Re-evaluating a track carries effect state without clicks.
A clip is a section for one track: lanes on one timeline.
clip riff { length: 2 bars notes: [c2 ~ eb2 g1 ~ c2 bb1 ~] gain: [0db -6db -3db -9db] bright: [0.2 0.5 0.8] tone: env[400hz (2 bars).exp 3khz]}- Lane targets:
notes, instrument parameters, track parameters, universal controls. Unknown lanes are errors. Clip lanes target only their track; scene/arrangement lanes can target any track. - Step lanes read at note start and cycle (polymeter);
.per_notemaps nth note → nth value. - Envelope/signal lanes run on the clip timeline, restart on launch, loop with the clip.
- Shorthand:
[c2 ~ eb2]→clip { notes: [...] }.load("...nms")is also a clip. riff.set(bright: [0.9])— lanes are fields.
Scenes and arrangement
Section titled “Scenes and arrangement”scene verse { bass: riff, drums: groove, keys: ~ }scene chorus { bass: riff.transpose(+5st), drums: groove, keys: chords }
launch chorus @ next 4 barsA bare pattern such as theme = [c4 e4 g4 b4] is shorthand for a clip with only a notes lane, and everything below works the same on both. A clip with no length: runs freely: its cycles keep counting, so <a b> and every alternate. Give it a length: and it loops, starting over each time.
Launching a scene starts the clips it lists and stops every other track that has an instrument, so a scene is the whole picture: leave a track out and it falls silent. ~ still works for a track you want to name as silent. To add a fill for a bar, write it as a play line instead of a scene.
See Score model for arrangement-level tempo, meter, and lanes.
Live commands
Section titled “Live commands”While a scene is playing you can change what a track plays by writing the change after its name. It lands on the next boundary, like a play, and the track’s clip starts over there:
launch versebass.reverse // the bass clip now plays backwardslead.transpose(+5st).thin(25%)stop verse // every track in the scene stops togetherEach change builds on what the track is playing, in the order you made them, and the tracks panel shows the stack (▶ riff · reverse → thin(25%)):
bass.reversebass.thin(25%) // reversed, then thinnedbass.undo // takes off the last change you made (here, the thin)bass.clear // takes off all of them- One line is one change, so
lead.transpose(+5st).thin(10%)is undone in oneundo. A track carries at most 16. - Redefining the clip itself (
riff = …) keeps your changes and applies them to the new clip. - A
playline or launching a scene starts the track fresh, with no changes. thindrops the same notes for the same amount wherever it is written, so undoing something else doesn’t change which notes it drops.- Only a live session can do this: in a file, write the change into the play line.
Quantized changes
Section titled “Quantized changes”Code compiles immediately; changes land on a musical boundary. Quantum (most specific first): per evaluation (@ next 4 bars), per definition (with(quantize:)), per kind in config, global default.
config { quantize: { default: 1 bar play: cycle instr: 1 beat track: 1 bar ctl: now tempo: 1 bar }}
tempo 124bpm @ next bar over 2 barsBoundaries: now, beat, bar, N beats, N bars, cycle. One evaluation is one transaction. Last write wins for pending changes.
Live coding model
Section titled “Live coding model”- Evaluate block/line while performing; whole file when rendering.
- Failed compile changes nothing.
- Redefinition: new notes use new defs; sounding notes finish on old ones.
- Tracks and effects keep delay/filter state across edits.
External control
Section titled “External control”ctl — named values from code, MIDI, OSC, or modulators:
ctl filth = midi.cc(21)ctl volume = midi.cc(7).range(-60db..0db)ctl drive = 0.3
track bass { out = it.lpf(cutoff: filth.range(200hz..4khz)).drive(amount: filth) }Keyboards: midi.keys with note, velocity, pressure as signals.
Triggers: key("r"), MIDI notes, osc_in. Inputs: input(1) or input(1..2).
Modules
Section titled “Modules”A module is a file. use rig loads rig.nml (neighbor, project library, packages). Core library is always in scope. One config per project. Circular use is an error.
use riguse score/verseuse acme_verbs as av
out = sig.av::shimmer(size: 0.9)