feat(denoise): switch noise suppression mid-call (+ fix re-captures ignoring noiseSuppression) #66

Merged
jared merged 1 commits from feat/live-denoise-switch into lotus 2026-10-30 21:15:44 -04:00
1 Commits
Author SHA1 Message Date
Lotus CIandClaude Opus 5.5 949103d649 feat(denoise): switch noise suppression mid-call (io.lotus.set_denoise)
CI / Build embedded bundle (push) Skipped
CI / Build embedded bundle (pull_request) Successful in 1m47s
CI / Publish to Gitea npm registry (pull_request) Skipped
The host can now change noise suppression on the live mic without a
rejoin: off / browser-native / ML, the ML model, the gate and stacking
browser NS in front of the model.

- Model swaps preload the new model while the old one keeps running,
  then swap the processor (no mic re-capture).
- Browser NS on/off re-captures the mic via restartTrack with the new
  constraint (passing the deviceId, without which LiveKit drops every
  constraint). The choice is kept in lotusCaptureOverride, which
  ConnectionFactory reads, so a later SFU reconnect captures the same way.
- Switches are serialized; a burst collapses into the last one. Each one
  reports io.lotus.denoise_state (now with `mode`).

Fixes found while testing in Chromium:
- The mic level meter (and muted-speech nudge) kept a clone of the
  ORIGINAL mic track and never noticed LiveKit's restartTrack. Chrome
  makes all open tracks of a device share audio processing, so every
  re-capture silently kept the old noiseSuppression (asked false, got
  true). The meter now drops its clone around our re-capture and
  re-taps on TrackEvent.Restarted, which also fixes it listening to the
  old device after a mic switch.
- LiveKit defaults voiceIsolation ON, a further voice filter in "off"
  and ML modes where the platform implements it. It now follows browser
  noise suppression.

Verified in a two-browser call: joined as browser and as ML(dtln), then
switched dtln -> deepfilternet -> rnnoise -> browser -> off; each step
applied within ~0.5 s and every re-capture got the constraints it asked
for.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017PCb59uY3UKqDqt7B6hzd5
2026-10-30 21:13:40 -04:00