Skip to content

Instantly share code, notes, and snippets.

@fullmetal1
Last active November 4, 2021 02:07
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fullmetal1/7314259657e612bfe819e8d88f1878c3 to your computer and use it in GitHub Desktop.
Save fullmetal1/7314259657e612bfe819e8d88f1878c3 to your computer and use it in GitHub Desktop.
A bash script to get system-wide push to talk through mouse/keyboard buttons on any Linux, BSD, Unix etc system running Xorg and pulseaudio

I couldn't find a single example of one of these online so I decided to do it myself and share it for the world's convenience.

This script requires a system with Xorg, pulseaudio, and xinput (not the Microsoft one). I have only ever tested on linux. You may need to modify some commands. Your usage may vary in which case you will have to modify this script. The functionality is slightly esoteric so I will describe the functionality here:

The script runs as a one liner bash command. This is done so that I can put it into XFCE's session and startup without creating a new script for it. First the script finds the id of the virtual core pointer (sum of all pointer devices) Then the script mutes the default source (hopefully your microphone). This is because pulseaudio tends to unmute sources on startup. After that the script runs an instance of xinput to catch all keyboard and mouse events. That output is modified to add a \f character (a placeholder for newlines) at the start of each event. After that, each newline character is translated to a space character, and then the \f is translated back into a newline. Each Event will now be on a single line. Now we grep out just RawButton (mouse depress/release events). Then we grep through xinput to find the id of the virtual core pointer (all pointer devices) Then we grep for just the virtual core pointer id in the xinput to get just that mouse. After that we grep for just the button 11 (detail: 11). I use button 11 but you may want to run xinput and watch the output as you press your button of choice for push to talk. For each line outputted now (just the button depress/release events for our selected button), we run a while loop. If it was a RawButtonPress event, then we unmute the microphone. Otherwise we re-mute the microphone.

bash -c 'device=$(xinput | grep '\''Virtual core pointer'\'' | sed '\''s/.*id=\([0-9]\+\).*/\1/g'\'') ; pactl set-source-mute @DEFAULT_SOURCE@ true ; xinput -test-xi2 --root | stdbuf -i0 -o0 -e0 sed -u '\''s/EVENT/\fEVENT/g'\'' | stdbuf -i0 -o0 -e0 tr -s '\''\n'\'' '\'' '\'' | stdbuf -i0 -o0 -e0 tr -s '\''\f'\'' '\''\n'\'' | grep --line-buffered RawButton | grep --line-buffered $device | grep --line-buffered "detail: 11" | while read line; do if [[ "$(echo $line | grep RawButtonPress)" != "" ]]; then pactl set-source-mute @DEFAULT_SOURCE@ false ; else pactl set-source-mute @DEFAULT_SOURCE@ true ; fi ; done'
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment