RayTone Documentation

01. Menu Panels

You can open the settings menu panel using the gear button in the top-right corner of the screen.

Volume: Global audio volume

BPM: Beats-per-minute (BPM) for sequencers

Resolution: Graphics resolution (low, mid, high, ultra)

Post Processing: Enable/disable post processing

Load: Load a project

Save: Save a project

Rescan: Rescan MIDI devices + ChucK source directory

Source Directory: Open the source directory in file browser. You can use this to locate template scripts for Voice unit and VFX unit.

Dual Display: Display a full-screen view of the canvas if there is a second monitor available.

02. Mouse + Shortcut Keys

Mouse Commands 🖱️

Left-click: Select and move a unit

Ctrl/Cmd/Shift + left-click: Select and move multiple units | Use selection box tool

Right-click + drag: Shift camera

Scroll wheel: Zoom in/out

General Shortcut Keys ⌨️

~: Open / close console

Space: Re-sync sequencer steps

Delete: Destroy selected units

Escape: Deselect selected units / Exit performance mode

N: Spawn a number box

E: Enter edit mode of selected unit (if applicable)

M: Open submenu of the unit in edit mode (if applicable)

Arrow keys: Shift camera

+/-: Zoom in/out

Menu Shortcut Keys ⌨️

C: Control Selection Panel

V: Voice Selection Panel

G: Graphics Selection Panel

Ctrl/Cmd Shortcut Keys ⌨️

Ctrl/Cmd + A: Select all units

Ctrl/Cmd + C: Copy selected units

Ctrl/Cmd + X: Cut selected units

Ctrl/Cmd + V: Paste copied units

Ctrl/Cmd + Z: Undo

Ctrl/Cmd + Y: Redo

Ctrl/Cmd + S: Save a project

Ctrl/Cmd + P: Load a project

Ctrl/Cmd + T: Toggle "performance" mode

Ctrl/Cmd + R: Randomize all steps in sequencer edit mode

03. Unit References

Below is a list of available units in RayTone by category. In this documentation, the following symbols are used to represent the unit socket types.

➡️: control-rate inlet

↩️: control-rate outlet

➡️🔊: audio-rate input

↩️🔊: audio-rate output

Additionally, the following symbol is used if a unit has a submenu panel for editing additional properties. You can either double click on the unit or click on the edit key on the right side of the screen to enter the edit mode.

🎚️: unit submenu panel

Control Units

GUI

Monitor

A GUI unit for monitoring a number every frame.

Number

A GUI unit for setting a constant number. Click on the box to edit the value. 

Sequencer

A circular step sequencer that outputs a value every step. Double click or click on the edit key on the right side of the screen to enter the edit mode. Use left and right arrow keys to select a step to edit. Use up and down arrow keys to edit the step value.

Ctrl/Cmd + up or down key to move all steps.

Shift + up or down key to move in increments of 10.

Ctrl/Cmd + R to randomize all steps within the range specified in submenu.

Slider

A GUI slider. 

Toggle

A GUI toggle button.

Trigger

A GUI button. Use this to manually send a trigger.

Math

Absolute

Add

Ceil

Clamp

Cos

Divide

Equal

Floor

Ftom

Greater

Lerp

Log

Max

Min

Mtof

Multiply

Pi

Power

Round

Sin

Sqrt

Subtract

Time

Average

Take the exponential moving average of the inlet value. Use this unit to smoothly interpolate between discrete values.

BPM

Set and get current global BPM. Use this unit in a project to explicitly set its BPM when loaded.

Day

Elapsed

Return the elapsed time in seconds since RayTone application started OR the last reset time. Use this unit to obtain a value that linearly increases over time.

Hour

Millisecond

Minute

Month

Second

Year

Utilities

KeyInput

Monitor a computer key press either continuously or as one-shot. This unit is useful for updating canvas parameters (Voice, VFX, etc.) in live performance and debugging settings. 

MIDI_CC_R

Receive MIDI CC value at specified channel and CC number. Use this unit to communicate with audio and graphics hardware.

MIDI_CC_S

Send MIDI CC value at specified channel and CC number. Use this unit to communicate with audio and graphics hardware.

OSC_R

Receive OSC floating point value at specified port and OSC address. Use this unit to communicate with other audio and graphics software.

OSC_S

Send OSC floating point value at specified IP address, port and OSC address. Use this unit to communicate with other audio and graphics software.

Rand

Select

A "switch" unit that returns the value at the specified "key" index (starting with 0). This unit is useful for creating scene states, such as which sequencer and texture are actively used. 

Tick

Volume

Set and get current global volume. Use this unit in a project to explicitly set its volume when loaded.

Voice Units

🎚️: every voice unit has a submenu panel

01.Sources

Bow

Bow_Q

Same as Bow, except that all inlets are read once a step. Use this version for accurate timing unbounded by frame-rate. 

FM

FM_Q

Noise

OSC

OSC_Q

Pulse

Pulse_Q

Sampler

Saw

Saw_Q

Square

Square_Q

Tri

Tri_Q

02.Effects

BPF

Chorus

Echo

HPF

LPF

Pitchshift

Reverb

03.Gain

Add4

Env

Gain

Multiply

05.Analyzers

Centroid

Use this unit to analyze the spectral centroid (center of mass of spectrum) of audio signals from another voice unit (or a chained series of voice units).

Pitch

Use this unit to estimate the fundamental frequency of audio signals from another voice unit (or a chained series of voice units). By combining with other voice units (oscillators), this can be used to resynthesize and harmonize with a sound file. 

RMS

Use this unit to analyze loudness of audio signals from another voice unit (or a chained series of voice units) and apply the result to control / graphics unit inlets, such as a VFX inlet.

STON

Signal to Number Converter. Use this unit to convert audio signals from another voice unit (or a chained series of voice units) to a floating point value and apply the result to control / graphics unit inlets, such as a VFX inlet.

Write your own voice units!

You can write your custom voice units using Chuck! Open the RayTone source directory from the settings panel (top right corner) and take a look at the template.ck file in ChucK/User folder to get started. New .ck files in this folder will appear as new voice units after clicking on Rescan button from the settings panel . Additionally, you can create new voice unit categories by adding folders parallel to this User folder. 


Use the following macros to define voice unit sockets:

RAYTONE_DEFINE_INPUTS("signal1", "signal2"); audio-rate input names with double quotation marks separated by commas. 

RAYTONE_DEFINE_INLETS("dry/wet 0-1", "Inlet2Name..."); control-rate inlet names with double quotation marks separated by commas. 

RAYTONE_DEFINE_OUTLET(true); set to true to add a control-rate outlet

RAYTONE_LOADFILE(false); set to true open a file browser to load a .wav file to this script. (For example, Sampler voice unit uses this feature.)


In order to send a signal to DAC and the output socket, you must add the following to your signal chain:

(Your Signal Chain) => RAYTONE_OUTPUT => dac;


Inside the ChucK script, you can read input and inlet values using the following macros:

RAYTONE_INPUT(0) Use an index starting at 0 inside the parentheses to access an input defined by RAYTONE_DEFINE_INPUTS(). 

RAYTONE_INLET(0) Use an index starting at 0 inside the parentheses to access an inlet defined by RAYTONE_DEFINE_INLETS(). 


You can send a float variable to the control-rate outlet using the following macro only if RAYTONE_DEFINE_OUTLET() is set to true:

RAYTONE_OUTLET


If RAYTONE_LOADFILE() is set to true, you can access the file path that is loaded to a voice unit using the following macro:

RAYTONE_FILEPATH 


The tick in RayTone is defined as a ChucK global event:

RAYTONE_TICK


Putting this all together... the following code is an example taken from the Sampler voice unit:

//-----------------------------------------------------------------------------

//Define RayTone inputs & inlets & file requirement

RAYTONE_DEFINE_INPUTS();

RAYTONE_DEFINE_INLETS("trigger", "rate");

RAYTONE_DEFINE_OUTLET(false);

RAYTONE_LOADFILE(true);

//-----------------------------------------------------------------------------


// DSP chain

SndBuf buf => RAYTONE_OUTPUT => dac;

RAYTONE_FILEPATH => buf.read;

0 => dac.gain;


// infinite loop

while (true)

{

    // Wait for tick

    RAYTONE_TICK => now;


// Check for trigger

if(RAYTONE_TRIG(0) == 1)

{

RAYTONE_LOCAL_GAIN => buf.gain;


// Read rate inlet; set to 1 if not connected

if (RAYTONE_INLET_STATUS(1) == 1)

{

RAYTONE_INLET(1) => buf.rate;

}

else

{

1 => buf.rate;

}


// Read playback position in ms

(RAYTONE_INLET(2) / (buf.length() / 1::ms) * buf.samples()) $ int => buf.pos;

}

}



Graphics Units

Image

Load a .png or .jpg image on canvas. The image can be passed as a texture to the VFX shader when it is connected to an inlet of Textures unit.

Text

Double click on the purple circle and use keyboard to edit text. Use this to write comments in your patch...

Textures

Load RayTone Graphics Assets (Image, Video, Webcam units) as textures to the GLSL fragment shader in the VFX unit. Use RAYTONE_TEXTURE(0-7) and RAYTONE_TEXTURE_RESOLUTION(0-7) (where the value in parentheses is the texture index starting at 0) in the fragment shader to read a texture and its resolution from RayTone.

*Only a single Textures Unit is allowed in a RayTone patch.

VFX

Load a GLSL fragment shader to display on canvas. Use RAYTONE_INLET(0-7) (where the value in parentheses is the inlet index starting at 0) in the fragment shader to read an inlet value from RayTone.

*Only a single VFX Unit is allowed in a RayTone patch.

Video

Load an .mp4 video on canvas. The video can be passed as a texture to the VFX shader when it is connected to an inlet of Textures unit.

Webcam

Capture the default webcam device on OS as a dynamic image on canvas. The webcam can be passed as a texture to the VFX shader when it is connected to an inlet of Textures unit.


The following is a template GLSL fragment shader code that you can use with the VFX unit.


#version 410


//-----------------------------------------------------------------------------

//RAYTONE HEADER

uniform vec3 iResolution;

uniform float iTime;

uniform float inlets[8];

uniform sampler2D textures[8];

uniform vec3 textureResolutions[8];


#define RAYTONE_RESOLUTION iResolution

#define RAYTONE_TIME iTime

#define RAYTONE_INLET(i) inlets[i]

#define RAYTONE_TEXTURE(i) textures[i]

#define RAYTONE_TEXTURE_RESOLUTION(i) textureResolutions[i]

//-----------------------------------------------------------------------------


out vec4 fragColor;

void main()

{

// Define UV coordinates based on canvas resolution

vec2 uv = gl_FragCoord.xy / RAYTONE_RESOLUTION.xy;


// Read inlet 0 to create yellow columns

float r = sin(uv.x * RAYTONE_INLET(0) * 100);

float g = sin(uv.x * RAYTONE_INLET(0) * 100);

float b = uv.y * (sin(RAYTONE_TIME) * 0.5 + 0.5);  // flashing blue


// Define texture coordinates based on its resolution

vec2 tex1_uv = gl_FragCoord.xy / RAYTONE_TEXTURE_RESOLUTION(0).xy;


// Sample texture

vec4 tex1 = texture(RAYTONE_TEXTURE(0), tex1_uv);


// Output is RGB + texture

fragColor = vec4(r, g, b, 1.0) + tex1;

}