ControlSend / ControlSendRaw

发送模拟键击到窗口或控件.

ControlSend, Control, Keys , WinTitle, WinText, ExcludeTitle, ExcludeText
ControlSendRaw, Control, Keys , WinTitle, WinText, ExcludeTitle, ExcludeText

参数

Control

如果为空或省略, 则使用目标窗口的顶层控件. 否则, 请指定 ClassNN(控件的类名和实例编号) 或控件的文本, 它们都可以通过 Window Spy 获取. 使用文本时, 匹配行为由 SetTitleMatchMode 决定. 如果此参数为 ahk_parent, 则直接发送键击到目标窗口而非其中的某个控件(请参阅自动化 Winamp 中的例子).

要对控件的 HWND(窗口句柄) 进行操作, 请将 Control 参数留空同时在 WinTitle 参数中指定 ahk_id %ControlHwnd%(即使在 DetectHiddenWindows 设置关闭时, 这样也可以操作隐藏控件). 获取控件的 HWND 的一般方法是使用 ControlGet Hwnd, MouseGetPosDllCall().

Keys

要发送的按键序列(请参阅 Send 命令了解详情). 要发送原义的逗号, 需要对它进行转义(`,). 发送字符的速率由 SetKeyDelay 决定.

Send 命令不同, ControlSend 不能发送鼠标点击. 请用 ControlClick 发送.

WinTitle, WinText, ExcludeTitle, ExcludeText

如果这些都是空白或省略, 将使用上次找到的窗口. 否则, 为 WinTitle 指定窗口标题或其他条件, 来标识目标窗口, 和/或为 WinText 指定目标窗口的单个文本元素的子字符串(由包含的 Window Spy 实用程序显示).

ExcludeTitleExcludeText 可用于根据标题或文本排除一个或多个窗口. 它们的规范类似于 WinTitleWinText, 除了 ExcludeTitle 不识别除窗口标题之外的任何条件.

窗口标题和文本是区分大小写的. 默认情况下, 不检测隐藏窗口, 而检测隐藏文本元素, 除非使用 DetectHiddenWindowsDetectHiddenText 进行更改. 默认情况下, 窗口标题必须以指定的 WinTitleExcludeTitle 开头才能匹配, 除非使用 SetTitleMatchMode 进行更改.

错误处理

[v1.1.04+]: 此命令失败时会抛出异常. 想了解更多信息, 请参阅运行时错误.

如果遇到问题则 ErrorLevel 被置为 1, 否则为 0.

备注

ControlSendRaw 会准确地按照原样发送 Keys 参数中的按键, 而不把 {Enter} 转换成 Enter, 把 ^c 转换成 Ctrl+C, 等等. 有关详细信息, 请参阅原始模式. 在 ControlSend 中, 使用 {Raw}{Text} 也是有效的. [v1.1.27+]: 文本模式可能更可靠的发送文本.

如果省略 Control 参数, 那么此命令会尝试直接发送到目标窗口的顶层控件(一般这个是正确的), 当目标窗口没有控件时则发送到窗口自身. 这可以用在窗口还不含有任何控件或无所谓发送给哪个控件的时候.

默认情况下, 修饰符键击(Ctrl, Alt, Shift 和 Win) 的发送方法和在 Send 命令一般模式下发送相同. 这样可以让命令提示符和其他控制台窗口正确检测到大写字母, 控制字符, 等等. 这样也提供了其他方面的可靠性.

然而, 在某些情况下这些修饰符事件可能和活动窗口发生冲突, 尤其是在 ControlSend 发送期间或正发送 Alt 的时候用户正在输入(因为 Alt 会激活活动窗口的菜单栏). 通过显式地发送修饰键的按下和弹起事件可以避免此问题, 例如:

ControlSend, Edit1, {Alt down}f{Alt up}, Untitled - Notepad

上面的方法还可以在工作站被锁定(被登录提示保护) 时发送修饰符键击(Ctrl, Alt, Shift 和 Win).

使用 ControlSend 发送键击到控制台窗口(例如命令提示符) 时, 应该避免使用 BlockInput. 因为它可能让大写字符和修饰符按键例如 Ctrl 工作不正常.

SetKeyDelay 的值决定了发送按键的速度. 如果目标窗口无法可靠地接收到键击, 请尝试在 SetKeyDelay 的第二个参数中增加按键时长, 例如:

SetKeyDelay, 10, 10
SetKeyDelay, 0, 10
SetKeyDelay, -1, 0

如果目标控件是 Edit 控件(或类似的控件), 则使用下列方法通常比 ControlSend 更可靠和快速:

Control, EditPaste, This text will be inserted at the caret position., ControlName, WinTitle
ControlSetText, ControlName, This text will entirely replace any current text., WinTitle

ControlSend 通常不能很好的操作窗口的菜单栏. 要变通解决此问题, 请使用 WinMenuSelectItem. 如果由于菜单栏的性质而操作失败, 那么您可以参照发送消息指南来尝试找到想要选择的菜单的对应消息.

SetKeyDelay, 转义序列(如 `%), Control, ControlGet, ControlGetText, ControlMove, ControlGetPos, ControlClick, ControlSetText, ControlFocus, Send, 自动化 Winamp

示例

打开记事本(最小化的) 并发送一些文本. 这个例子在 Windows 11 或更高版本系统可能会失败, 因为它需要经典版本的记事本.

Run, Notepad,, Min, PID  ; 最小化运行记事本.
WinWait, ahk_pid %PID%  ; 等待记事本进程的出现.
; 将文本发送到不活动的记事本编辑控件.
; 省略了第三个参数, 因此使用最后一个找到的窗口.
ControlSend, Edit1, This is a line of text in the notepad window.{Enter}
ControlSendRaw, Edit1, Notice that {Enter} is not sent as an Enter keystroke with ControlSendRaw.

MsgBox, Press OK to activate the window to see the result.
WinActivate, ahk_pid %PID%  ; 显示结果.

打开命令提示符并向它发送一些文本.

SetTitleMatchMode, 2
Run, %A_ComSpec%,,, PID  ; 打开命令提示符.
WinWait, ahk_pid %PID%  ; 等待它的出现.
ControlSend,, ipconfig{Enter}, cmd.exe  ; 直接发送到命令提示符窗口.

创建一个带有编辑控件的 GUI, 并向它发送一些文本.

Gui, Add, Edit, r10 w500
Gui, Show
Gui, +LastFound
; 省略第三个参数, 以便使用最后找到的窗口.
ControlSend, Edit1, This is a line of text in the edit control.{Enter}
ControlSendRaw, Edit1, Notice that {Enter} is not sent as an Enter keystroke with ControlSendRaw.