Just the basics. Much more detail at rtcmix.org.

Note: function arguments in [ ] are optional.

## Minc Syntax

For more, consult the documentation for the Minc parser.

• loops

```for (init; test; increment) {
// block of statements
}```

e.g.,

```for (start = 0; start < total_duration; start = start + time_increment) {
// do something interesting
}```

or ...

```while (test) {
// block of statements
}```

e.g.,
```start = 0
while (start < total_duration) {
// do something interesting
start = start + time_increment)
}```

The for and while examples above are identical in effect. Use whichever makes the most sense to you. But if you use a while loop, remember to add the line that increments the variable you test on the while line, or else you’ll have an infinite loop!

• conditionals

```if (x > 0) {	// or <, >=, <=, ==, !=
// do something fun
}
else if {
// do something exciting
}
else {
// do something boring
}```

You don’t need the “else” statements, but if you have several of them, the last one must be an “else,” not an “else if.”

• lists

```mylist = { item0, item1, item2, ..., itemN-1 }
numitems = len(mylist)```

Items can be any combination of numbers, strings (in double quotes), other lists, or table references (like envelopes).

Write to a list element like this...

`mylist = 99.9`
Read a list element like this...
`myval = mylist`

Note that lists are zero-based — that is, the index of the first element is 0; the second, 1; the last, N-1, where N is the number of items in the list. If you try to read with an index >= N, Minc returns the last item of the list. If you try to write to an index >= N, Minc expands the size of the list to accommodate the new data.

• +=, -=, *=, /=

A common contraction...

`start += increment`
is the same as...
`start = start + increment`

Same for the -, *, and / operators. Be sure not to add any space between the + (or other operator) and the =.

• user functions

Define your own functions. You must put them above the place in the score where you use them.

Here is an example of defining a function and then using it.

```float play_triad(float start, float root)
{
pan = 0.5
WAVETABLE(start, dur, amp * env, root, pan)
WAVETABLE(start, dur, amp * env, root + 0.03, pan)
WAVETABLE(start, dur, amp * env, root + 0.07, pan)
return start + dur	// end time of chord
}

dur = 1
amp = 4000
env = maketable("line", 1000, 0,0, 1,1, 2,0)

Notice that pan is a local variable that exists only within the function. If you were to try using it outside of the function, you would probably get an error. To avoid confusion between global and local variables, you can use an underscore as the first character of all local variable names, e.g., _pan, or use a ‘g’ in front of all global variables, e.g., gDur. (This is purely for the reader’s benefit — it does not affect RTcmix behavior.)

Notice that we use the returned end time as the start time for the next chord, and that you can ignore the return value, as in the last chord.

Functions can have zero or more arguments. Data types include float, string, list, and handle (which is what a table is, for example). For more about user functions, search for “custom functions” on the Minc documentation page.

• include statements

You can include a score inside another one by using an include statement.

`include myfunctions.sco`

Then everything in the included file will be treated as if you had typed it into the main file. So if a global variable is declared in the included file, it will be global inside the main file as well.

Include files are especially handy for building a library of functions that you use in many scores. When doing this, it makes sense to use underscores as the first character of global variables within the library, so that you’ll be less likely to access them unintentionally in the file that uses the library.

## Utility Functions

• setup

NOTE: These four are for use only in cmd-line RTcmix, not in any RTcmix apps, such as RTcmixShell.

```rtsetparams(sample_rate, num_channels)

set_option("play = off")     // don't play while I'm writing a sound file

set_option("clobber = on")   // overwrite existing output file

• sound files

```rtinput("soundfile_name")  // must include extension, e.g., ".wav", ".aiff"

duration = DUR()    // of most recently opened input file

rtoutput("soundfile_name.wav")   // or ".aiff"```

NOTE: rtoutput works only in cmd-line RTcmix.

• randomization

```val = irand(min, max)   // returns floating-point value

val = trand(min, max)   // val is truncated (i.e., integer)

val = random()          // val is between 0 and 1

val = rand()            // val is between -1 and 1

srand(seed)             // seed is any integer```

• pitch conversion

```freq_in_Hz = cpspch(pitch_in_octave_point_pc)

pitch_in_octave_point_pc = pchcps(freq_in_Hz)

freq_in_Hz = cpsmidi(midi_notenum)

pitch_in_octave_point_pc = pchmidi(midi_notenum)

pitch = pchadd(pitch1, pitch2)      // all in oct.pc```

pchadd prevents you from getting an inappropriate result when computing pitches using oct.pc. For example, if you were to subtract one semitone (0.01) from middle C (8.00), you would get 7.99, which is about 8 octaves higher than what you intended. No other pitch representations have this problems, so you can use arithmetic operators freely with them.

• amplitude conversion

```linear_amp = ampdb(dB)

dB = dbamp(linear_amp)```

• tables

`table = maketable(type, [norm,] size, description)`

where type can be: "line", "curve", "wave", "random", "literal", "textfile", etc. (complete list here). The type must be in double quotes.

norm is either "norm" (the default) or "nonorm". This is optional. "nonorm" prevents the table from being scaled to the 0-1 range (or -1 to 1, if it contains any negative numbers). These tags must be in double quotes.

size is number of elements in table

remaining arguments depend on type:

• for line:   time0,val0, time1,val1, ..., timeN,valN
• for curve:   time0,val0,curve0, time1,val1,curve1, ..., timeN,valN
where curve=0 is linear, curve<0 is exponential, and curve>0 is logarithmic
• for wave:   either a double-quoted name like "saw", "tri", "square", "buzz", or
relative partial amplitudes: p1, p2, ..., pN
• for random:   type, min, max[, seed]
where type is "linear", "low", "high", "triangle", "gaussian", or "cauchy"
• for textfile:   "filename"
• data streams

`stream = makeLFO(wavetable, frequency, amp)`

where wavetable can be a previously defined table or a double-quoted name such as you would pass to maketable("wave"...), frequency is LFO rate in Hz, and amp is the peak deviation. (For example, if amp is 2, the waveform will oscillate between -2 and 2.) Instead of amp, you can give min and max arguments defining the amplitude extremes of the wave. All parameters except for wavetable can be constants or references to tables or other streams.

`stream = makerandom(type, frequency, min, max[, seed])`

where type is one of the random distributions listed for maketable("random"...) above, frequency is how fast the random value changes, min and max define the range of values, and seed is an optional integer seed. The frequency, min, and max parameters can be constants or references to tables or streams.

NOTE: A stream should not be used in multiple instruments that play simultaneously, or else the streams will run at a frequency different from the one you requested. This applies also to streams processed by makefilter and/or makeconverter (see below).

• table and stream format conversion

Values entering an instrument from a table or stream cannot be converted by the pitch and amplitude conversion functions listed earlier. These functions are designed to convert a single value, not a sequence of values read at the control rate. Instead, use makeconverter.

```// gliss down a perfect 5th from middle C, using MIDI note numbers
mpitch = maketable("line", "nonorm", 1000, 0,60, 1,53)
freq = makeconverter(mpitch, "cpsmidi")```

Think of makeconverter as processing the data stream stored in the mpitch variable.

All the conversion function names listed earlier can be used with makeconverter.

• table and stream processing

Sometimes values from a table or stream change too abruptly (e.g., when using "square" as an LFO waveform). Smooth these changes with a data filter.

```freq = makerandom("even", rfreq=6, min=200, max=800)
freq = makefilter(freq, "smooth", lag=50, initval=500)```

Notice that it’s okay to use the same variable name (freq in this case) for the input and output of makefilter (or of makeconverter).

There are other data filter types: clip, constrain, delay, fitrange, invert, map, and quantize. See the online documentation for details.

• audio buses

`bus_config("INSTRUMENT_NAME", [input_bus,] output_bus)`

where input_bus can be "in 0-1", "aux 0  in", or "aux 0-1 in", and output_bus can be "out 0", "out 0-1", "aux 0 out", or "aux 0-1 out". There are 64 internal (aux) buses. The number of input and output buses depends on your audio hardware. For file input, the "in 0-1" tag does not let you select input channels. Instead, most processing instruments have an inchan argument that lets you do that. Obviously, only instruments that process audio can have an input bus.

Instruments reading from an aux bus must have an inskip of zero. Certain instruments, like TRANS or REVMIX, cannot consume real-time input, because they might need to use audio that hasn't happened yet.

• miscellaneous

`control_rate(rate_in_Hz)`

## Instruments

This is just a selection of instruments. For more, go here.

Note: pan always works like this: hard left = 1, center = 0.5, hard right = 0. (Yes, this looks backwards.)

• synthetic
```// chaotic noise generator
CRACKLE(start, duration, peak_amp[, chaos_param, pan])
// chaos_param is 0-1, default=1

// simple 2-operator Chowning FM
FMINST(start, duration, peak_amp, carrier_freq, modulator_freq,
min_modindex, max_modindex, pan, wavetable, index_guide_table)

// physical model of metallophones
MBANDEDWG(start, duration, peak_amp, freq, strike_position, pluck_flag,
max_velocity, preset, bow_pressure, mode_resonance,
integration_constant, pan)
// strike_position [0-1]
// pluck_flag [0: no pluck, 1: pluck]
// max_velocity [0-1]
// preset [0: uniform bar, 1: tuned bar, 2: glass harmonica,
3: Tibetan bowl]
// bow_pressure [0-1, 0 mean strike only]
// mode_resonance [0-1, 0.99 for normal strike]
// integration_constant [0-1, try 0]

// white noise
NOISE(start, duration, peak_amp, pan)	// affected by srand()

// Karplus-Strong plucked string model
STRUM2(start, duration, peak_amp, freq, squish, decay_time, pan)

// vector synthesis using any number of wavetables
VWAVE(start, duration, freq, peak_amp, pan, vector_guide,
wavetab1, wavetab2, ..., wavetabN)
// vector_guide is 0-1, controlling wavetable selection

// simple wavetable synthesis
WAVETABLE(start, duration, peak_amp, freq, pan[, wavetable])

// combine two wavetable oscillators algebraically
WAVY(start, duration, peak_amp, oscilA_freq, oscilB_freq,
oscilB_phase_offset, oscilA_wavetable, oscilB_wavetable,
expression, pan)
// expression can be "a + b", "a - b", "a * b", etc.```
• processing
```// recursive comb filter
COMBIT(start, inskip, duration, amp_multiplier, freq, reverb_time,
inchan, pan, ringdown_duration)

// delay line with feedback
DELAY(start, inskip, duration, amp_multiplier, delay_time, feedback,
ringdown_duration, inchan, pan)

// distortion
DISTORT(start, inskip, duration, amp_multiplier, type=1, pre_gain,
lowpass_cf, inchan, pan, bypass)

// any number of band-pass filters, fed in parallel
FILTERBANK(start, inskip, duration, amp_multiplier, ringdown_duration,
inchan, pan, cf1, bw1, gain1, cf2, bw2, gain2, ..., cfN, bwN, gainN)
// bw is bandwidth as percent of cf, from 0 to 1

// reverberation
FREEVERB(start, inskip, input_duration, amp_multiplier, room_size,
pre_delay_time, ringdown_duration, damp, dry_level, wet_level,
stereo_width)
// last 4 args are 0-100, room_size is 0-1.07143 (don't ask)

// any number of EQ filters, fed in series
MULTEQ(start, inskip, duration, amp_multiplier, master_bypass,
type1, freq1, q1, gain1, bypass1, ...,
type2, freq2, q2, gain2, bypass2, ...,
typeN, freqN, qN, gainN, bypassN)
// type is "lowpass", "highpass", "lowshelf", "highshelf",
// "peaknotch", "bandpass"

// play a sound file backwards from the inskip
REVMIX(start, inskip, duration, amp_multiplier, inchan, pan)

// waveshaping
SHAPE(start, inskip, duration, amp_multiplier, min_distort_index,
max_distort_index, amp_norm_table, inchan, pan,
transfer_function_table, index_guide_table)

// play a sound file forwards
STEREO(start, inskip, duration, amp_multiplier, pan)

// play a sound file forwards, with varispeed transposition
// (i.e., transposition affects duration)
TRANS(start, inskip, duration, amp_multiplier,
transp_in_octave_point_pc, inchan, pan)```