Skip to content

Instantly share code, notes, and snippets.

@NoRaincheck
Last active December 8, 2025 05:10
Show Gist options
  • Select an option

  • Save NoRaincheck/4c3943c9cf8adedcedeaa9d0783a9be1 to your computer and use it in GitHub Desktop.

Select an option

Save NoRaincheck/4c3943c9cf8adedcedeaa9d0783a9be1 to your computer and use it in GitHub Desktop.
strudel.cc music
/*
@title Strudeldudel
@by Lennard Voogdt
@license CC BY-NC-SA
*/
// let cpm = 77
setcps(78/60)
register('withAsdr', x => x.attack(saw.range(0, 0.05).fast(6)).decay(rand.range(0.1, 0.3)).sustain(0))
register('withLpfVib', (a, b, x) => x.lpf(saw.range(a, b).slow(16)).lpq(0).vib(1).vibmod(.1))
register('mainTempo', x => x.cpm(cpm))
let synth = (noteIndices, { scale = scales.synth, sound = "sawtooth", release = 3 } = {}) =>
n(noteIndices)
// .mainTempo()
.scale(scale).sound(sound).release(release)
let bassSynth = (noteIndices, options = {}) =>
synth(noteIndices, options)
.attack(0)
.decay("<0.2>")
.sustain(0)
// .lpf(200)
.withLpfVib(options.lpfA ?? "100", options.lpfB ?? "300")
.room(0.1)
let chordSynth = (noteIndices, options = {}) =>
synth(noteIndices, options)
.withLpfVib(options.lpfA ?? "500", options.lpfB ?? "800")
.withAsdr()
let melody = (notesIndices) => notesIndices.n()
.sound("gm_electric_guitar_muted, gm_synth_strings_2, gm_overdriven_guitar")
.withLpfVib("500", "8000")
.pan(rand)
.room(1).rsize(15)
.attack(0).decay(0.2).sustain(0).release(0)
let scales = {
melody: "<F3:major> | <F4:major>",
bass: "F2:major",
altMelody: "F5:major",
synth: "F3:major:pentatonic",
}
let intro = stack(
sound("brown").gain(0.4),
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: saw.range(0, 4).slow(16)})
.pan("0.1 0.5 0.9").gain(0.8).color('yellow')
// .speed(1)
.lpf(saw.range(0, 500).slow(16))
// ._scope({ width: 1800, height: 100})
)
let part1 = ({ withBass = true}) => stack(
sound("brown*2").gain(0.4),
chordSynth( "<{0 3 5 2} {0 1 3 5 2 1} {0 1 <3!3 5b> 2} {0 1 3 1 2}>").pan(0).gain(0.3).color('red'),
chordSynth( "<{0 3 5 2} {0 1 3 5 2 1} {0 1 <3!3 5b> 2} {0 1 3 1 2}>", {release: 3}).pan(1).gain(0.3).color('red'),
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: "<0.5 0.7 1.0 0.8>"}).pan("0.1 0.5 0.9").gain(0.8).color('yellow'),
withBass ? bassSynth("<-7(4,8)>", {scale: scales.bass, sound: "gm_synth_bass_2", release: 0.1}).gain(2).color('cyan')
._punchcard({ width: 1800, height: 100})
: [],
)
let part2 = ({ withBass = true}) => stack(
sound("brown*2"),
chordSynth( "<{0 3 5 2} {0 1 3 5 2 1} {0 1 <3!3 5b> 2} {0 1 3 1 2}>", {lpfA: "4000", lpfB: "500"}).pan(0).gain(0.3).color('yellow')
._punchcard({ width: 1800, height: 30})
,
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: 1, lpfA: "500", lpfB: "4000"}).pan(1).gain(0.3).color('yellow')
._punchcard({ width: 1800, height: 30})
,
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: "<0.5 0.7 1.0 0.8>", lpfA: "500", lpfB: "3000"}).pan("0.1 0.5 0.9").gain(0.8).color('yellow')
._punchcard({ width: 1800, height: 30})
,
withBass ? bassSynth("<-6(4,8)!3 ~ -4(4,8)!3 ~ -7(4,8)!3 ~ -3(4,8)!4>", {scale: scales.bass, sound: "gm_synth_bass_2", release: 0, lpfA: "500", lpfB: "3000"}).gain(2).color('cyan') : [],
withBass ? sound("[<bd bd>]*2").bank("KorgDDM110").dist("2:0.5").color('white') : [],
withBass ? sound("<~ ~ ~ sd>").bank("KorgDDM110").speed("0.8").lpf(2300).dist("2:0.5").color('white').room(0.1).gain(0.3)
// ._scope({ width: 1800, height: 100})
: [],
sound("<hh>*4").bank("AkaiXR10").gain(".2!2 1 .2!2 1 .2 1").lpf(4500).velocity(".6 .2").gain(0.3).color('white'),
melody(`<~!3 <[0 6 7 4] [6 7 8 9] [7 6 4 3] [7 4 2 1]> ~!2 [~!3 <3 1 2 1>] <[~!2 <2 0> ~][~ <2 4> <-3 ~> 0]>>`).scale(scales.melody).gain(0.7).color('magenta')
// ._punchcard({ width: 1800, height: 100})
,
n("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>").scale(scales.synth).sound("piano").release(5).rev().gain(0.4)
)
let prechorus = stack(
bassSynth("-3", {scale: scales.bass, sound: "gm_synth_bass_2", release: 1, lpfA: "500", lpfB: "3000"}).gain(0.8).sustain(1).color('cyan'),
n("0 1,5b 2 3 0 1 5b 2 3").scale(scales.synth).sound("piano").distort(0).release(5).gain(0.5).withLpfVib("50", "10000")
// ._punchcard({ width: 1800, height: 100})
)
let chorus = ({bigger = false}) => stack(
sound("<brown>"),
chordSynth( "<{0 3 5 2} {0 1 3 5 2 1} {0 1 <3!3 5b> 2} {0 1 3 1 2}>", {lpfA: "10000", lpfB: "2000"}).pan(0).gain(0.3).color('yellow')
// ._punchcard({ width: 1800, height: 30})
,
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: 1, lpfA: "10000", lpfB: "2000"}).pan(1).gain(0.3).color('yellow')
// ._punchcard({ width: 1800, height: 30})
,
chordSynth("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>", {release: "<0.5 0.7 1.0 0.8>", lpfA: "4000", lpfB: "10000"}).pan("0.1 0.5 0.9").gain(0.8).color('yellow')
// ._punchcard({ width: 1800, height: 30})
,
bassSynth("<-6(4,8)!3 ~ -4(4,8)!3 ~ -7(4,8)!3 ~ -3(4,8)!4>", {scale: scales.bass, sound: "gm_synth_bass_2", release: 0.1, lpfA: "1000", lpfB: "3000"}).gain(2).color('cyan'),
bigger ? sound("[<bd bd>]*2").bank("KorgDDM110").dist("2:0.5").color('white') : [],
(bigger ? sound("<<[bd sd]!3 [bd sd sd bd]> <[bd sd]!3 [bd sd sd bd]>>") : sound("<<<bd [bd bd]> [~ bd] [<~!4 sd ~ ~> bd?]>*2 <sd!7 [~ sd ~ [sd sd]]>>") ).bank("KorgDDM110").room(0.2).lpf(2300).dist("2:0.5").color('white')
// ._punchcard({ width: 1800, height: 30})
,
sound("[<~!12 sd ~!3>]*4").bank("KorgDDM110").speed("0.3").color('white').room(1).hpf(6000),
sound("<hh>*4").bank("AkaiXR10").gain(".2!2 1 .2!2 1 .2 1").lpf(4500).velocity(".6 .2").gain(0.4).color('white').when(bigger, x => x.jux(rev)),
melody(`<~!3 <[0 6 7 4] [6 7 8 9] [7 6 4 3] [7 4 2 1]> ~!2 [~!3 <3 1 2 1>] <[~!2 <2 0> ~][~ <2 4> <-3 ~> 0]>>`).scale(scales.melody).gain(bigger ? 1 : 0.7).color('magenta')
._punchcard({ width: 1800, height: 30})
,
n("<{0 3 5 2} {0 1 3 5} {0 1 <3!3 5b> 2} {0 1 3 2}>").scale(scales.synth).sound("piano").release(5).rev().gain(0.4).when(bigger, x => x.jux(rev)),
// bigger ? n("<~ <[~ 0] [0] [0 0] [4 2]> <[-3 ~] ~> [0 ~] <[-1 ~][-4 ~][-1 ~][2 ~]> <[~ 0] [~ 3] [~ 0] [~ 1]> ~ <0 2 -1 0 >>*2").pan("0.2 0.5 0.8").scale(scales.altMelody).sound("gm_celesta").clip(1).room(0.8).gain(0.2) : []
)
let inbetween = stack(chordSynth("<{0 3 5 2 1} {0 1 3 5 2 1}>", {release: saw.range(0, 4).slow(16)}).pan("0.1 0.5 0.9").gain(0.8).color('yellow'))
let outro = stack(
chordSynth("<{0 3 5 2 1} {0 1 3 5 2 1} {0 1 3 5 2 1 0}>", {release: saw.range(0, 3).slow(22)}).pan("0.1 0.5 0.9").gain(0.8).color('yellow').lpf(saw.range(3500, 0).slow(23).room("0.8 ... 0.1"))
// ._scope({ width: 1800, height: 100})
// melody(`<0>`).scale(scales.melody).gain(0.7).color('magenta'),
// melody(`<~!3 <[0 6 7 4] [6 7 8 9] [7 6 4 3] [7 4 2 1]> ~!2 [~!3 <3 1 2 1>] <[~!2 <2 0> ~][~ <2 4> <-3 ~> 0]>>`).scale(scales.melody).gain(0.7).color('magenta'),
)
let colors = true;
arrange(
[16, intro.when(colors, x => x.theme("strudelTheme"))],
[16, part1({ withBass: true }).when(colors, x => x.theme("githubDark"))],
[14, part2({ withBass: true }).when(colors, x => x.theme("githubDark materialDark"))],
[4, prechorus.when(colors, x => x.theme("githubLight xcodeLight"))],
[30, chorus({bigger: false}).when(colors, x => x.theme("githubDark aura androidstudio abcdef"))],
[2, inbetween.when(colors, x => x.theme("terminal"))],
[16, part2({ withBass: false }).rev().when(colors, x => x.theme("<githubDark materialDark>"))],
[14, part2({ withBass: false }).jux(rev).when(colors, x => x.theme("githubDark materialDark"))],
[4, prechorus.when(colors, x => x.theme("githubLight xcodeLight"))],
[62, chorus({ bigger: true}).when(colors, x => x.theme("githubDark aura androidstudio abcdef"))],
[23, outro.when(colors, x => x.theme("githubLight xcodeLight"))],
[9999, silence.when(colors, x => x.theme("strudelTheme"))]
)
// .mainTempo()
// .theme("strudelTheme")
// .theme("[terminal abcdef androidstudio atomone aura bespin darcula dracula duotoneDark eclipse githubDark gruvboxDark materialDark nord okaidia solarizedDark sublime tokyoNight tokyoNightStorm vscodeDark xcodeDark bbedit duotoneLight githubLight gruvboxLight materialLight noctisLilac solarizedLight tokyoNightDay xcodeLight]/64")
.fontFamily("x3270")
// .color("[fuschia [aquamarine dodgerblue] [hotpink] blueviolet deeppink [cornsilk indigo] crimson cyan]/12")
// .punchcard({fold:1,flipTime:1,vertical:1})
// //test
// @version 1.0
$: s("bd!4")
.bank("RolandTR909")
.scope()
$: n("[~ [<[3, 5, 7]!2 [0, 2, 4]!2> ~]]*2").scale("D:major").sound("gm_electric_guitar_muted").delay(.5)
// alternative, demonstrating how to sample randomness
$: n("[~ [<[[3, 5, 7]|[4, 6, 1]]!2 [[0, 2, 4]|[4, 7, 9]]!2> ~]]*2")
.scale("D:minor")
.sound("gm_electric_guitar_muted")
.delay(.5)
"0!2 2 4 7 9 11 14 16 18 21 18 16 14 11 9 7 4 2 ~".scale("C:major").scaleTranspose("<0 -4 -3 -1>")
.note()
.jux(rev)
.fast(0.5)
.clip(4).s("piano")
$: s("bd!4, hh!2 oh")
.bank("RolandTR909")
.scope()
note(`<
[e5 [b4 c5] d5 [c5 b4]]
[a4 [a4 c5] e5 [d5 c5]]
[b4 [~ c5] d5 e5]
[c5 a4 a4 ~]
[[~ d5] [~ f5] a5 [g5 f5]]
[e5 [~ c5] e5 [d5 c5]]
[b4 [b4 c5] d5 e5]
[c5 a4 a4 ~]
,
[[e2 e3]*4]
[[a2 a3]*4]
[[g#2 g#3]*2 [e2 e3]*2]
[a2 a3 a2 a3 a2 a3 b1 c2]
[[d2 d3]*4]
[[c2 c3]*4]
[[b1 b2]*2 [e2 e3]*2]
[[a1 a2]*4]
>`)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment