编辑

编辑

我有一台 Windows 10 笔记本电脑,它的键盘是由白痴设计的。他们试图将箭头键塞进不该放的地方,结果这个up arrow之间right shift/键(美国键盘布局)。这是设计师可能做过的最愚蠢的事情之一,因为这意味着当我要按右 Shift 键时(大多数情况下都是这样),我最终会按错up arrow。这非常烦人。

我找到了一个名为锐键这样我就可以重新映射按键,使up arrow充当 shift 键, 充当right shiftup arrow现在,至少我可以打字了。但是,我现在失去了up arrow键的重要功能。向上箭头(现在标记为“转移”在我的键盘上)不会重复。因此,我不能只按住该键来向上移动。相反,我必须反复按下该键。我该如何解决这个问题,以便我的右移键表现为向上箭头,而我的向上箭头键表现为right shift

编辑

根据评论的建议,我安装了 AutoHotkey。我有以下脚本:

RShift::Up
Up::RShift

我遇到了与之前相同的问题。但是,由于 AHK 是一种脚本语言,是否可以使用它来更改重复行为?

答案1

我尝试了您列出的热键...它们对我来说效果很好,按住时会自动重复...

#Persistent
Return

#IfWinActive    ; Make replacement operate globally
RShift::Up
Up::RShift

您或许可以尝试不同的SendMode...

RShift::SendInput {Up}
Up::SendInput {RShift}

或者...

RShift::SendPlay {Up}
Up::SendPlay {RShift}

您是否有其他程序可以拦截这些或类似的东西?脚本未运行时,按键重复功能是否正常工作?

设置自定义循环可能看起来像这样......

RShift::
    While GetKeyState("RShift", "P") {
        Send {Up}
        Sleep 50    ; Set delay to taste
    }
Return

编辑

为了满足其他修饰符的工作需求,可以将“*”与热键一起使用,尽管在有两个 Shift 键的情况下,默认情况下它可能无法正常工作。我为 Shift 键检测添加了一个特殊情况,但我不知道如果您将其他修饰符混入其中,它会如何工作……在这种情况下,您可以考虑将修饰符添加{blind}到语句中Send,看看是否可以使其正常工作。

为了解决“竞争条件”,还可以在重复循环之前添加另一个预重复延迟以及初始发送语句(见下文)。

*Up::SendInput {blind}{RShift Down}
*Up Up::SendInput {blind}{RShift Up}

*RShift::
    Send % GetKeyState("LShift", "P") ? "+{Up}" : "{Up}"
    Sleep 250           ; Initial delay before repeat
    While GetKeyState("RShift", "P") {
        Send % GetKeyState("LShift", "P") ? "+{Up}" : "{Up}"
        Sleep 100    ; Repeat delay
    }
Return

答案2

所有其他答案的问题在于,重复shift按下将被忽略,因为前一个热键子程序仍在执行。默认情况下,#MaxThreadsPerHotkey为 1,并且#最大线程数是 10。

以下是两种可能的解决方案。对我来说,两种方法都很有效。

增加#MaxThreadsPerHotkey (和#MaxThreads)

SendMode Input
#MaxThreads 150
#MaxThreadsPerHotkey 150

; return the send command including any pressed modifier keys
getSendCommand() {
    sendCmd = {Up}
    sendCmd = % GetKeyState("LAlt", "P") ? "!" . sendCmd : sendCmd
    sendCmd = % GetKeyState("LCtrl", "P") ? "^" . sendCmd : sendCmd
    sendCmd = % GetKeyState("LShift", "P") ? "+" . sendCmd : sendCmd
    sendCmd = % GetKeyState("Win", "P") ? "#" . sendCmd : sendCmd
    return sendCmd
}

*$RShift::
    ; Immediately send an up key
    Send % getSendCommand()
    Sleep, 450

    While GetKeyState("RShift", "P") {  ; while key remains pressed
        Send % getSendCommand()  ; keep sending up keys
        Sleep, 30
    }
    Return

shift释放按键时立即中止执行

SendMode Input

; return the send command including any pressed modifier keys
getSendCommand() {
    sendCmd = {Up}
    sendCmd = % GetKeyState("LAlt", "P") ? "!" . sendCmd : sendCmd
    sendCmd = % GetKeyState("LCtrl", "P") ? "^" . sendCmd : sendCmd
    sendCmd = % GetKeyState("LShift", "P") ? "+" . sendCmd : sendCmd
    sendCmd = % GetKeyState("Win", "P") ? "#" . sendCmd : sendCmd
    return sendCmd
}

*$RShift::
    ; Immediately send an up key
    Send % getSendCommand()

    ; Initial wait period (sleep time = 350 ms, execution time ~450 ms)
    Loop 35 {  ; Check keystate every 10 ms, abort execution as soon as shift is released
        Sleep, 10  ; 10 ms is the shortest possible sleep interval
        if not GetKeyState("RShift", "P") {
            return
        }
    }

    ; Start repeating if and while key is still pressed. Stop execution as soon as shift is released
    While GetKeyState("RShift", "P") {
        Send % getSendCommand()

        Loop 2 {
            if not GetKeyState("RShift", "P") {
                return
            }
            Sleep, 10
        }
    }
    Return

答案3

虽然 JJohnston2 的回答给了我部分解决方案,但我最终还是询问了其他几个地方,并自己做了很多实验。以下是我最终得到的结果:

Up::RShift
*RShift::
    delay=400
    While GetKeyState("RShift", "P") {
        Send {Blind}{Up}
        Sleep %delay%    ; Set delay to taste
        delay=30
    }
    Return

这解决了按键重复和允许 shift+up 按预期工作的问题。有两个未解决的问题我还没有解决,但它们的优先级足够低,所以我无论如何都会认为这个问题已经解决了:

  1. 竞争条件尚未解决。我尝试将第一次迭代放在循环之外,就像 JJohnston2 所做的那样,但对我来说没有明显的效果。
  2. 所有这些麻烦的根本原因是系统似乎不会重复 Shift、Ctrl 或 Alt 键,即使其他键会重复。因此,AHK 无法重复它从未见过的内容。由于我寻求帮助的每个人都没有遇到过这个问题,所以我的设置一定有问题,但我完全不知道那可能是什么。

相关内容