dreamstack/examples/step-sequencer.ds
enzotar 2aa2c7ad8e feat: step sequencer demo — reactive pads, playhead, BPM
Step sequencer: 4 instruments × 8 steps, timer-driven playhead,
toggleable pads, BPM controls with streaming. 75 lines of .ds code.

Parser fixes:
- UI elements checked before LParen (button (if ...) is element, not call)
- Element args support parenthesized expressions: button (if cond ...)
- StringInterp recognized as valid string start in parse_primary/parse_element

Codegen fixes:
- emit_expr checks local_vars: loop var i emits 'i' not 'i.value'
- Array index mutations re-trigger signal: pads.value = [...pads.value]

110 tests, 0 failures.
2026-02-25 19:33:12 -08:00

72 lines
1.7 KiB
Text
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

-- DreamStack Step Sequencer
-- Collaborative beat grid: two tabs, same pads, real-time sync
let bpm = 120
let step = 0
-- 4 instruments × 8 steps = 32 pads (flat array, index with row*8+col)
let pads = [0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0]
-- Playhead advances every beat
every (60000 / bpm / 2) -> step = (step + 1) % 8
-- Stream for multiplayer
stream sequencer on "ws://localhost:9100/source/beats" { mode: signal }
view sequencer =
column [
text "DreamStack Beats"
text "BPM: {bpm}"
-- Kick (pads 0-7)
text "Kick"
row [
for i in [0, 1, 2, 3, 4, 5, 6, 7] ->
button (if pads[i] then "●" else "○") {
click: pads[i] = if pads[i] then 0 else 1
}
]
-- Snare (pads 8-15)
text "Snare"
row [
for i in [8, 9, 10, 11, 12, 13, 14, 15] ->
button (if pads[i] then "●" else "○") {
click: pads[i] = if pads[i] then 0 else 1
}
]
-- Hi-hat (pads 16-23)
text "HiHat"
row [
for i in [16, 17, 18, 19, 20, 21, 22, 23] ->
button (if pads[i] then "●" else "○") {
click: pads[i] = if pads[i] then 0 else 1
}
]
-- Bass (pads 24-31)
text "Bass"
row [
for i in [24, 25, 26, 27, 28, 29, 30, 31] ->
button (if pads[i] then "●" else "○") {
click: pads[i] = if pads[i] then 0 else 1
}
]
-- Playhead indicator
row [
for i in [0, 1, 2, 3, 4, 5, 6, 7] ->
text (if i == step then "▼" else "·")
]
-- BPM controls
row [
button "10" { click: bpm -= 10 }
text "{bpm}"
button "+10" { click: bpm += 10 }
]
]