太长不看
SetWindowSubClass
,然后 return DefSubclassProc(hWnd, uMsg, wParam, lParam);
,不要有 WS_CHILD
这个 Style。
缘起
翻 ControlSpy 的时候发现了 BS_GROUPBOX
Style,结合脑补觉得这是类似 Frame
的东西,安排了一个还真是。
ControlSpy 截图,无 HiDPI 支持
那么既然控件要放在 Frame 里,而 Frame 是一种 Button,那么就会存在按钮嵌套“按钮”的情况发生,所以 BS_PUSHBUTTON
应该也是可以嵌套 BS_PUSHBUTTON
的,甚至可能可以嵌套 Static
。
测试程序,开了 HiDPI 支持,所以高清一些
然后测试事件绑定的时候就发现了问题,WndProc
里面没有收到消息,然后简单翻了一下发现会传 WM_PARENTNOTIFY
,然后在 WndProc
的回调里面加上了这个 case
,的确收到了,但是根据文档来看这个东西给出的事件和信息都很有限,甚至后期测文本框的时候文本框的 CHANGE
事件都收不到,所以就锅++了。
Day 1
搜了一个小时,并没有搜出来什么东西,于是就去 StackOverflow 上面问了。当时问的时候给的图是按钮套按钮的,看上去很怪异,而且并不会有人去这样用控件,而且可能描述上也存在一些问题,导致评论区负面评价比较多,也没获得啥有用信息。
当时查了挺多的东西,翻这些网页流量都 300 多 M(宽带),可见有多猛。。看了许多相关不相关的东西,啥 MFC 的、GetMenu
什么的都有看过,虽然开的时候就知道这种东西不太相关但是还是看了看。
因为前一天太猛,第二天累到爆炸,咕了一天。
Day 3
首先是简单整理了一下原来建 TextBox
的代码,然后依然是从 WM_PARENTNOTIFY
开始找起,看到了 WM_NOTIFY
,然后了解了一下 Windows 的消息流程,随着引导看到了 SendAsyncProc
,但是对解决问题都没啥用,又抱有一丝希望。花了一段时间去研究为啥收不到 WM_NOTIFY
,没啥发现,最后也没收得到,然后看到了 MFC 相关的一些东西,发现这么方便,有一点酸,但是项目架构原因只能用原生。
最后,在这里 Child windows does not receive WM_DESTROY?,看到了真正的答案。既然涉及到了 Child Windows,要手动收到 WM_DESTROY
就说明题主想要在 Destroy 时额外做点什么,而如果能解决,就必定有遍历发消息什么的。其实之前看到了一个提问,只是下面没回答。然后就说到了 SetWindowSubClass
,顺理成章地看文档,发现就是要的这个,然后放上去。
放上去之后 F5 开幕雷击,整个窗口算是全白的,之前在新的回调里就是直接调的旧的回调,然后折腾了一下试了几种方案都不行,回去看代码发现在构造的时候 or 了 WS_CHILD
,然后既然 SetWindowSubClass
了,就不像是一个 Child,注释掉就好了。
用了这个以后之前注册控件类回调挂掉,错误的注册方法没啥问题的注册函数可以不用要了。