Skip to content

Instantly share code, notes, and snippets.

@jcsteh
Last active June 21, 2024 14:44
Show Gist options
  • Save jcsteh/7ccbc6f7b1b7eb85c1c14ac5e0d65195 to your computer and use it in GitHub Desktop.
Save jcsteh/7ccbc6f7b1b7eb85c1c14ac5e0d65195 to your computer and use it in GitHub Desktop.
AutoHotkey script to control Spotify with global keyboard shortcuts
; SpotifyGlobalKeys.ahk:
; AutoHotkey script to control Spotify with global keyboard shortcuts
; Author: James Teh <jamie@jantrid.net>
; Copyright 2017-2018 James Teh
; License: GNU General Public License version 2.0
DetectHiddenWindows, On
; Get the HWND of the Spotify main window.
getSpotifyHwnd() {
WinGet, spotifyHwnd, ID, ahk_exe spotify.exe
Return spotifyHwnd
}
; Send a key to Spotify.
spotifyKey(key) {
spotifyHwnd := getSpotifyHwnd()
; Chromium ignores keys when it isn't focused.
; Focus the document window without bringing the app to the foreground.
ControlFocus, Chrome_RenderWidgetHostHWND1, ahk_id %spotifyHwnd%
ControlSend, , %key%, ahk_id %spotifyHwnd%
Return
}
; Win+alt+p: Play/Pause
#!p::
{
spotifyKey("{Space}")
Return
}
; Win+alt+down: Next
#!Down::
{
spotifyKey("^{Right}")
Return
}
; Win+alt+up: Previous
#!Up::
{
spotifyKey("^{Left}")
Return
}
; Win+alt+right: Seek forward
#!Right::
{
spotifyKey("+{Right}")
Return
}
; Win+alt+left: Seek backward
#!Left::
{
spotifyKey("+{Left}")
Return
}
; shift+volumeUp: Volume up
+Volume_Up::
{
spotifyKey("^{Up}")
Return
}
; shift+volumeDown: Volume down
+Volume_Down::
{
spotifyKey("^{Down}")
Return
}
; Win+alt+o: Show Spotify
#!o::
{
spotifyHwnd := getSpotifyHwnd()
WinGet, style, Style, ahk_id %spotifyHwnd%
if (style & 0x10000000) { ; WS_VISIBLE
WinHide, ahk_id %spotifyHwnd%
} Else {
WinShow, ahk_id %spotifyHwnd%
WinActivate, ahk_id %spotifyHwnd%
}
Return
}
@skyfenton
Copy link

Just spent most of my workday troubleshooting this thing....

Guys, if the shortcut keys don't work reliably, you have to rewrite the script.

From: spotifyKey("^{Right}") To: spotifyKey("{Ctrl Down}{Right}{Ctrl Up}")

I can't get this to work and I feel like I've read the whole thread, any ideas?

@The-Dolphi
Copy link

Works perfectly, thank you for it!
Just changed the volume control to page up and down with a #IfWinExist condition looking for Spotify.

@juanmalunatic
Copy link

juanmalunatic commented May 17, 2022

Modified some of the base functions to make it work with AHK v2

;; Get the handle
getSpotifyHwnd() {
	spotifyHwnd := WinGetID("ahk_exe Spotify.exe")
	Return spotifyHwnd
}

; Send a key, generic
spotifyKey(key) {
	spotifyHwnd := getSpotifyHwnd()
	; Chromium ignores keys when it isn't focused.
	; Focus the document window without bringing the app to the foreground.
	ControlFocus "Chrome_RenderWidgetHostHWND1", "ahk_id " . spotifyHwnd
	ControlSend key, , "ahk_id " . spotifyHwnd
	Return
}

; My combination, feel free to change to suit your tastes.
^+Space::{
        spotifyKey("{Space}")
        Return
}

@elhertz
Copy link

elhertz commented Jun 3, 2022

is there a way to show the spotify overlay? it doesn't show when using these hotkeys

@AdasOsorus
Copy link

Modified some of the base functions to make it work with AHK v2

;; Get the handle
getSpotifyHwnd() {
	spotifyHwnd := WinGetID("ahk_exe Spotify.exe")
	Return spotifyHwnd
}

; Send a key, generic
spotifyKey(key) {
	spotifyHwnd := getSpotifyHwnd()
	; Chromium ignores keys when it isn't focused.
	; Focus the document window without bringing the app to the foreground.
	ControlFocus "Chrome_RenderWidgetHostHWND1", "ahk_id " . spotifyHwnd
	ControlSend key, , "ahk_id " . spotifyHwnd
	Return
}

; My combination, feel free to change to suit your tastes.
^+Space::{
        spotifyKey("{Space}")
        Return
}

Thank you!

@Mane660
Copy link

Mane660 commented Apr 28, 2024

Modified some of the base functions to make it work with AHK v2

;; Get the handle
getSpotifyHwnd() {
	spotifyHwnd := WinGetID("ahk_exe Spotify.exe")
	Return spotifyHwnd
}

; Send a key, generic
spotifyKey(key) {
	spotifyHwnd := getSpotifyHwnd()
	; Chromium ignores keys when it isn't focused.
	; Focus the document window without bringing the app to the foreground.
	ControlFocus "Chrome_RenderWidgetHostHWND1", "ahk_id " . spotifyHwnd
	ControlSend key, , "ahk_id " . spotifyHwnd
	Return
}

; My combination, feel free to change to suit your tastes.
^+Space::{
        spotifyKey("{Space}")
        Return
}

Not working when spotify is minimized.
image

when spotify is opened in background it works fine.

@walbjorn
Copy link

walbjorn commented May 7, 2024

This is what currently works for me using AHK 1.1 (it will not work if you minimize Spotify).

The keybindings are set at the bottom of the script, currently set to use Winkey and Winkey+Alt modifiers.

DetectHiddenWindows, On

; Get the HWND of the Spotify main window.
getSpotifyHwnd() {
  WinGet, spotifyHwnd, ID, ahk_exe spotify.exe
  Return spotifyHwnd
}

; Send a key to Spotify.
spotifyKey(key) {
  spotifyHwnd := getSpotifyHwnd()
  ControlClick, x500 y100, ahk_id %spotifyHwnd%, , Left, 1, U
  ControlSend, ahk_parent, %key%, ahk_id %spotifyHwnd%
}

; Define keybindings here
#x::spotifyKey("^{Left}")			; Previous song
#c::spotifyKey("^{Right}")		; Next song
#Down::spotifyKey("^{Down}")	; Volume down
#Up::spotifyKey("^{Up}")		; Volume up
#Space::spotifyKey("{Space}")		; Play/pause
;#!Space::spotifyKey("!+{b}")		; Like song
#Left::spotifyKey("+{Left}")		; Seek backward
#Right::spotifyKey("+{Right}")	; Seek forward

; Win+Alt+Space: Hotkey to show/focus Spotify
#!Space::
  WinActivate, ahk_exe spotify.exe
  WinMaximize, ahk_exe spotify.exe
  return

@OmTatSat
Copy link

OmTatSat commented Jun 13, 2024

to make the controls work when the window is minimized to the taskbar or tray, you need to use winhide

can be done like this

#If OnMy_Close_or_Min_Buttons()
LButton:: Winhide
#If
OnMy_Close_or_Min_Buttons() {
Static MyWindowCriteria := "ahk_exe Spotify.exe" ; change to meet your neeeds
Critical
SetTitleMatchMode, 2
CoordMode, Mouse, Screen
MouseGetPos, X, Y, MID
;ToolTip, mid %mid%
If (WID := WinExist(MyWindowCriteria)) && (WID = MID) {
SendMessage, 0x0084, 0, (X & 0xFFFF) | ((Y & 0xFFFF) << 16) ; WM_NCHITTEST
;Return (ErrorLevel = 20) ; HTCLOSE
;Return (ErrorLevel = 8) ; HTmin
;ToolTip, ErrorLevel %ErrorLevel%
if ((ErrorLevel = "20") or (ErrorLevel = "8"))
{
;ToolTip, test
return true
}
}
Return False
}

and function to send hotkeys is like this

; Send a key to Spotify.
spotifyKey(key) {
;spotifyHwnd := getSpotifyHwnd()
; Chromium ignores keys when it isn't focused.
; Focus the document window without bringing the app to the foreground.
IfWinNotActive, ahk_exe Spotify.exe
{
DetectHiddenWindows, on
DetectHiddenText, on
WinGet, OutputVar1, ID , ahk_exe Spotify.exe
ControlFocus, , ahk_id %OutputVar1%
ControlSend, ahk_parent , %key%, ahk_class Chrome_WidgetWin_1
return
}
IfWinActive, ahk_exe Spotify.exe
{
Send, %key%
;ToolTip, keyssend
return
}
Return
}

@Zivers88
Copy link

Zivers88 commented Jun 17, 2024

to make the controls work when the window is minimized to the taskbar or tray, you need to use winhide

can be done like this

#If OnMy_Close_or_Min_Buttons() LButton:: Winhide #If OnMy_Close_or_Min_Buttons() { Static MyWindowCriteria := "ahk_exe Spotify.exe" ; change to meet your neeeds Critical SetTitleMatchMode, 2 CoordMode, Mouse, Screen MouseGetPos, X, Y, MID ;ToolTip, mid %mid% If (WID := WinExist(MyWindowCriteria)) && (WID = MID) { SendMessage, 0x0084, 0, (X & 0xFFFF) | ((Y & 0xFFFF) << 16) ; WM_NCHITTEST ;Return (ErrorLevel = 20) ; HTCLOSE ;Return (ErrorLevel = 8) ; HTmin ;ToolTip, ErrorLevel %ErrorLevel% if ((ErrorLevel = "20") or (ErrorLevel = "8")) { ;ToolTip, test return true } } Return False }

and function to send hotkeys is like this

; Send a key to Spotify. spotifyKey(key) { ;spotifyHwnd := getSpotifyHwnd() ; Chromium ignores keys when it isn't focused. ; Focus the document window without bringing the app to the foreground. IfWinNotActive, ahk_exe Spotify.exe { DetectHiddenWindows, on DetectHiddenText, on WinGet, OutputVar1, ID , ahk_exe Spotify.exe ControlFocus, , ahk_id %OutputVar1% ControlSend, ahk_parent , %key%, ahk_class Chrome_WidgetWin_1 return } IfWinActive, ahk_exe Spotify.exe { Send, %key% ;ToolTip, keyssend return } Return }

Where should I paste this code? I get an error
«Error at line 23.
Line Text: and function to send hotkeys is like this
Error: This line does not contain a recognized action.»

The code above from walbjorn works great!
(and the page author's code does not work for me) It turned out to work, but somehow strangely and every once in a while

@OmTatSat
Copy link

OmTatSat commented Jun 17, 2024

what is in line 23?
you can insert this part at the beginning or end of the code

#If OnMy_Close_or_Min_Buttons()
LButton:: Winhide
#If
OnMy_Close_or_Min_Buttons() {
Static MyWindowCriteria := "ahk_exe Spotify.exe" ; change to meet your neeeds
Critical
SetTitleMatchMode, 2
CoordMode, Mouse, Screen
MouseGetPos, X, Y, MID
;ToolTip, mid %mid%
If (WID := WinExist(MyWindowCriteria)) && (WID = MID) {
SendMessage, 0x0084, 0, (X & 0xFFFF) | ((Y & 0xFFFF) << 16) ; WM_NCHITTEST
;Return (ErrorLevel = 20) ; HTCLOSE
;Return (ErrorLevel = 8) ; HTmin
;ToolTip, ErrorLevel %ErrorLevel%
if ((ErrorLevel = "20") or (ErrorLevel = "8"))
{
;ToolTip, test
return true
}
}
Return False
}

this

; Send a key to Spotify.
spotifyKey(key) {
;spotifyHwnd := getSpotifyHwnd()
; Chromium ignores keys when it isn't focused.
; Focus the document window without bringing the app to the foreground.
IfWinNotActive, ahk_exe Spotify.exe
{
DetectHiddenWindows, on
DetectHiddenText, on
WinGet, OutputVar1, ID , ahk_exe Spotify.exe
ControlFocus, , ahk_id %OutputVar1%
ControlSend, ahk_parent , %key%, ahk_class Chrome_WidgetWin_1
return
}
IfWinActive, ahk_exe Spotify.exe
{
Send, %key%
;ToolTip, keyssend
return
}
Return
}`

instead of

`; Send a key to Spotify.
spotifyKey(key) {
spotifyHwnd := getSpotifyHwnd()
ControlClick, x500 y100, ahk_id %spotifyHwnd%, , Left, 1, U
ControlSend, ahk_parent, %key%, ahk_id %spotifyHwnd%
}

but additional testing revealed that sometimes this method stops working, I am looking for and trying new approaches that can give permanent work in a collapsed state.

@drandarov-io
Copy link

drandarov-io commented Jun 18, 2024

https://gist.github.com/drandarov-io/96a5df7d1dee2d545f22fcaddf522284

Thought I'd add something that worked for me after much trial and error.

@OmTatSat
Copy link

Yesterday I came to a similar approach) until it seems not stop working

spotifyKey(key) {
IfWinNotActive, ahk_exe Spotify.exe
{
DetectHiddenWindows, on
DetectHiddenText, on

	ControlFocus, , , Chrome Legacy Window
	ControlSend, ahk_parent , %key%, ahk_class Chrome_WidgetWin_1
	return
	}
IfWinActive, ahk_exe Spotify.exe
{
	Send,  %key%
	return
}
Return

}

@Zivers88
Copy link

Zivers88 commented Jun 21, 2024

what is in line 23? you can insert this part at the beginning or end of the code

#If OnMy_Close_or_Min_Buttons() LButton:: Winhide #If OnMy_Close_or_Min_Buttons() { Static MyWindowCriteria := "ahk_exe Spotify.exe" ; change to meet your neeeds Critical SetTitleMatchMode, 2 CoordMode, Mouse, Screen MouseGetPos, X, Y, MID ;ToolTip, mid %mid% If (WID := WinExist(MyWindowCriteria)) && (WID = MID) { SendMessage, 0x0084, 0, (X & 0xFFFF) | ((Y & 0xFFFF) << 16) ; WM_NCHITTEST ;Return (ErrorLevel = 20) ; HTCLOSE ;Return (ErrorLevel = 8) ; HTmin ;ToolTip, ErrorLevel %ErrorLevel% if ((ErrorLevel = "20") or (ErrorLevel = "8")) { ;ToolTip, test return true } } Return False }

this

; Send a key to Spotify. spotifyKey(key) { ;spotifyHwnd := getSpotifyHwnd() ; Chromium ignores keys when it isn't focused. ; Focus the document window without bringing the app to the foreground. IfWinNotActive, ahk_exe Spotify.exe { DetectHiddenWindows, on DetectHiddenText, on WinGet, OutputVar1, ID , ahk_exe Spotify.exe ControlFocus, , ahk_id %OutputVar1% ControlSend, ahk_parent , %key%, ahk_class Chrome_WidgetWin_1 return } IfWinActive, ahk_exe Spotify.exe { Send, %key% ;ToolTip, keyssend return } Return }`

instead of

`; Send a key to Spotify. spotifyKey(key) { spotifyHwnd := getSpotifyHwnd() ControlClick, x500 y100, ahk_id %spotifyHwnd%, , Left, 1, U ControlSend, ahk_parent, %key%, ahk_id %spotifyHwnd% }

but additional testing revealed that sometimes this method stops working, I am looking for and trying new approaches that can give permanent work in a collapsed state.

This code works fine for me with Spotify minimized in tray (!), much to my delight (finally! After months of agony!)

DetectHiddenWindows, On

; Get the HWND of the Spotify main window.
getSpotifyHwnd() {
WinGet, spotifyHwnd, ID, ahk_exe spotify.exe
Return spotifyHwnd
}

; Send a key to Spotify.
spotifyKey(key) {
spotifyHwnd := getSpotifyHwnd()
; Chromium ignores keys when it isn't focused.
; Focus the document window without bringing the app to the foreground.
ControlFocus, Chrome_RenderWidgetHostHWND1, ahk_id %spotifyHwnd%
ControlSend, , %key%, ahk_id %spotifyHwnd%
Return
}

; Ctrl+Shift+q: Play/Pause
^+q::
{
spotifyKey("{Space}")
Return
}

; alt+v: Next
!v::
{
spotifyKey("^{Right}")
Return
}

; alt+z: Previous
!z::
{
spotifyKey("^{Left}")
Return
}

; Ctrl+alt+Up: Volume up
^!Up::
{
spotifyKey("^{Up}")
Return
}

; Ctrl+alt+Down: Volume Down
^!Down::
{
spotifyKey("^{Down}")
Return
}

; Ctrl+: Show Spotify ^::
{
spotifyHwnd := getSpotifyHwnd()
WinGet, style, Style, ahk_id %spotifyHwnd%
if (style & 0x10000000) { ; WS_VISIBLE
WinHide, ahk_id %spotifyHwnd%
} Else {
WinShow, ahk_id %spotifyHwnd%
WinActivate, ahk_id %spotifyHwnd%
}
Return
}

Sometimes it doesn't catch the focus or on the contrary, holds it, but it already trifles for a couple clicks :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment