ControlSend 使用SetKeyDelay, 0, 0 时随机发送错误字符(修改和未修改) [英] ControlSend randomly sending wrong characters (modified and unmodified) when using SetKeyDelay, 0, 0

查看:24
本文介绍了ControlSend 使用SetKeyDelay, 0, 0 时随机发送错误字符(修改和未修改)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我自己回答了这个问题,因为我在互联网上看到过这个问题,但几乎没有有用的答案,而且我绝对找不到关于 Stack Overflow 的解决方案.

I'm self-answering this question because I've seen it asked all over the Internet, but with few helpful answers, and definitely no resolutions on Stack Overflow that I can find.

考虑这段代码,它只写了几行 shell 命令:

Consider this code, which simply writes several lines of shell commands:

^0::
    SetKeyDelay, 0, 0
    myWindow = ahk_exe Notepad.exe
    ControlSend, , set c=".cshrc-andrew.cheong"`n, %myWindow%
    ControlSend, , set v=".vimrc-andrew.cheong"`n, %myWindow%
    ControlSend, , foreach d ( /userhome/andrew.cheong /home/$USER /data/$USER )`n, %myWindow%
    ControlSend, , if ( -e $d/$c ) source $d/$c`n, %myWindow%
    ControlSend, , if ( -e $d/$v ) alias vim "vim -N -u $d/$v"`n, %myWindow%
    ControlSend, , end`n, %myWindow%
    Return

我正在将命令写入记事本,以表明它不是仅限于 PuTTy 或 xterm 等终端应用程序的问题.这么想很容易,因为这些应用程序有时会出现滞后行为.

I'm writing the commands to Notepad to show that it is not an issue limited to terminal applications like PuTTy or xterm. It's easy to think so, since these applications sometimes have laggy behavior.

特别是当使用 SetKeyDelay, 0, 0 进行快速打字"时,我会遇到各种奇怪的行为,例如:

Specifically when using SetKeyDelay, 0, 0 for fast "typing," I get all kinds of weird behavior, like:

  • 双引号替换为单引号.括号由 9 和 0 代替.美元符号被 4 代替.

  • Double-quotes replaced by single-quotes. Parentheses replaced by 9's and 0's. Dollar signs replaced by 4's.

set c=".cshrc-andrew.cheong'
set v=".vimrc-andrew.cheong"
foreach d ( /userhome/andrew.cheong /home/$USER /data/$USER )
if 9 -e 4d/4c 0 source 4d/4c
if ( -e $d/$v ) alias vim 'vim -n -u 4d/4v'
end

  • 破折号被下划线代替.案例更改.

  • Dashes replaced by underscores. Case changes.

    set c='.cshrc-andrew.cheong"
    set v='.vimrc-andrew.cheong'
    foreach d ( /userhome/andrew.cheong /home/4user /data/$USER )
    if 9 -e 4d/$C ) source 4d/$c
    if 9 _e $d/$v ) alias vim 'vim -N -u $d/$v"
    end
    

  • 句号被>代替.更多案例变化.

  • Periods replaced by >'s. More case changes.

    set c=".cshrc-andrew.cheong"
    set v=">VIMrc-andrew.cheong"
    foreach d ( /userhome/andrew.cheong /home/$USER /data/$USER )
    if 9 -e $d/$c ) source 4d/$c
    if ( -e $d/$V ) alias vim "vim -N -u $d/$v"
    end
    

  • 很明显,这个问题与 Shift 修饰符有关,就像它被随机打开或关闭一样.

    It's obvious the issue has something to do with the Shift modifier, as if it's being randomly turned on or off.

    为什么会发生这种情况,我们该如何解决?

    请注意,使用 Send 及其变体时没有问题.该问题特别出现在 ControlSend 中,需要将输入发送到特定控件或未聚焦的窗口.

    Note that there are no problems when using Send and its variants. The issue specifically arises with ControlSend, which is needed to send inputs to specific controls or to an unfocused window.

    推荐答案

    解决方案

    将其复制到您的脚本中(来自 AutoHotkey 论坛上的用户 RHCP):

    Solution

    Copy this into your script (from user RHCP at AutoHotkey forums):

    pSendChars(string, control := "", WinTitle := "", WinText := "", ExcludeTitle := "", ExcludeText := "")
    {
        for k, char in StrSplit(string)
            postmessage, WM_CHAR := 0x102, Asc(char),, %Control%, %WinTitle%, %WinText%, %ExcludeTitle%, %ExcludeText%
        return
    }
    

    并像这样使用它:

    ^0::
        myWindow = ahk_exe Notepad.exe
        line .= "set c="".cshrc-acheong""`n"
        line .= "set v="".vimrc-acheong""`n"
        line .= "foreach d ( /userhome/andrew.cheong /home/cama /home/$USER )`n"
        line .= "    if ( -e $d/$c ) source $d/$c`n"
        line .= "    if ( -e $d/$v ) alias vim ""vim -N -u $d/$v""`n"
        line .= "end`n"
        pSendChars(line, "edit1", myWindow)
        Return
    

    就是这样.

    请注意,edit1 是记事本的文本控件名称.将此脚本用于 PuTTy 时,我将其更改为空白字符串.使用 AutoHotkey 的 WindowSpy 程序找出您希望写入的控件.

    Note that edit1 is Notepad's name for its text control. When using this script for PuTTy, I changed it to a blank string. Use AutoHotkey's WindowSpy program to find out the control you wish to write to.

    这种情况以前出现过几次.只是为了补充什么 Lexikos写道,问题是由于 controlSend 使用两个帖子message 和 sendInput/sendEvent 发送击键.这是必需的因为某些程序不会正确解释击键,除非发送的修饰键在逻辑上是向下的(通过 sendInput/Event 发送).

    This has come up a few times before. Just to add to what Lexikos wrote, the issue is due to the fact that controlSend uses both post message and sendInput/sendEvent to send keystrokes. This is required as some programs will not correctly interpret the keystrokes unless the sent modifier keys are logically down (sent via sendInput/Event).

    修改键(除非明确说明,例如{shitft down})被发送通过 sendInput 而非修饰符通过 postMessage 发送.密钥已发送通过 postmessage 直接发送到窗口,因此延迟更少比其他键/消息.因此,按键是可能的消息到达不同步导致意外字符.在您的情况下,大写字母需要通过发送 shift 键发送输入/事件.

    Modifier keys (unless explicitly stated e.g. {shitft down}) are sent via sendInput while non-modifers are sent via postMessage. Keys sent via postmessage are sent directly to the window and so have less delay than the other keys/messages. Consequently it's possible for keystroke messages to arrive out of synch resulting in unexpected characters. In your case the capitalised letters require the shift key to be sent via sendInput/Event.

    除了使用keyDelays,还可以试试controlSetText和postingWM_Char 消息.如果您正在使用文本控件,我会推荐使用 controlSetText.

    In addition to using keyDelays, you can try controlSetText and posting WM_Char messages. If you're working with a text control i would recommend using controlSetText.

    - RHCP 2013 年 9 月 30 日

    这篇关于ControlSend 使用SetKeyDelay, 0, 0 时随机发送错误字符(修改和未修改)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆