头些天弄一个锁定的窗口,搞不定,来论坛得到了帮助。这些天我又加了些功能,这个无边框窗口不仅可以随意的拖动,还可以随意的拉伸。当然这对于高手和行家来说,实在不算什么。可自已在做的过程中,还是经历了多次的失败。虽说网络很方便,可是很多介绍却是含糊而简略的。这里我将这个做出的代码贴出来与大家分享,说不准能够帮到一些人。
发送$HTCAPTION指令移动窗体后,窗体大小就无法伸缩了。网上有很多方法,AU3的却很少。而那些方法,要么含糊不清,要么云山雾罩,贴来贴来,未经验实的居多。令我等凡人,头疼不已。试想微软也提供消息接口参数,让大家可以利用。而这么一个简单的功能,却没人提供现成的代码,对于这些,高手们完全可以无偿提供代码及注解,让后学者不至于做无谓的付出。
窗体不能伸缩后,通过做窗体移动,发送$HTCAPTION消息的经验,想到,也许可以通过向系统发送某个消息来使窗体伸缩。就去查,但只查WM_NCHITTEST。又到网上查,看了许多别人各式各样的代码,总算知道了HTBOTTOMRIGHT这几个指令。然后摸索着在AU3中写。想到一定还有一样的朋友在找这样的代码,所以干脆贴出来,方便大家直接使用,各取所需。#include <GUIConstantsEx.au3>
#include <StaticConstants.au3>
#include <WindowsConstants.au3>
#include <Misc.au3>
$Form1 = GUICreate("无边框窗体移动拉伸", 600, 400, 200, 100, BitOR($WS_POPUP,$WS_CLIPSIBLINGS))
$Button1 = GUICtrlCreateButton("退出", 250, 300, 75, 25, 0)
GUISetState(@SW_SHOW)
GUIRegisterMsg($WM_NCHITTEST, "topbottom")
While 1
$nMsg = GUIGetMsg()
Switch $nMsg
Case $GUI_EVENT_CLOSE
Exit
Case $Button1
Exit
EndSwitch
WEnd
Func topbottom($hWnd, $iMsg, $iwParam, $ilParam)
$MousePos = MouseGetPos()
$nPos = WinGetPos("")
$DT = ($hWnd = $Form1 and $iMsg = $WM_NCHITTEST)
$DDx = ($MousePos[0] < $nPos[0]+ $nPos[2]- 8) and ($MousePos[0] > $nPos[0]+ 8)
$DDy = ($MousePos[1] < $nPos[1]+ $nPos[3]- 8) and ($MousePos[1] > $nPos[1]+ 8)
; 以上是无边框窗体移动事件的发生条件
$S1x = ($MousePos[0] >= $nPos[0]+ $nPos[2]- 8) ; 右下角x
$S1y = ($MousePos[1] >= $nPos[1]+ $nPos[3]- 8) ; 右下角y
$S2x = ($MousePos[0] <= $nPos[0]+ 8) ; 左上角x
$S2y = ($MousePos[1] <= $nPos[1]+ 8) ; 左上角y
$S3x = ($MousePos[0] <= $nPos[0]+8) ; 左下角x
$S3y = ($MousePos[1] >= $nPos[1]+ $nPos[3]- 8) ; 左下角y
$S4x = ($MousePos[0] >= $nPos[0]+ $nPos[2]- 8) ; 右上角x
$S4y = ($MousePos[1] <= $nPos[1]+ 8) ; 右上角y
;以上是四角拉伸事件的发生条件
$S5 = ($MousePos[0] <= $nPos[0]+ 8) ; 左边
$S6 = ($MousePos[1] <= $nPos[1]+ 8) ; 顶边
$S7 = ($MousePos[0] >= $nPos[0] + $nPos[2]- 8) ; 右边
$S8 = ($MousePos[1] >= $nPos[1] + $nPos[3]- 8) ; 底边
;以上是四边拉伸事件的发生条件
If $DT and $DDx and $DDy then Return $HTCAPTION ;移动
If $S1x and $S1y Then Return $HTBOTTOMRIGHT ;右下角拉伸
If $S2x and $S2y Then Return $HTTOPLEFT ;左上角拉伸
If $S3x and $S3y Then Return $HTBOTTOMLEFT ;左下角拉伸
If $S4x and $S4y Then Return $HTTOPRIGHT ;右上角拉伸
If $S5 Then Return $HTLEFT ;左边拉伸
If $S6 Then Return $HTTOP ;上边拉伸
If $S7 Then Return $HTRIGHT ;右边拉伸
If $S8 Then Return $HTBOTTOM ;下边拉伸
EndFunc
代码的思路:
无边框窗体的移动,利用GUIRegisterMsg 注册的自定义函数向系统发送 HTCAPTION 指令,使窗体的非客户区与标题栏客户区一样移动。达到窗口移动的目的。但发送$HTCAPTION指令后,窗体大小无法伸缩了。但是正常情况下,鼠标在窗体边缘是可以拉伸窗体的,这证明,鼠标移动到窗体边缘附近时,会发送某个消息指令给系统,系统接收后,便允许鼠标拉伸。这个消息就是WM_NCHITTEST。其实这个消息与移动时发送的消息是一致的,只不过具体指令不一样而已。而鼠标具体在窗体边缘的哪一个方位将会发出对应的不同的指令。这就是代码中的八个指令$HTBOTTOMRIGHT,$HTTOPLEFT,$HTBOTTOMLEFT,$HTTOPRIGHT,$HTLEFT,$HTTOP,$HTRIGHT,$HTBOTTOM。只要定义好这8个指令的触发条件就可以了。基本思路就这样。
条件判断写的时候费点时间,测试了好多次,因为不是经常写代码的人。不过写好了就没必要都再写一次了。也不想看第二次。
不认为让每一个人都来折腾一番是一种好的锻炼方法。个人认为,对于普及者爱好者来说,引用与操作是更重要的,很多事见多了,做多了,自然也就有了经验与思路。 |