Anatomy of a DSP — and your first one
A minimal generator DSP is three lines:
import("stdfaust.lib");
level = hslider("level", 0.3, 0, 1, 0.001);
process = os.osc(440) * level;
import("stdfaust.lib")mounts the standard library under its usual two-letter prefixes (os.oscillators,fi.filters,en.envelopes,no.noise,ba.basics,ma.math, …).- Every
hslider/nentry/button/checkboxbecomes a live knob in the module's UI panel and a param path the AI can read and write. processis the DSP's signal function. Generator shape means no audio inputs:process = <expression>;. Mono output is fine — split to stereo with<: _, _when you want both channels.
Two shapes the editor treats differently:
| Shape | Example | Where it runs |
|---|---|---|
| Generator | process = os.osc(f); | A .dsp module (this book) |
| FX | process = _ : fi.lowpass(1, fc); | Master-FX or track-FX slots — a standalone .dsp module has no input source, so Run refuses it with a friendly error. Validate FX sources with dsp.compile instead. |
Build one hands-free
actions:
- action_id: documents.add
input: { type: "faust-dsp", title: "Tutorial Tone" }
save_as: mod
label: "▶ 1. Create a .dsp module (file lands in assets/)"
- action_id: editor.source.set
input: { module_id: "{{mod.module_id}}", source: "import(\"stdfaust.lib\"); level = hslider(\"level\", 0.2, 0, 1, 0.001); process = os.osc(440) * level <: _, _;" }
label: "▶ 2. Write a sine-tone source into the buffer"
- action_id: dsp.run
input: { module_id: "{{mod.module_id}}" }
label: "▶ 3. Compile + start the worklet"
- action_id: mixer.tracks.input.set
input: { module_id: "{{mod.module_id}}", source_title: "Tutorial Tone" }
label: "▶ 4. Attach to a mixer track — now it is audible"
- action_id: dsp.stop
input: { module_id: "{{mod.module_id}}" }
label: "▶ 5. Stop the tone (strip + file survive)"