залил
This commit is contained in:
@@ -0,0 +1,120 @@
|
||||
package hotkey
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"runtime"
|
||||
"strings"
|
||||
"syscall"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
var (
|
||||
user32 = syscall.NewLazyDLL("user32.dll")
|
||||
procSendInput = user32.NewProc("SendInput")
|
||||
)
|
||||
|
||||
const (
|
||||
INPUT_KEYBOARD = 1
|
||||
KEYEVENTF_KEYDOWN = 0x0000
|
||||
KEYEVENTF_KEYUP = 0x0002
|
||||
)
|
||||
|
||||
type INPUT struct {
|
||||
Type uint32
|
||||
Ki KEYBDINPUT
|
||||
}
|
||||
|
||||
type KEYBDINPUT struct {
|
||||
WVirtKey uint16
|
||||
WScan uint16
|
||||
DwFlags uint32
|
||||
Time uint32
|
||||
DwExtra uint32
|
||||
}
|
||||
|
||||
// Виртуальные коды клавиш
|
||||
var keyCodes = map[string]uint16{
|
||||
"A": 0x41, "B": 0x42, "C": 0x43, "D": 0x44, "E": 0x45, "F": 0x46, "G": 0x47, "H": 0x48,
|
||||
"I": 0x49, "J": 0x4A, "K": 0x4B, "L": 0x4C, "M": 0x4D, "N": 0x4E, "O": 0x4F, "P": 0x50,
|
||||
"Q": 0x51, "R": 0x52, "S": 0x53, "T": 0x54, "U": 0x55, "V": 0x56, "W": 0x57, "X": 0x58,
|
||||
"Y": 0x59, "Z": 0x5A,
|
||||
"0": 0x30, "1": 0x31, "2": 0x32, "3": 0x33, "4": 0x34, "5": 0x35, "6": 0x36, "7": 0x37, "8": 0x38, "9": 0x39,
|
||||
"F1": 0x70, "F2": 0x71, "F3": 0x72, "F4": 0x73, "F5": 0x74, "F6": 0x75, "F7": 0x76, "F8": 0x77,
|
||||
"F9": 0x78, "F10": 0x79, "F11": 0x7A, "F12": 0x7B,
|
||||
"SPACE": 0x20, "ENTER": 0x0D, "TAB": 0x09, "ESC": 0x1B,
|
||||
"SHIFT": 0x10, "CTRL": 0x11, "ALT": 0x12, "WIN": 0x5B,
|
||||
"LEFT": 0x25, "UP": 0x26, "RIGHT": 0x27, "DOWN": 0x28,
|
||||
}
|
||||
|
||||
var modCodes = map[string]uint16{
|
||||
"ALT": 0x12,
|
||||
"CTRL": 0x11,
|
||||
"SHIFT": 0x10,
|
||||
"WIN": 0x5B,
|
||||
}
|
||||
|
||||
var enabled bool = false
|
||||
|
||||
func Init() error {
|
||||
if runtime.GOOS != "windows" {
|
||||
return fmt.Errorf("hotkey emulation only supported on Windows")
|
||||
}
|
||||
enabled = true
|
||||
return nil
|
||||
}
|
||||
|
||||
func SetEnabled(e bool) {
|
||||
enabled = e
|
||||
}
|
||||
|
||||
func PressCombination(combination string) error {
|
||||
if !enabled {
|
||||
return fmt.Errorf("hotkey emulation disabled by user")
|
||||
}
|
||||
parts := strings.Split(combination, "+")
|
||||
if len(parts) == 0 {
|
||||
return fmt.Errorf("invalid combination")
|
||||
}
|
||||
|
||||
var mods []uint16
|
||||
var mainKey uint16
|
||||
|
||||
for _, p := range parts {
|
||||
upper := strings.ToUpper(p)
|
||||
if code, ok := modCodes[upper]; ok {
|
||||
mods = append(mods, code)
|
||||
} else if code, ok := keyCodes[upper]; ok {
|
||||
mainKey = code
|
||||
} else {
|
||||
return fmt.Errorf("unknown key: %s", p)
|
||||
}
|
||||
}
|
||||
if mainKey == 0 {
|
||||
return fmt.Errorf("no main key found")
|
||||
}
|
||||
|
||||
for _, mod := range mods {
|
||||
pressKey(mod, true)
|
||||
}
|
||||
pressKey(mainKey, true)
|
||||
pressKey(mainKey, false)
|
||||
for i := len(mods) - 1; i >= 0; i-- {
|
||||
pressKey(mods[i], false)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func pressKey(vk uint16, down bool) {
|
||||
var flags uint32 = KEYEVENTF_KEYDOWN
|
||||
if !down {
|
||||
flags = KEYEVENTF_KEYUP
|
||||
}
|
||||
input := INPUT{
|
||||
Type: INPUT_KEYBOARD,
|
||||
Ki: KEYBDINPUT{
|
||||
WVirtKey: vk,
|
||||
DwFlags: flags,
|
||||
},
|
||||
}
|
||||
_, _, _ = procSendInput.Call(1, uintptr(unsafe.Pointer(&input)), unsafe.Sizeof(input))
|
||||
}
|
||||
Reference in New Issue
Block a user