WM_MOVING
WM_CREATE
WM_TIMER
然后来到对应的cpp文件,在头部定义一些宏:
//收缩模式 #define HM_NONE0//不收缩
#define HM_TOP1//向上收缩
#define HM_BOTTOM2//向下收缩
#define HM_LEFT3//向左收缩
#define HM_RIGHT4//向右收缩
#define CM_ELAPSE200 //检测鼠标是否离开窗口的时间间隔
#define HS_ELAPSE5//伸缩过程每步的时间间隔
#define HS_STEPS10//伸缩过程分成多少步完成
#define INTERVAL20//触发粘附时鼠标与屏幕边界的最小间隔,单位为象素
#define INFALTE10//触发收缩时鼠标与窗口边界的最小间隔,单位为象素
逆@风@者 然后在构造函数初始化成员变量:
m_isSizeChanged = FALSE;
m_isSetTimer = FALSE; m_hsFinished = TRUE;
m_hiding = FALSE; m_oldWndHeight = MINCY;
m_taskBarHeight = 30;
m_edgeHeight = 0;
m_edgeWidth=0;
m_hideMode = HM_NONE;
完成了一些初始的工作,那么就开始进入关键的函数实现了。首先是在OnCreate做些窗口的初始化和获得一些系统信息。
【代码一】
接着如何知道鼠标进入或移出窗口呢?在前面我已经证明了WM_MOUSEMOVE和WM_MOUSELEAVE不符合我们的要求,于是我用了WM_ NCHITTEST这个消息,你可以看到我在这个消息响应函数中用了两个SetTimer,一个用于检测鼠标是否离开,一个用于伸缩过程,不管你喜欢不喜欢,要达到第7点和第11点,这个是必须的,考虑的效率问题,在不需要的时候关闭这些Timer就好了。
【代码二】
然后在OnTimer中
【代码三】
暂时不管OnTimer中的DoHide(); DoShow();
先来看看核心的函数之一的 FixMoving,该函数在OnMoving中被调用,FixMoving通过检测鼠标位置和窗口位置来决定窗口的收缩模式,并修正粘附边界时窗口的位置,从而达到像移动QQ时出现的效果。
【代码四】
收缩模式和位置决定后,剩下的工作就由最后两个核心函数完成了:实现收缩的DoHide(),实现伸展的DoShow()。在这两个过程中m_hsFinished,m_hiding 这两个变量起到很重要的控制作用。由于伸缩过程没完成时,hsFinished始终为FALSE,所以Timer 2 不会关闭,于是在OnTimer中会重复调用这两个函数之一,在这两个函数体内,窗口位置有规律地递减或递增就可以达到QQ的“抽屉”效果了,有趣的是即使伸缩过程还没完成,你也可以在这个过程中改变m_hiding这个值来决定他是伸还是缩,正如QQ一样。你可以把Timer 2 的事件间隔调大一点,然后在窗口伸缩时,鼠标来回地进出窗口就会很容易看到这样有趣的效果(还没缩进去又被拉了出来,或者还没拉出来又缩进去了)。
【代码五】
【代码六】
到此,程序终于完成了。在我的源代码中还有对WM_SIZING的处理和定义了与之相关的宏,这些主要是控制窗口在调整大小时不能超过最小的宽度和高度,与QQ的自动伸缩无关,所以不在这里提及了。
三、结束语
虽然还不能算是完美的模仿,但效果已经非常非常的接近了。也许有人会奇怪为什么要用Tool Window 风格,这是因为,这样在任务栏中不会显示窗口。从QQ的标题栏高度也可以判断出他也是这种风格,但这样一来就不能拥有最小化、最大化按键了。实际上QQ的最大化、最小化和关闭按键都是用DC画上去的。如何在Caption上增加按键,外国一些开源网站有源代码,我下载并看了一下,发现里面有个知识点很有趣,那就是更改消息路由,有兴趣的可以去下载来学习一下。
QQ的成功很大部分在于他的界面比较人性化(用了MSN后深有感受),而这些界面实现起来原理也许很简单,难的是观察东西心要细、设计东西心要密、开发东西心要异。废话就不多说了,在vckbase偷师那么久,这是第一次在vckbase上发表原创,看了“投稿须知”,对其格式要求似懂非懂的,也不知道这篇文章会不会被采纳。不论结果如何,希望这篇文章对你们有所帮助。 本文章更多内容:<<上一页 - 1 - 2 |