abc2midi guide ..
abc cheatsheet
Fiddle Runtime ..
Fiddle Resources
Extending Fiddle ..
Installing Fiddle
General MIDI ..
MIDI CC ..
MIDI notes
Box2D API ..
Tidal Cheatsheet
Banklist File .. Sample TOC File
Audio Troubleshooting
Fiddle Runtime is the collection of
.ck
and.yaml
files that come with the Fiddle distribution and that underpin the ChucK Live feature set.If you are interested in extending the Fiddle Runtime, this information is for you. Otherwise, perhaps not.
Fiddle Runtime source is found at (fiddle install)/resources/Fiddle/chuckruntime.
Right-click to navigate to a place in this doc.
Fiddle App is the running instance of Fiddle GUI application.
Fiddle Runtime is the collection of over 100 .ck
files that, when loaded
into a ChucK session, allow for control and monitoring of ChucK by Fiddle App.
Fiddle Node is both the graphical representation in Fiddle App and the concrete instance of a Fiddle Runtime class running in a ChucK session.
ChucK Session is an instance of ChucK running over the course of your performance. Usually you only need a single ChucK session active but you can have multiple sessions running simultaneously.
ChucK Shred is ChucK's version of a programatic thread of execution. In a typical performance, tens of shreds are active and operating simultaneously.
_bootstrap.ck
is used to bootstrap the entire Fiddle runtime.
Only after the successful loading of this program does Fiddle App
correctly interoperate with a running ChucK session.
A single instance of the Fiddle class acts as the liaison between the
Fiddle App and running instances of chuck
. Fiddle
extends the
OscListener
class and this means that we employ OSC
for our intercommunication layer. It is over this channel that parameter
updates from Fiddle App to the ChucK session occur. The same mechanism is
used to deliver ChucK updates for Fiddle App that provide feedback and
plotter data.
IController is the base class for all subclasses that require a separate
ChucK shred
for independent operation. The key function of a Controller
is to "drive" Controllables. To do this, we require
Fiddle to spork our subclass' Play method. IController is the base class
for eg Player, TimeKeeper, ccSampler, ccGenerator, etc.
Players control instruments by delivering note events to instruments with the correct timing. When a note is sustained, a player's shred is effectively idling for a note's duration. Embedded control-changes like pitch-bend are also delivered to an instrument by its player. When Player is connected to multiple instruments it manages polyphony (even MPE) by routing note and control-change events to the appropriate instrument.
Timekeeping is an opt-in feature. Classes that keep track of TimeKeeper state are said to be in sync. When you play notes on your MIDI device you can try to be in sync or not, there is no enforcement there. The same can be said of procedural nodes that disregard TimeKeeper. Player opts-in to TimeKeeper by
public class TimeKeeper
{
// beats per measure, beat-type (ie: 4/4 or 3/4 or 3/8)
int Signature[2];
float bpm;
// durations (changed when bpm changes)
dur Measure, Beat;
dur HalfNote, QuarterNote, EighthNote, SixteenthNote;
TimeLocation CurrentTime; // composition time coordinatates
}
public class TimeLocation
{
0=>int Measure; // indexed from 0
0=>float Beat;
0=>float TotalBeats;
t_zero => time Time;
... methods...
}
Like Players, CCControllers
, control other node behaviors by running
in a separate shred
and delivering control change (CC) messages
to the downstream controllable nodes.
Unlike Players, CCControllers
have no knowledge or support for
NoteStreams. You can think of the CCController as
a generalization of the LFO.
CCControllers typically deliver updates to one or more named
control channel at a rate of your choice. Control Change signals can be
delivered to any number of downstream controllables.
At right you can see a CCController subclass, CCGenerator, sending BPM
updates to both the TimeKeeper (to produce tempo changes) as well as
the CCPlot node.
Other CCControllers of note:
You can implement your own controller by extending the base class and overriding:
fun float ComputeControl(int iter, int clientId); // override
It's likely that your custom controller will require synchronization with other aspects of your composition. The TimeKeeper and TimeLocation classes expose the current global time in a number of representations. ChucK has a cross-shred notification feature, called Events. A system of custom extensions could exploit this capability in interesting and powerful ways.
Controllable is an interface for delivering Control Change
messages to a receiver. Most classes directly or indirectly extend
this class. A few need to apply a bit of trickiness to become controllable.
This is due to the fact that ChucK doesn't currently support
multiple inheritance. To get around this, we employ pretty simple trick.
The idea is to create a lightweight Controllable subclass that knows how
to delegate messages to its target.
The Fiddle Runtime comprises a large number of Instruments. That said, custom instruments are always desireable and if you find yourself extending Fiddle, it's likely you'll be developing an instrument. Keep in mind that you can accomplish this task without any programming via the ADSR or Envelope nodes. But if you want something more exotic or procedural, you've come to the right place.
Most instruments are monophonic and inherit from the Instrument base class. They can easily be placed anywhere in a stereo soundfield via downstream Channel or Effects nodes. In contrast, some instruments want to conflate stereo position with control events and thus opt to inherit from the Instrument2 base class. GrainBuf is one such example.
Instruments minimally override these methods. Other methods are available for override but we'll refer you to the source for more details.
fun float Freq(float f) ;
fun void NoteOn(float velocity);
fun void NoteOff(float velocity);
fun void ControlChange(string name, float value);
Most of ChucK's built-in instruments have been wrapped in Instrument subclasses to deliver the benefits of ChucK Live.
Like Instrument, NoteStream is another excellent opportunity for customization. A NoteStream represents a canned or procedural sequence of notes active over a time range.
Here are some NoteStream subclasses that ship with Fiddle organized by category:
These tree broad categories and their constituents provide a solid foundation for composition, but clearly there's no end to the variety of notestreams that can be conceived.
Here's all you need to implement your own NoteStream subclass:
public class MyNoteStream extends NoteStream
{
fun Note NextNote(TimeLocation loc)
{
// your code here..
}
}
The Note
class is central to this interface. It embodies the information
needed to allow the downstream Player to perform its duties.
Notes
come in two flavors: live (aka untimed) and timed either of
which can be requested through the Note interface:
public class Note
{
fun void Reset(); // to a 1-beat rest
// pitch is in midi scale, -1 means rest
fun int Init(float pitch, float nbeats, float v);
fun void LiveNoteOn(float pitch, float v);
fun void LiveNoteOff(float pitch, float v);
ControlChange @cc; // can piggy-back with notes
}
Using LiveNotes in your NoteStream incurs the responsibility that the note event be delivered at the right time. This implies that your node will idle, either in another blocking method (like waiting for a MIDI or OSC event) or by chucking to now yourself. It also requires that you deliver the associated LiveNoteOff. Failing to do so may result in "stuck notes", depending on the downstream instrument.
Notes can be decorated with modifiers by assigning a ControlChange instance to the note's cc parameter. If you have no decorations to apply you should do this
null => Note.cc;
Here's the ControlChange class in its entirety:
public class ControlChange
{
string name;
int id;
float value;
int midinote; // for polyphonic aftertouch (not MPE)
}
The Channel base class is the primary means to control a chain
of audio processing stages. It comes equipped with dry
and wet
ports and a Mix
parameter. It automatically routes the input signal
to the output through the dry port. The wet port depends on a per-subclass
signal flow.
Subclasses should do this:
this.inlet => myeffect => this.wet;
It should be noted that to support Effects Chains, Fiddle's code generator automatically generates Channel subclasses.
From the outside world the inlet and outlet keywords are Pan2 nodes which support gain and pan parameters.
Channels can be arranged "hierarchically" and at least one instance should be be routed to the dac, either manually or via the ToDAC param/method. In this way, a graph can include a master signal control as well as any number of Channels (groups and/or channels).
We currently don't anticipate the need to extend this class manually but, who knows? If there is a will, there is a way.
The FX
base class accepts one or more Signals
as input and combines them
into a single outlet
. To subclass FX you simply need to assign and
object reference to this.fx
:
/* controllable Gain node */
public class GainFX extends FX
{
Gain gain @=> this.fx;
}
The Filter
base class accepts a single signal as input and
produces a filtered output signal. Standard parameters
for Quality
, Cutoff
and Gain
are supported.
public class HighPass extends Filter
{
HPF hpf @=> this.filt;
}
The Workspace
class is responsible for resolving resource references
according to your current workspace settings. It is a static, singlton
class. There may not be value in subclassing it, but if your .ck
code
needs to resolve an asset file reference, here's how:
SndBuf b => dac;
Workspace.ResolvePath("mySound.wav") => string fullpath;
fullpath => b.read;