Add mac app agent and Terminal.app specific keybinds
This commit is contained in:
21
mac-agent/com.user.kb-focus.plist
Normal file
21
mac-agent/com.user.kb-focus.plist
Normal file
@@ -0,0 +1,21 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>Label</key>
|
||||
<string>com.user.kb-focus</string>
|
||||
<key>ProgramArguments</key>
|
||||
<array>
|
||||
<string>/usr/bin/python3</string>
|
||||
<string>kb-focus.py</string>
|
||||
</array>
|
||||
<key>WorkingDirectory</key>
|
||||
<string>/Users/USER/keyboard/mac-agent</string>
|
||||
<key>KeepAlive</key>
|
||||
<true/>
|
||||
<key>StandardOutPath</key>
|
||||
<string>/tmp/kb-focus.stdout.log</string>
|
||||
<key>StandardErrorPath</key>
|
||||
<string>/tmp/kb-focus.stderr.log</string>
|
||||
</dict>
|
||||
</plist>
|
||||
67
mac-agent/kb-focus.py
Normal file
67
mac-agent/kb-focus.py
Normal file
@@ -0,0 +1,67 @@
|
||||
import signal, sys
|
||||
from AppKit import NSWorkspace
|
||||
from Foundation import NSRunLoop, NSDate
|
||||
import hid
|
||||
|
||||
VID, PID = 0x3384, 0x0009
|
||||
USAGE_PAGE, USAGE = 0xFF60, 0x61
|
||||
CMD_SET_FOCUSED_APP = 0x80
|
||||
|
||||
def find_keyboard_path():
|
||||
for info in hid.enumerate(VID, PID):
|
||||
if info["usage_page"] == USAGE_PAGE and info["usage"] == USAGE:
|
||||
return info["path"]
|
||||
return None
|
||||
|
||||
def send_app_name(dev, name):
|
||||
payload = name.encode("utf-8", errors="ignore")[:31]
|
||||
payload = payload.decode("utf-8", errors="ignore").encode("utf-8")
|
||||
data = bytes([0x00, CMD_SET_FOCUSED_APP]) + payload + b"\x00" * (32 - 1 - len(payload))
|
||||
dev.write(data)
|
||||
dev.read(32, timeout=1000)
|
||||
|
||||
def main():
|
||||
signal.signal(signal.SIGINT, lambda *_: sys.exit(0))
|
||||
ws = NSWorkspace.sharedWorkspace()
|
||||
dev = None
|
||||
last_app = None
|
||||
|
||||
while True:
|
||||
connected = find_keyboard_path() is not None
|
||||
|
||||
# Detect disconnect
|
||||
if dev is not None and not connected:
|
||||
print("Keyboard disconnected")
|
||||
dev = None
|
||||
last_app = None
|
||||
|
||||
# Connect and send current app
|
||||
if dev is None and connected:
|
||||
try:
|
||||
dev = hid.Device(path=find_keyboard_path())
|
||||
print("Keyboard connected")
|
||||
last_app = ws.frontmostApplication().localizedName()
|
||||
print(f"App: {last_app}")
|
||||
send_app_name(dev, last_app)
|
||||
except Exception:
|
||||
dev = None
|
||||
|
||||
# App change
|
||||
if dev is not None:
|
||||
app = ws.frontmostApplication().localizedName()
|
||||
if app != last_app:
|
||||
print(f"App: {app}")
|
||||
last_app = app
|
||||
try:
|
||||
send_app_name(dev, app)
|
||||
except Exception:
|
||||
print("Keyboard disconnected")
|
||||
dev = None
|
||||
last_app = None
|
||||
|
||||
NSRunLoop.currentRunLoop().runUntilDate_(
|
||||
NSDate.dateWithTimeIntervalSinceNow_(0.25)
|
||||
)
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
2
mac-agent/requirements.txt
Normal file
2
mac-agent/requirements.txt
Normal file
@@ -0,0 +1,2 @@
|
||||
pyobjc-framework-Cocoa
|
||||
hid
|
||||
Reference in New Issue
Block a user