所选答案很好,但在找到这个答案之前,我花了整整一晚上写自己的解决方案,所以...
以下是我过度设计的解决方案 -
SequenceRegister() {
registeredHook := 0
inputLen := 0
actions := Map()
return SequenceClosure
SequenceClosure(seq := "", ActionCb := () => true) {
if (!registeredHook) {
h := InputHook("BI")
h.KeyOpt("{All}", "N")
h.OnKeyDown := KeyDownHandler
h.Start()
registeredHook := h
}
actionKey := actions.Count
actions.Set(actionKey, Action)
Action(hook, VK, SC) {
if (SubStr(seq, 1, inputLen) = hook.Input && inputLen < StrLen(seq)) {
return
}
if (hook.Input = seq && inputLen = StrLen(seq)) {
ActionCb()
return
}
actions.delete(actionKey)
if (actions.Count = 0) {
Send("{Blind}" . Format("{{}vk{:x}sc{:x}{}}", VK, SC))
hook.Stop()
return
}
}
}
KeyDownHandler(hook, VK, SC) {
inputLen++
for key, value in actions.Clone() {
value(hook, VK, SC)
}
}
}
使用方法如下:
Capslock & s::{
CreateSequence := SequenceRegister()
CreateSequence("sleep", () => MsgBox("I sleep"))
CreateSequence("sleed", SleedCb)
SleedCb() {
MsgBox("I sleed")
}
}
这允许注册任意数量的序列,如果没有序列匹配,则重放按下的键。
请注意,此代码仅适用于AHK v2。