修改鼠标光标的形状(五)

本文详细解析了MFC中沙漏光标的操作机制,包括CWinApp::DoWaitCursor()函数的具体实现,以及如何通过不同的方法查看该函数的源代码。

    通过上一篇,我们已经知道 MFC 对沙漏光标的几种操作方式最终都是通过调用 CWinApp::DoWaitCursor() 来实现的。以下是 CWinApp::DoWaitCursor() 的实现代码:

void  CWinApp::DoWaitCursor( int  nCode)
{
    
//  0 => restore, 1=> begin, -1=> end
    ASSERT(nCode  ==   0   ||  nCode  ==   1   ||  nCode  ==   - 1 );
    ASSERT(afxData.hcurWait 
!=  NULL);
    AfxLockGlobals(CRIT_WAITCURSOR);
    m_nWaitCursorCount 
+=  nCode;
    
if  (m_nWaitCursorCount  >   0 )
    {
        HCURSOR hcurPrev 
=  ::SetCursor(afxData.hcurWait);
        
if  (nCode  >   0   &&  m_nWaitCursorCount  ==   1 )
            m_hcurWaitCursorRestore 
=  hcurPrev;
    }
    
else
    {
        
//  turn everything off
        m_nWaitCursorCount  =   0 ;      //  prevent underflow
        ::SetCursor(m_hcurWaitCursorRestore);
    }
    AfxUnlockGlobals(CRIT_WAITCURSOR);
}

 根据上面的代码,我们至少可以分析出以下知识点:
(1)afxData 是一个全局的结构,CWinApp 把沙漏光标的句柄存放在它一个成员变量 afxData.hcurWait 当中,同时 CWinApp::DoWaitCursor() 是一个虚函数,如果我们需要实现自定义沙漏光标的话,直接修改 afxData.hcurWait  的值或者重载 CWinApp::DoWaitCursor() 应该都是可以率先考虑的做法;


(2)CWinApp 对沙漏光标的打开、关闭和刷新操作,是通过其成员变量 CWinApp::m_nWaitCursorCount 来控制的,CWinApp 实际上是对沙漏光标作一个引用计数的管理,引用计数操作的类型由函数参数 nCode 的值决定;


(3)CWinApp::DoWaitCursor() 的代码实现中包含了对 API 函数 SetCursor() 的调用,这跟《修改鼠标光标的形状(二)》中所涉及的内容是相吻合的;

 

    *想查看某个 MFC 函数的实现代码,(我知道的)一般有以下三种方法,为弥补本人表达能力和部分读者理解能力的不足,我举例稍微说明一下,比方说要查 CWinApp::DoWaitCursor() 的实现代码:
方法1:通过 VC 的查找功能进行定位;
(1.1)先在通过主菜单 Edit->Find in Files... 调出查找窗口;



(1.2)Find What 里面填入查找关键字:CWinApp::DoWaitCursor;
(1.3)In Folder 里面填入查找 MFC 代码的存放路径:C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO/VC98/MFC;
(1.4)其它查找选项根据实际情况填写;
(1.5)按“Find”按钮开始查找

 

方法2:安装 Visual Assist,利用它的代码跳转功能进行定位;
根据我多年的使用体会,Visual Assist 的确可以提高代码编写的速度,作为一名 VC 程序员,如果你还没有用过的话,推荐安装使用。在 www.VCKbase.com 上有个叫程序员工具箱的栏目,里面的“辅助开发工具”分类中有最新版本下载。

 

方法3:在代码中函数被调用的地方设置断点,通过 Debug 进行定位。
沿用之前的代码例子,在 CMyDialog::OnInitDialog() 函数中添加以下代码:

BOOL CMyDialog::OnInitDialog()
{
    CDialog::OnInitDialog();

    
//  TODO: Add extra initialization here
    AfxGetApp() -> DoWaitCursor( 0 );
    
    
return  TRUE;   //  return TRUE  unless you set the focus to a control
}

按 F9 在 DoWaitCursor() 所在行设置断点,Debug 模式下使程序运行到断点处,依次按下 F11、Shift+F11和F11,CWinApp::DoWaitCursor() 的实现代码就展现在你面前了。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值