Files
audioswitch/Cargo.toml
Vincent Lannurien 77be2c188d Cycle the Windows default audio output from a global hotkey
A single 306 KB GUI-subsystem binary with no tray icon and no settings
window: one hidden popup owns the hotkey, the device-change callbacks and
the flyout, and the process sleeps in GetMessageW at 0% CPU in between.

Windows exposes no public API for setting the default audio endpoint, so
this uses the undocumented IPolicyConfig COM interface, confined to
src/policy.rs. Verified working on build 26200. Everything else -
enumeration, IMMNotificationClient, RegisterHotKey, the flyout - is
documented Win32.

The flyout uses the DWM acrylic backdrop and rounded corners the shell
uses for its own flyouts, with text drawn via DrawThemeTextEx and
DTT_COMPOSITED into a 32-bpp DIB, which is what keeps GDI from leaving
black fringes on a composited surface.

Console and Multimedia roles move by default; Communications stays put so
voice chat keeps its headset. Config is a hand-parsed INI reloaded on the
next keypress, keeping the dependency list to the windows crate alone.

Built by cross-compiling from a devcontainer with mingw-w64, so nothing is
installed on the Windows host and the exe imports only system DLLs.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-17 07:29:04 +02:00

45 lines
1.1 KiB
TOML

[package]
name = "audioswitch"
version = "0.1.0"
edition = "2021"
description = "Cycle the Windows default audio output from a global hotkey, with a native OSD flyout"
license = "MIT"
[dependencies]
# The `interface` and `implement` macros expand to `::windows_core::…` paths, so the
# crate has to be nameable directly. It is the same crate `windows` re-exports, so the
# COM types are identical.
windows-core = "0.62"
[dependencies.windows]
version = "0.62"
features = [
"Win32_Devices_FunctionDiscovery",
"Win32_Foundation",
"Win32_Graphics_Dwm",
"Win32_Graphics_Gdi",
"Win32_Media_Audio",
"Win32_Media_Audio_Endpoints",
"Win32_Security",
"Win32_System_Com",
"Win32_System_Com_StructuredStorage",
"Win32_System_Console",
"Win32_System_LibraryLoader",
"Win32_System_Registry",
"Win32_System_Threading",
"Win32_Storage_FileSystem",
"Win32_System_Variant",
"Win32_UI_Controls",
"Win32_UI_HiDpi",
"Win32_UI_Input_KeyboardAndMouse",
"Win32_UI_Shell_PropertiesSystem",
"Win32_UI_WindowsAndMessaging",
]
[profile.release]
opt-level = "z"
lto = true
codegen-units = 1
panic = "abort"
strip = true