vs2008建立一个ATL工程,选择DLL类型,在工程里面,创建ATL简单对象,按照以下选择构建对象
新增继承:public IDispEventImpl<1, CMyBHO, &DIID_DWebBrowserEvents2, &LIBID_SHDocVw, 1, 1>
增加公共函数:
public:
STDMETHOD(SetSite)(IUnknown * pUnkSite);
增加私有变量:
protected:
CComPtr<IWebBrowser2> m_spWebBrowser;//保存Browser指针的私有变量
然后添加实现:
STDMETHODIMP CMyBHO::SetSite(IUnknown*pUnkSite)
{
if (pUnkSite != NULL)
{
// Cache the pointer to IWebBrowser2.
HRESULT hr = pUnkSite->QueryInterface(IID_IWebBrowser2, (void **)&m_spWebBrowser);
if (SUCCEEDED(hr))
{
// Register to sink events from DWebBrowserEvents2.
hr = DispEventAdvise(m_spWebBrowser);
}
}
else
{
// Unregister event sink.
DispEventUnadvise(m_spWebBrowser);
// Release cached pointers and other resources here.
m_spWebBrowser.Release();
}
//返回基类实现
return IObjectWithSiteImpl::SetSite(pUnkSite);
}
若要响应事件,添加如下代码,注意,红色的1要对应继承接口IDispEventImpl那个1
BEGIN_SINK_MAP(CMyBHO)
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_DOCUMENTCOMPLETE, OnDocumentComplete)
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_BEFORENAVIGATE2, OnBeforeNavigate2)
END_SINK_MAP()
void STDMETHODCALLTYPE OnDocumentComplete(IDispatch *pDisp, VARIANT *pvarURL);
void STDMETHODCALLTYPE OnBeforeNavigate2(IDispatch *pDisp, VARIANT *pvarURL, VARIANT *pvarFlags , VARIANT *pvarTargetFrameName , VARIANT *pvarPostData, VARIANT *pvarHeaders ,BOOL *cancel);
实现:
void STDMETHODCALLTYPE CMyBHO::OnDocumentComplete(IDispatch *pDisp, VARIANT *pvarURL)
{
// Retrieve the top-level window from the site.
HWND hwnd;
HRESULT hr = m_spWebBrowser->get_HWND((LONG_PTR*)&hwnd);
if (SUCCEEDED(hr))
{
// Output a message box when page is loaded.
//MessageBox(hwnd, L"Hello World!", L"BHO", MB_OK);
}
}
void STDMETHODCALLTYPE CMyBHO::OnBeforeNavigate2(IDispatch *pDisp, VARIANT *pvarURL, VARIANT *pvarFlags , VARIANT *pvarTargetFrameName , VARIANT *pvarPostData, VARIANT *pvarHeaders ,BOOL *cancel)
{
if(wcscmp(pvarURL->bstrVal,L"http://www.baidu.com/")==0)
{
CComVariant varUrl(L"http://www.google.com");
m_spWebBrowser->Navigate2(&varUrl,NULL,NULL,NULL,NULL);
}
}