Headphone/Speaker fast switching with Pipewire

EDIT: Oh no, IDs don't survive reboot(!?!) This post will need some work as I figure this out. Keep reading though.

I've recently gone all in on Fedora Silverblue, and while I was able to modify the initial setup to fit me as an Ubuntu ex-pat I was missing one thing I use all the time.

There's the awesome sound-switcher-indicator but I can't get that in Fedora, so I've been getting used to sound-output-device-chooser, which is similar enough, but missing a key feature I needed, the ability to assign a keyboard shortcut to switch where the sound comes out of.

I am in meetings all day and playing games at night, and I am constantly switching back and forth, so I like to assign keyboard shortcuts. Ctrl-Alt-H (for headphones) and Ctrl-Alt-S (for speakers) just flip my output on the fly, so if I'm watching something on my headset and want to kick over to speakers I can just do that, and when the family comes into the room to use the TV I can quickly just move to headphones without interrupting, pausing, going into a menu, oh-no-what-desktop-is-spotify-in, all that.

Here's how I set this up in Fedora Silverblue 35, which is now using Pipewire. And while they do offer a Pulse compatabiltiy layer, I wanted to figure out how to do this with the new tools. First cool tool I discovered was pw-top, which is exactly what you think it is:

top for sound

This let me get the crucial bit of info I needed, what ID does the sound system use for my speakers, and for my headset. The output here is 39 for my Steelseries Headset, and the output for my USB speaker is 101. Now I open Spotify and play Megadeth.

Doing a wpctl set-default 39 will automatically switch the audio to my headset, and wpctl set-default 101 changes it to the speaker. This works with everything, your music client, your games, etc. So now we have the commands, let's hook 'em up to the keyboard shortcuts.

Make two, one for headphones, and one for speakers

Go into the keyboard settings for GNOME and make a custom shortcut. We'll need two, one for switching to speakers, one to switching for headphones, and then set them to whatever hotkey works for you.

Not quite so easy! (Updated)

So I found that the ID's change on reboot or when you unplug and replug the device back in! So sometimes it might be 42, sometimes it might be 51. Echoes of /dev/sda -> UUID right? Instead I used the name of the entire sink as the switch:

pactl set-default-sink alsa_output.usb-Jieli_Technology_UACDemoV1.0_45414534343616FF-00.analog-stereo

pactl set-default-sink alsa_output.usb-SteelSeries_Arctis_Pro_Wireless-00.stereo-game

I was hoping wpcctl set-default alsa_output.usb-Jieli_Technology_UACDemoV1.0_45414534343616FF-00.analog-stereo would be the new version of this command, but unfortunately it only takes ID as an argument and not a name.

Things I learned today: Pipewire commands start with pw- are pipewire commands, and I was expecting to find pwctl to be the replacement for pulseaudio's pactl. However it's actually wpctl, which is wireplumber, so heads up if you're not familiar with this.

Silverblue doesn't come with pulseaudio-utils installed by default, so I layered it so I could at least use the pactl commands to make this work. Now off to go read wireplumber bugs to see if the IDs are supposed to change, they for sure are changing on two of my computers.

And that's it. Thanks to the Fedora Discord for helping out!