mirror of
https://github.com/eliasstepanik/strudel.git
synced 2026-01-10 05:08:33 +00:00
* 0.5 default cps * 1 -> 0.5 cps defaults * start moving examples to 2Hz * more 2Hz doc edits * small tweaks * format * adapt cycles page * adapt pitch page * tonal page * accumulation * synth page * adapt conditional-modifiers * audio effects page * adapt signals doc * fix: errors for signals * adapt signals page * start time modifiers * adapt time modifiers * adapt factories * hydra + pattern intro * adapt mini notation page * start recipes * adapt recipes page * use code_v1 table * delete old dbdump + add new csv based tool * fix: tests * fix: cpm * shuffle featured patterns * fix: snapshot --------- Co-authored-by: Felix Roos <flix91@gmail.com>
169 lines
5.1 KiB
Plaintext
169 lines
5.1 KiB
Plaintext
---
|
||
title: Synths
|
||
layout: ../../layouts/MainLayout.astro
|
||
---
|
||
|
||
import { MiniRepl } from '../../docs/MiniRepl';
|
||
import { JsDoc } from '../../docs/JsDoc';
|
||
|
||
# Synths
|
||
|
||
In addition to the sampling engine, strudel comes with a synthesizer to create sounds on the fly.
|
||
|
||
## Basic Waveforms
|
||
|
||
The basic waveforms are `sine`, `sawtooth`, `square` and `triangle`, which can be selected via `sound` (or `s`):
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`note("c2 <eb2 <g2 g1>>".fast(2))
|
||
.sound("<sawtooth square triangle sine>")
|
||
.scope()`}
|
||
/>
|
||
|
||
If you don't set a `sound` but a `note` the default value for `sound` is `triangle`!
|
||
|
||
## Noise
|
||
|
||
You can also use noise as a source by setting the waveform to: `white`, `pink` or `brown`. These are different
|
||
flavours of noise, here written from hard to soft.
|
||
|
||
<MiniRepl client:idle tune={`sound("<white pink brown>").scope()`} />
|
||
|
||
Here's a more musical example of how to use noise for hihats:
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`sound("bd*2,<white pink brown>*8")
|
||
.decay(.04).sustain(0).scope()`}
|
||
/>
|
||
|
||
Some amount of pink noise can also be added to any oscillator by using the `noise` paremeter:
|
||
|
||
<MiniRepl client:idle tune={`note("c3").noise("<0.1 0.25 0.5>").scope()`} />
|
||
|
||
You can also use the `crackle` type to play some subtle noise crackles. You can control noise amount by using the `density` parameter:
|
||
|
||
<MiniRepl client:idle tune={`s("crackle*4").density("<0.01 0.04 0.2 0.5>".slow(2)).scope()`} />
|
||
|
||
### Additive Synthesis
|
||
|
||
To tame the harsh sound of the basic waveforms, we can set the `n` control to limit the overtones of the waveform:
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`note("c2 <eb2 <g2 g1>>".fast(2))
|
||
.sound("sawtooth")
|
||
.n("<32 16 8 4>")
|
||
.scope()`}
|
||
/>
|
||
|
||
When the `n` control is used on a basic waveform, it defines the number of harmonic partials the sound is getting.
|
||
You can also set `n` directly in mini notation with `sound`:
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`note("c2 <eb2 <g2 g1>>".fast(2))
|
||
.sound("sawtooth:<32 16 8 4>")
|
||
.scope()`}
|
||
/>
|
||
|
||
Note for tidal users: `n` in tidal is synonymous to `note` for synths only.
|
||
In strudel, this is not the case, where `n` will always change timbre, be it though different samples or different waveforms.
|
||
|
||
## Vibrato
|
||
|
||
### vib
|
||
|
||
<JsDoc client:idle name="vib" h={0} />
|
||
|
||
### vibmod
|
||
|
||
<JsDoc client:idle name="vibmod" h={0} />
|
||
|
||
## FM Synthesis
|
||
|
||
FM Synthesis is a technique that changes the frequency of a basic waveform rapidly to alter the timbre.
|
||
|
||
You can use fm with any of the above waveforms, although the below examples all use the default triangle wave.
|
||
|
||
### fm
|
||
|
||
<JsDoc client:idle name="fm" h={0} />
|
||
|
||
### fmh
|
||
|
||
<JsDoc client:idle name="fmh" h={0} />
|
||
|
||
### fmattack
|
||
|
||
<JsDoc client:idle name="fmattack" h={0} />
|
||
|
||
### fmdecay
|
||
|
||
<JsDoc client:idle name="fmdecay" h={0} />
|
||
|
||
### fmsustain
|
||
|
||
<JsDoc client:idle name="fmsustain" h={0} />
|
||
|
||
### fmenv
|
||
|
||
<JsDoc client:idle name="fmenv" h={0} />
|
||
|
||
## Wavetable Synthesis
|
||
|
||
Strudel can also use the sampler to load custom waveforms as a replacement of the default waveforms used by WebAudio for the base synth. A default set of more than 1000 wavetables is accessible by default (coming from the [AKWF](https://www.adventurekid.se/akrt/waveforms/adventure-kid-waveforms/) set). You can also import/use your own. A wavetable is a one-cycle waveform, which is then repeated to create a sound at the desired frequency. It is a classic but very effective synthesis technique.
|
||
|
||
Any sample preceded by the `wt_` prefix will be loaded as a wavetable. This means that the `loop` argument will be set to `1` by defalt. You can scan over the wavetable by using `loopBegin` and `loopEnd` as well.
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`samples('github:Bubobubobubobubo/Dough-Waveforms/main/');
|
||
|
||
note("<[g3,b3,e4]!2 [a3,c3,e4] [b3,d3,f#4]>")
|
||
.n("<1 2 3 4 5 6 7 8 9 10>/2").room(0.5).size(0.9)
|
||
.s('wt_flute').velocity(0.25).often(n => n.ply(2))
|
||
.release(0.125).decay("<0.1 0.25 0.3 0.4>").sustain(0)
|
||
.cutoff(2000).scope({}).cutoff("<1000 2000 4000>").fast(4)`}
|
||
/>
|
||
|
||
## ZZFX
|
||
|
||
The "Zuper Zmall Zound Zynth" [ZZFX](https://github.com/KilledByAPixel/ZzFX) is also integrated in strudel.
|
||
Developed by [Frank Force](https://frankforce.com/), it is a synth and FX engine originally intended to be used for size coding games.
|
||
|
||
It has 20 parameters in total, here is a snippet that uses all:
|
||
|
||
<MiniRepl
|
||
client:idle
|
||
tune={`note("c2 eb2 f2 g2") // also supports freq
|
||
.s("{z_sawtooth z_tan z_noise z_sine z_square}%4")
|
||
.zrand(0) // randomization
|
||
// zzfx envelope
|
||
.attack(0.001)
|
||
.decay(0.1)
|
||
.sustain(.8)
|
||
.release(.1)
|
||
// special zzfx params
|
||
.curve(1) // waveshape 1-3
|
||
.slide(0) // +/- pitch slide
|
||
.deltaSlide(0) // +/- pitch slide (?)
|
||
.noise(0) // make it dirty
|
||
.zmod(0) // fm speed
|
||
.zcrush(0) // bit crush 0 - 1
|
||
.zdelay(0) // simple delay
|
||
.pitchJump(0) // +/- pitch change after pitchJumpTime
|
||
.pitchJumpTime(0) // >0 time after pitchJump is applied
|
||
.lfo(0) // >0 resets slide + pitchJump + sets tremolo speed
|
||
.tremolo(0) // 0-1 lfo volume modulation amount
|
||
//.duration(.2) // overwrite strudel event duration
|
||
//.gain(1) // change volume
|
||
.scope() // vizualise waveform (not zzfx related)
|
||
`}
|
||
/>
|
||
|
||
Note that you can also combine zzfx with all the other audio fx (next chapter).
|
||
|
||
Next up: [Audio Effects](/learn/effects)...
|