feat(sim): real buzzer/RTTTL sound via Web Audio

genericBuzzer (src/helpers/ui/buzzer.h/.cpp) gets a third platform branch,
#elif defined(SIM_PLATFORM), alongside the existing NRF52 (direct PWM) and
NonBlockingRtttl paths -- purely additive, no changes to either real-hardware
branch. It reuses the NRF52 branch's already hardware-free RTTTL parser
(_parseHeader/_parseNext/_noteFreq, now shared via a widened guard) but
tracks (current frequency, note-end-time) instead of touching real PWM/timer
registers, advancing on plain millis() polling from loop() -- same
non-blocking shape UITask already drives every tick.

Wired into the sim build the same way every real board sets its buzzer pin
(-D PIN_BUZZER=<n> in build_flags/DEFINES; here it's a dummy sentinel since
there's no real pin, just something to activate the existing #ifdef
PIN_BUZZER guards in UITask.h/.cpp/SoundNotifier.h unchanged), plus two new
small UITask accessors (isBuzzerPlaying/buzzerFreqHz/buzzerVolume) and three
EMSCRIPTEN_KEEPALIVE exports so a host page can poll the buzzer's state.

Browser side: one Web Audio oscillator+gain per companion instance (index.html
single-instance; mesh.html per A/B, not R which is headless), created lazily
on the first real user gesture (AudioContext autoplay policy), polled every
20ms and mapped to the oscillator frequency/gain -- so every notification
sound, ringtone, alarm, and volume-blip that already worked on real hardware
now actually produces audio in the browser, unchanged at the call-site level.

Verified end-to-end with real RTTTL playback traces (not just "no errors"):
the startup jingle's exact note frequencies (C6/E6/G6) and a real DM-received
notification triggering the receiving instance's Web Audio gain node from 0
to its mapped volume and back, matching the actual "MsgRcv3" melody's notes.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
Jakub
2026-09-03 13:59:26 +02:00
co-authored by Claude Sonnet 5
parent 0cb02ee18f
commit f61d6832a7
8 changed files with 254 additions and 18 deletions
+4
View File
@@ -75,6 +75,7 @@ SRCS=(
src/helpers/StaticPoolPacketManager.cpp
src/helpers/TransportKeyStore.cpp
src/helpers/TxtDataHelpers.cpp
src/helpers/ui/buzzer.cpp
lib/ed25519/add_scalar.c
lib/ed25519/fe.c
lib/ed25519/ge.c
@@ -127,6 +128,9 @@ DEFINES=(
# DisplayDriver (variants/sim/SimDisplayDriver.h's __EMSCRIPTEN__-guarded
# SimDisplayDriverCanvas class) instead of the ASCII/stdout one.
-DDISPLAY_CLASS=SimDisplayDriverCanvas
# Dummy sentinel (no real pin) -- see platformio.ini's own comment on the
# native env's identical flag.
-DPIN_BUZZER=0
-DMAX_CONTACTS=100
-DMAX_GROUP_CHANNELS=8
)