快捷键

快捷键分成两种,一种是窗口快捷键,一种是全局快捷键。

窗口快捷键是在窗口窗口之后,在窗口被选中的时候,按下才有用处。全局快捷键是通过 user32 注册在系统里面的,在任何位置按下都可以使用。

因为window 的窗口设计十分复杂,从标题栏,侧边栏到应用本体,都需要调用函数,现有的开发框架都对这一现象进行了整合,以 WPF 举例。

WPF 中的Window ,并不是原生的API 窗口,而是采取了一种很取巧的方式,每建立一个窗口,都会创建一个隐藏的原生API 指针,对外的形式Window ,可以用HwndSource.FromHwnd ,找到这个窗口的原始指针。另外在WPF 中的对象可以是先创立然后在初始化的。

窗口快捷键

在窗口没有被初始化之前,原生的指针会是空指针,会报错。

在窗口初始化完成时之后,只需要在窗口层面上,写一个检测,检测窗口中按下了什么案件,然后触发即可。

全局快捷键

全局快捷键,我用的最多的就是QQ 的截屏,和注册在系统中快捷键。因为全局快捷键采用的是占坑制,只要被占用,后来的就注册不进去,因此QQ 微信都安装的话,微信的快捷键通常是不能用(电脑版的微信做的很克制,功能很少)

添加的话,只需要把修改符和按键 注册在里面即可。

此时,当按键被按下时,会触发一个消息通知事件,根据注册的窗口和id,触发消息WM_HOTKEY ,然后msg 就是这个id ,可以根据这个id ,执行对应的命令即可。

扩展

设立一个快捷键是一个比较简单的事情,不管是窗口还是全局快捷键。

如果我需要同时注册很多个快捷键呢?我可以通过建立一个Map 类似的东西,把已经注册的值放在Map 里面,然后就可以通过查询map,实现对应的功能。

由此可以延申出两种功能的写法,一种是工具式,可以自己添加并定制快捷键的功能情况。一种是便捷式,在功能已定的情况下,对快捷键的具体键位,进行控制和修正。

也就是在我们需要对这个模块进行第三次的封装。

第一层的封装,就是原始的 user32.dll 的调用方式,通常是通过指针和int 类型的数据进行的。

第二层的封装,是我们需要建立一个窗口和事件的对照表,注册一个事件,就要把字典添加一个,注销的时候删除这个事件。并在在原生窗体上AddHook 一个监听事件,让处理对应的方式的时候可以找到这个id ,并通过委托的方式让对应的事件执行。

第三层的封装就是选择性的,我是否需要建立一个功能表,和对照的存储的按键表。在窗口建立的时候,按照这个表个注册控件。并且可以接触和新建对应的空间表。

如果这么写的话,这个类面应该分成 全局和窗体两种类型,并且,里面的功能也应该是可以自动添加,并取消的。

根据所有的需求层次,适当的修改代码的复杂度。

如果是特定软件,可以直接从第一层之后,直接在监听的时候,把需要的功能写进去。如果是封装层次,封装第二层之后,的可用性会大大提高。