fix(pipeline): dynamic capture sample rates and reactive device format tracking - #50
Merged
Merged
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What does this PR do?
Fixes hardcoded 48 kHz in System Audio & App Audio UI:
Previously, the
System AudioandApp Audionodes displayed a static48.0 kHz · 2 ch · f32badge and a misleadingResampling: 48 kHz → <pipelineRate>tooltip, even when the OS capture was delivering audio at a different rate (e.g. 96 kHz) and running bit-transparently without resampling. A newcapture_device_infoTauri IPC command was added to report the true native capture format across macOS, Windows, and Linux.Supports dynamic pipeline sample rates for Windows WASAPI App Audio loopback:
Previously on Windows,
VIRTUAL_AUDIO_DEVICE_PROCESS_LOOPBACKwas hardcoded to 48 kHz. Now, the virtual capture endpoint initializes directly at the configured Pipeline sample rate, letting Windows Audio Engine deliver process audio at the pipeline rate with zero engine resamplers allocated.Fixes lack of reactivity to OS audio settings changes in Speaker and Microphone nodes:
Previously, changing an output or input device's sample rate in external system tools (such as macOS Audio MIDI Setup or Windows Sound Control Panel) did not update the
SpeakerorMicrophonenode badges unless the selected device ID changed.Introduces a universal reactive
useDeviceInfohelper:Consolidates device/capture inspection into a single composable in
$lib/modules/audio/device_info.svelte.ts. It re-queries immediately upon window focus / visibility change and maintains a lightweight background poll (2.5s) so side-by-side configuration updates reflect without manual interaction.Adds tests for 1:1 bit-transparent audio passthrough:
Adds unit tests in Rust (
audio::pipeline::input::testsandaudio::pipeline::output::tests) validating that matching sample rates (e.g. 96 kHz App Audio → 96 kHz Pipeline → 96 kHz Speaker) allocate no resamplers (resampler == None) and preserve audio samples bit-for-bit with exact float bit equality (a.to_bits() == b.to_bits()).Documents per-platform capture semantics in
docs/CONCEPT.md:Clarified how sample rate negotiation behaves across macOS (CoreAudio tap follows hardware output device), Windows (App Audio follows pipeline rate, System Audio follows output mix format), and Linux (PipeWire negotiates pipeline rate).
Why is this the right approach?
Speaker,Microphone,System Audio, andApp Audio,useDeviceInfounifies format strings, channel counts, and resampling tooltip derivations in one place.Checklist
bun run checkpasses (0 errors)cargo check --manifest-path src-tauri/Cargo.tomlpassesbun run formatleaves the tree cleanDspWorker::runPlatform coverage
Speaker,System Audio, andApp Audioimmediately update their sample rate badges and hide the resampling indicator when matchingpipelineSampleRate.cargo test --lib audio::pipeline(14 passing tests including bit-transparency tests).bun test(15 passing tests).src-tauri/src/audio/capture/mod.rs(cross-platformcapture_device_infodispatcher)src-tauri/src/audio/capture/windows.rs(WASAPI process loopback dynamic rate)src-tauri/src/audio/pipeline/input/windows.rs(target rate passing for Windows inputs)docs/CONCEPT.md(cross-platform capture negotiation documentation)Related