Basic Control Containment基本的控制容器[1]

首先回顾一下CWindow中的窗口过程:

 

#define DECLARE_WND_CLASS(WndClassName) /
static ATL::CWndClassInfo& GetWndClassInfo() /
{ /
static ATL::CWndClassInfo wc = /
{ /
{ sizeof(WNDCLASSEX), CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS, StartWindowProc, /
0, 0, NULL, NULL, NULL, (HBRUSH)(COLOR_WINDOW + 1), NULL, WndClassName, NULL }, /
NULL, NULL, IDC_ARROW, TRUE, 0, _T("") /
}; /
return wc; /
}

指定了窗口过程StartWindowProc.

 

然后通过pThis->m_thunk.Init(WindowProc, pThis); thunk机制调换了

static LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)中

的HWND为CContainedWindowT< TBase >* pThis = (CContainedWindowT< TBase >*)hWnd;

接下来就利用多态调用

BOOL bRet = pThis->m_pObject->ProcessWindowMessage(pThis->m_hWnd, uMsg, wParam, lParam, lRes, pThis->m_dwMsgMapID);

 

该函数是通过宏定义

 

#define BEGIN_MSG_MAP(theClass) /
public: /
BOOL ProcessWindowMessage(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT& lResult, DWORD dwMsgMapID = 0) /
{ /
BOOL bHandled = TRUE; /
(hWnd); /
(uMsg); /
(wParam); /
(lParam); /
(lResult); /
(bHandled); /
switch(dwMsgMapID) /
{ /
case 0:

 

若这个函数返回FALSE,则跳转到DefWindowProc

if(uMsg != WM_NCDESTROY)
lRes = pThis->DefWindowProc(uMsg, wParam, lParam);

 

以上就是关于CWindow中的窗口过程调用。

接下来看一下CAxHostWindow对象是如何被创建的。在CMainWindow中:

CAxWindow m_bullseyeWin;

m_bullseyeWin.Create( m_hWnd, rect, controlName, WS_CHILD | WS_VISIBLE, 0, ID_BULLSEYE );

其中就指定了CLASSNAME     GetWndClassName() = ATLAXWIN_CLASS,该宏正是"AtlAxWin80"

 

该窗口类在AtlAxWinInit()注册的时候,使用的是wc.lpfnWndProc = AtlAxWindowProc;

来看一下window procedure AtlAxWindowProc:

在其中调用了HRESULT hRet = AtlAxCreateControlLic(T2COLE_EX_DEF(spName), hWnd, spStream, &spUnk, NULL);

将spName传递进去,并最终调用了AtlAcCreateControlLicEx(atlHost.h LN1980)

 

hr = CAxHostWindow::_CreatorClass::CreateInstance(NULL, __uuidof(IUnknown), (void**)&spUnkContainer);
if (SUCCEEDED(hr))
{
CComPtr pAxWindow;
spUnkContainer->QueryInterface(__uuidof(IAxWinHostWindow), (void**)&pAxWindow);
CComBSTR bstrName(lpszName);
hr = pAxWindow->CreateControlLicEx(bstrName, hWnd, pStream, &spUnkControl, iidSink, punkSink, bstrLic);
}

 

interface IAxWinHostWindow : IUnknown {

HRESULT CreateControl([in] LPCOLESTR lpTricsData, [in] HWND hWnd, [in] IStream* pStream);

 HRESULT CreateControlEx([in] LPCOLESTR lpTricsData, [in] HWND hWnd, [in] IStream* pStream, [out] IUnknown** ppUnk, [in] REFIID riidAdvise, [in] IUnknown* punkAdvise);

 HRESULT AttachControl([in] IUnknown* pUnkControl, [in] HWND hWnd);

HRESULT QueryControl([in] REFIID riid, [out, iid_is(riid)] void **ppvObject);

HRESULT SetExternalDispatch([in] IDispatch* pDisp); HRESULT SetExternalUIHandler( [in] IDocHostUIHandlerDispatch* pDisp); };

 

// TODO  复习SubclassWindow,即子类化

http://www.vckbase.com/document/viewdoc/?id=1119

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值