注册 登录
编程论坛 VFP论坛

请问如何用VFP代码实现模拟ctrl+Win的按键动作?

jlliushi 发布于 2021-12-30 09:19, 2398 次点击
请问如何用VFP代码实现模拟ctrl+Win的按键动作?
10 回复
#2
laowan0012021-12-30 09:25
MESSAGEBOX( INKEY(0))返回一个按键的值
ctrl+Win好像不是一个有值的按键,就象单独按ctrl或shift一样
#3
吹水佬2021-12-30 10:09
观察 WM_KEYDOWN、WM_KEYUP、WM_SYSKEYDOWN 和 WM_SYSKEYUP 消息
WM_KEYDOWN      equ 100h
WM_KEYUP        equ 101h
WM_SYSKEYDOWN   equ 104h
WM_SYSKEYUP     equ 105h
虚拟键码保存在wParam参数
程序代码:
of = CREATEOBJECT("form1")
of.show(1)

DEFINE CLASS form1 as Form
    ADD OBJECT edit1 as editbox WITH left=10,top=10,width=300,height=200
    PROCEDURE init
        BINDEVENT(this.hWnd, 0x100, this, "myKeyDown")
        BINDEVENT(this.hWnd, 0x101, this, "myKeyUp")
        BINDEVENT(this.hWnd, 0x104, this, "mySysKeyDown")
        BINDEVENT(this.hWnd, 0x105, this, "mySysKeyUp")
    ENDPROC
    PROCEDURE myKeyDown(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "KeyDown " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC
    PROCEDURE myKeyUp(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "KeyUp " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC     
    PROCEDURE mySysKeyDown(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "SysKeyDown " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC
    PROCEDURE mySysKeyUp(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "SysKeyUp " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC   
ENDDEFINE
#4
schtg2021-12-30 11:04
回复 3楼 吹水佬
学习啦,谢谢!
#5
jlliushi2021-12-30 12:08
回复 3楼 吹水佬
如何用VFP代码实现模拟ctrl+Win的按键动作?

快捷键Ctrl+Win是用来实现“Windows语音识别聆听模式”和“正在休眠”模式的切换的

[此贴子已经被作者于2021-12-30 12:10编辑过]

#6
吹水佬2021-12-30 19:29
以下是引用jlliushi在2021-12-30 12:08:22的发言:

如何用VFP代码实现模拟ctrl+Win的按键动作?

快捷键Ctrl+Win是用来实现“Windows语音识别聆听模式”和“正在休眠”模式的切换的

试试
程序代码:
DECLARE Long keybd_event IN user32 long,long,long,long
#define KEYEVENTF_KEYUP  2
#define VK_CONTROL       0x11
#define VK_LWIN          0x5B
#define VK_E             0x45
      
of = CREATEOBJECT("form1")
of.show(1)

DEFINE CLASS form1 as Form
    ADD OBJECT cmd1 as commandbutton with left=10,top=10,width=100,height=22,caption="Ctrl+Win"
    ADD OBJECT cmd2 as commandbutton with left=120,top=10,width=100,height=22,caption="Win+E"
    ADD OBJECT edit1 as editbox WITH left=10,top=40,width=300,height=200
    PROCEDURE init
        BINDEVENT(this.hWnd, 0x100, this, "myKeyDown")
        BINDEVENT(this.hWnd, 0x101, this, "myKeyUp")
        BINDEVENT(this.hWnd, 0x104, this, "mySysKeyDown")
        BINDEVENT(this.hWnd, 0x105, this, "mySysKeyUp")
    ENDPROC
    PROCEDURE myKeyDown(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "KeyDown " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC
    PROCEDURE myKeyUp(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "KeyUp " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC     
    PROCEDURE mySysKeyDown(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "SysKeyDown " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC
    PROCEDURE mySysKeyUp(hWnd, Msg, wParam, lParam)
        this.edit1.SelText = "SysKeyUp " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A
    ENDPROC
    PROCEDURE cmd1.click   
        Keybd2(VK_CONTROL, VK_LWIN)    && Ctrl+Win
    ENDPROC
    PROCEDURE cmd2.click
        Keybd2(VK_LWIN, VK_E)    && Win+E 打开资源管理器
    ENDPROC
ENDDEFINE

FUNCTION Keybd2(vk1, vk2)
    keybd_event(vk1, 0, 0, 0)
    keybd_event(vk2, 0, 0, 0)
    keybd_event(vk2, 0, KEYEVENTF_KEYUP, 0)
    keybd_event(vk1, 0, KEYEVENTF_KEYUP, 0)
ENDFUNC
#7
cssnet2021-12-30 21:18
以下是引用吹水佬在2021-12-30 19:29:45的发言:
        this.edit1.SelText = "KeyDown " + TRANSFORM(wParam,"@0") + ", " + TRANSFORM(lParam,"@0") + 0h0D0A


忍不住赞叹一下,擦一下吹水佬版主的鞋:
阅读吹水佬的代码,真的是一种视觉享受:
简洁、优雅,一语中的,无任何啰嗦废话!

PS:可怜我写了半辈子代码,竟然从没想过可以用“ + 0h0D0A”来取代“ + chr(0x0D) + chr(0x0A)”。
呵呵,水平层次的差别,高下立判!
#8
jlliushi2022-01-03 18:26
回复 6楼 吹水佬
这个模拟按键的代码在VFP环境内都好使,但经过编译后就不起作用了,是什么原因?怎么办?
#9
吹水佬2022-01-03 21:01
以下是引用jlliushi在2022-1-3 18:26:39的发言:

这个模拟按键的代码在VFP环境内都好使,但经过编译后就不起作用了,是什么原因?怎么办?

不清楚你的代码
#10
jlliushi2022-01-04 05:36
回复 9楼 吹水佬
     DECLARE Long keybd_event IN user32 long,long,long,long
    keybd_event(0x11, 0, 0, 0)
    keybd_event(0x5B, 0, 0, 0)
    keybd_event(0x5B, 0, 2, 0)
    keybd_event(0x11, 0, 2, 0)
以上代码在未编译前能够模拟按下Ctrl+Win实现切换语音键入的聆听和关闭模式,
但一经编译后就不好使了(Win7和Win11都不好使)。

还有我另一个贴是说模拟鼠标点击的也是为了实现模拟点击(按下Ctrl+Win实现切换语音键入的聆听和关闭模式的)那个按钮,
这个是在Win7下好使,在Win10和Win11下都不好使,都是在未编译情况下测试的。

我现在要做的是用语音控制某些功能。 需要频繁模拟切换Ctrl+Win来关闭和开启麦克风。
或者是能模拟用鼠标点击那个按钮也行(不如模拟按键好), 但现在这两种方法都有问题。
希望吹版主能够帮我找到解决办法。谢谢!

只有本站会员才能查看附件,请 登录


[此贴子已经被作者于2022-1-4 05:47编辑过]

#11
吹水佬2022-01-04 08:50
模拟其他热键有无效? 如 Win+E
如果全部热键都无效就无效了
试试将表单设为顶层表单 ShowWindow=2 ,或相对在桌面 Desktop = .T.
1