Skip to content

Instantly share code, notes, and snippets.

@andyngo
Last active August 23, 2023 09:32
Show Gist options
  • Save andyngo/e5da7322cbc04d00e71da019c2afd259 to your computer and use it in GitHub Desktop.
Save andyngo/e5da7322cbc04d00e71da019c2afd259 to your computer and use it in GitHub Desktop.
My personal hammerspoon config.
-- global config --
-- disable all window animation
hs.window.animationDuration = 0
-- custom alert style
hs.alert.defaultStyle.radius = 4
hs.alert.defaultStyle.fillColor = {white = 0, alpha = 0.9}
hs.alert.defaultStyle.strokeColor = {white = 0, alpha = 0}
hs.alert.defaultStyle.fadeInDuration = 0
hs.alert.defaultStyle.fadeOutDuration = 0
hs.alert.defaultStyle.textSize = 14
hs.alert.defaultStyle.textStyle = {paragraphStyle = {alignment = "center"}}
-- display names
local dellU2414H = "DELL U2414H"
local builtInDisplay = "Color LCD"
-- display layouts --
-- layout if *only* Dell Monitor is running
local dellU2414HLayout = {
{"Tweetbot", hs.appfinder.windowFromWindowTitlePattern("Main Window - "), dellU2414H, hs.geometry.unitrect(0,0,0.175,1), nil, nil},
{"TaskPaper", nil, builtInDisplay, hs.geometry.unitrect(0,0,0.175,1), nil, nil},
{"Google Chrome", nil, dellU2414H, hs.geometry.unitrect(0.175,0,0.825,1), nil, nil},
{"MacVim", nil, dellU2414H, hs.geometry.unitrect(0.175,0,0.825,1), nil, nil}
}
-- layout if no external displays are connected
local macbookProLayout = {
{"Tweetbot", hs.appfinder.windowFromWindowTitlePattern("Main Window - "), builtInDisplay, hs.geometry.unitrect(0,0,0.275,1), nil, nil},
{"TaskPaper", nil, builtInDisplay, hs.geometry.unitrect(0,0,0.275,1), nil, nil},
{"Google Chrome", nil, builtInDisplay, hs.geometry.unitrect(0.275,0,0.725,1), nil, nil},
{"MacVim", nil, builtInDisplay, hs.geometry.unitrect(0.275,0,0.725,1), nil, nil}
}
-- layout if Dell Monitor and Macbook Pro displays are running
local dualMonitorLayout = {
{"Tweetbot", hs.appfinder.windowFromWindowTitlePattern("Main Window - "), dellU2414H, hs.geometry.unitrect(0,0,0.2,1), nil, nil},
{"Google Chrome", nil, dellU2414H, hs.geometry.unitrect(0.2,0,0.8,1), nil, nil},
}
-- function to check if external display is connected
function hasExternalDisplay()
for _, screen in pairs(hs.screen.allScreens()) do
if screen:name() == dellU2414H then
return true
end
end
return false
end
-- function to watch applications
function applicationWatcher(appName, eventType, appObject)
if (eventType == hs.application.watcher.activated) then
if (appName == "Tweetbot" or appName == "MacVim" or appName == "TaskPaper") then
if hasExternalDisplay() then
hs.layout.apply(dellU2414HLayout)
else
hs.layout.apply(macbookProLayout)
end
end
end
end
usbWatcher = nil
-- usb device uuids
local targusHub = 0x0610
local pokerII = 0x0611
local mxMaster2S = 0xc52b
local audioEngineA2 = 0x2704
-- custom hs.alert.show function
function showAlert(message, style, screen, duration)
-- show only one alert at a time
hs.alert.closeAll()
hs.alert.show(message, style, screen, duration)
end
-- function to check if USB devices are connected/removed
function usbDeviceCallback(data)
if (data["productID"] == targusHub) then
if (data["eventType"] == "added") then
showAlert('🔌USB: Targus Hub is connected.')
elseif (data["eventType"] == "removed") then
showAlert('🔌USB: Targus Hub is removed.')
end
end
if (data["productID"] == pokerII) then
if (data["eventType"] == "added") then
showAlert('⌨️USB: Poker II is connected.')
elseif (data["eventType"] == "removed") then
showAlert('⌨️USB: Poker II is removed.')
end
end
if (data["productID"] == mxMaster2S) then
if (data["eventType"] == "added") then
showAlert('🖱USB: MX Master 2S is connected.')
elseif (data["eventType"] == "removed") then
showAlert('🖱USB: MX Master 2S is removed.')
end
end
if (data["productID"] == audioEngineA2) then
if (data["eventType"] == "added") then
showAlert('🔊USB: AudioEngine A2+ is connected.')
elseif (data["eventType"] == "removed") then
showAlert('🔊USB: AudioEngine A2+ is removed.')
end
end
end
-- Spotify bindings --
-- toggle play/pause
hs.hotkey.bind({"cmd", "alt", "shift"}, "8", function() hs.spotify.playpause() end)
-- volume down
hs.hotkey.bind({"cmd", "alt", "shift"}, "-", function()
hs.spotify.volumeDown()
showAlert(
"🔈Spotify volume: " .. hs.spotify.getVolume() .. "%"
)
end)
-- volume up
hs.hotkey.bind({"cmd", "alt", "shift"}, "=", function()
hs.spotify.volumeUp()
showAlert(
"🔊Spotify volume: " .. hs.spotify.getVolume() .. "%"
)
end)
-- next track
hs.hotkey.bind({"cmd", "alt", "shift"}, "9", function()
hs.spotify.next()
showAlert(
"⏭Spotify: " .. hs.spotify.getCurrentTrack() .. " by " .. hs.spotify.getCurrentArtist()
)
end)
-- previous track
hs.hotkey.bind({"cmd", "alt", "shift"}, "7", function()
hs.spotify.previous()
showAlert(
"⏮Spotify: " .. hs.spotify.getCurrentTrack() .. " by " .. hs.spotify.getCurrentArtist()
)
end)
-- rewind 5 seconds
hs.hotkey.bind({"cmd", "alt", "shift"}, ",", function()
hs.spotify.rw()
showAlert(
"⏪Spotify: Rewind track by 5 seconds"
)
end)
-- forward 5 seconds
hs.hotkey.bind({"cmd", "alt", "shift"}, ".", function()
hs.spotify.ff()
showAlert(
"⏩Spotify: Forward track by 5 seconds"
)
end)
-- display current track info as alert
hs.hotkey.bind({"cmd", "alt", "shift"}, "0", function()
showAlert(
"💿Spotify: " .. hs.spotify.getCurrentTrack() .. " by " .. hs.spotify.getCurrentArtist()
)
end)
-- reload hammerspoon config
hs.hotkey.bind({"cmd", "alt", "ctrl"}, "r", function()
hs.reload()
showAlert('✨Config reloaded.')
end)
-- show current time in an alert
hs.hotkey.bind({"cmd", "alt", "ctrl"}, "t", function()
showAlert(
"⏰Current time: " .. os.date("%I:%M%p")
)
end)
-- show current battery in an alert
hs.hotkey.bind({"cmd", "alt", "ctrl"}, "b", function()
showAlert(
"⚡️Current battery: " .. hs.battery.percentage() .. "%"
)
end)
-- function to set muted(boolean)
function micCheck()
if hs.audiodevice.defaultInputDevice():muted() then
hs.audiodevice.defaultInputDevice():setMuted(false)
showAlert(
"🎙Microphone: Live and recording... (Menu + M to mute)"
)
else
hs.audiodevice.defaultInputDevice():setMuted(true)
showAlert(
"🎙Microphone: Muted"
)
end
end
-- mute / unmute microphone
hs.hotkey.bind({"cmd", "alt", "shift"}, "m", function()
micCheck()
end)
appWatcher = hs.application.watcher.new(applicationWatcher)
appWatcher:start()
layoutWatcher = hs.screen.watcher.new(hasExternalDisplay)
layoutWatcher:start()
usbWatcher = hs.usb.watcher.new(usbDeviceCallback)
usbWatcher:start()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment