ATL窗口:      

1. ATL 采用严格的接口/实现相分离来设计,ATL 有一个类定义了窗口的“接口”,也就是对一个窗口可以做什么。这个类就是 CWindow。

2. CWindow 有一个当你需要原始 HWND 时可以访问的公用成员 m_hWnd。CWindow 也有一个 operator HWND 方法,于是你可以传递 CWindow 对象到接受 HWND 的函数中.

3.

3.1 ATL 中窗口的实现类是 CWindowImpl。CWindowImpl 包含了做这些事情的代码,比如窗口类注册,窗口子类化,消息映射,以及一个基本的 WindowProc()。

 

 任何要创建的非对话框窗口应该从 CWindowImpl 派生。新类里需要包含三样:

  1. 窗口类定义
  2. 消息映射
  3. 窗口使用的默认风格,称作窗口修饰

3.2 还有两个独立的类,包含了对对话框的实现,CDialogImpl 和 CAxDialogImpl。CDialogImpl 用于普通的对话框,而 CAxDialogImpl 用于要掌控 ActiveX 控件的对话框。

重点: CWindowImpl

 
    
  1. typedef CWinTraits<WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN,  
  2. WS_EX_APPWINDOW> CMyWindowTraits;  
  3.  
  4. class CMyWindow : public CWindowImpl<CMyWindow, CWindow, CMyWindowTraits> 
  5. {  
  6. public:  
  7.     DECLARE_WND_CLASS(_T("My Window Class"))  
  8.        BEGIN_MSG_MAP(CMyWindow)  
  9.     END_MSG_MAP()  
  10. };  
  11.  

 其中,我们可以使用系统给的:

 
    
  1. ATL 还有一些专用的预定义 CWinTraits ,其中适用于像我们这样的顶级窗口的一个是   
  2. CFrameWinTraits:typedef CWinTraits CFrameWinTraits;  
  3.  
 
    
  1. template<class T, class TBase = CEdit, class TWinTraits = CControlWinTraits>  
  2. class ATL_NO_VTABLE CEditXPImpl : public CWindowImpl  
  3. {  
  4. private:  
  5.     HPEN m_hPen;  
  6. public:  
  7.     DECLARE_WND_SUPERCLASS(NULL, TBase::GetWndClassName())  
  8.     // 消息映射 The WM_NCPAINT message is sent to a window when its frame must be painted.  
  9.     //  处理WM_NCPAINT消息可以实现自绘窗口边框和标题栏  
  10.     BEGIN_MSG_MAP(CEditXP)  
  11.         MESSAGE_HANDLER(WM_NCPAINT, OnNCPaint)  
  12.     END_MSG_MAP()  
  13.  
  14.     CEditXPImpl()  
  15.     {  
  16.         m_hPen = CreatePen(PS_SOLID, 1, RGB(0, 255, 255));  
  17.     }  
  18.     ~CEditXPImpl()  
  19.     {  
  20.         DeleteObject(m_hPen);  
  21.     }  
  22.       
  23.     // 重绘控件边框  
  24.     LRESULT OnNCPaint(UINT uMsg, WPARAM wParam , LPARAM lParam, BOOL& bHandled)  
  25.     {  
  26.         CRect rect;  
  27.         GetWindowRect(&rect);  
  28.         CDCHandle dc = GetWindowDC();  
  29.         HPEN hOldPen = dc.SelectPen(m_hPen);  
  30.         // 颜色填充的区域  
  31.         rect.right  -=  rect.left;  
  32.         rect.bottom -=  rect.top;  
  33.         rect.left   =   rect.top    = 0;  
  34.         dc.Rectangle(&rect);  
  35.         dc.SelectPen(hOldPen);  
  36.         ReleaseDC(dc);  
  37.         return 0;  
  38.     }  
  39.       
  40.  
  41.  
  42. };  
  43.  
  44. class CEditXP : public CEditXPImpl  
  45. {  
  46. public:  
  47.     DECLARE_WND_CLASS(_T("WTL_XPEdit"));  
  48. }; 

 使用的时候就是:  CEditXP m_edit;  m_eidt.SubclassWindow(GetDlgItem(IDC_EDIT1));