duilib 的IE瀏覽器控件去邊框和去滾動條的代碼


 近些天在duilib群里經常有朋友問起,怎么讓duilib的IE控件可以去邊框,去滾動條的問題,或者是如何去控件IE控件的行為。為了避免重復的回答,我就寫一篇博文,把處理方法說明一下。

        duilib中有Webbrowser控件,是繼承ActivexUI控件后針對IE進行的封裝,使用IE控件的話就用他了。這個控件留了一個接口名為SetWebBrowserEventHandler,這個函數用了指定一個事件處理器,來控制IE的行為。而這個函數需要一個CWebBrowserEventHandler對象指針,這個CWebBrowserEventHandler類在duilib的Utils目錄中已經寫好了,是一個基本的事件處理器框架,只要重寫這個CWebBrowserEventHandler類的GetHostInfo函數就可以控制去掉IE瀏覽器的邊框和滾動條,同時還有其他功能,比如控制是否可以顯示IE右鍵菜單,NavigateComplete2來截獲瀏覽器加載完畢的事件等等。

        所以我們如果要去控制瀏覽器,那么正確的做法就是寫一個類,繼承CWebBrowserEventHandler然后重寫你需要的函數。我簡單寫了一個名叫CCustomWebEventHandler,代碼如下:

#ifndef _CCUSTOM_WEBBROWSER_EVENT_HANDLER_H_
#define _CCUSTOM_WEBBROWSER_EVENT_HANDLER_H_

#pragma once
class CCustomWebEventHandler:public CWebBrowserEventHandler
{
public:
    CCustomWebEventHandler() {}
    ~CCustomWebEventHandler() {}

    virtual void BeforeNavigate2( IDispatch *pDisp,VARIANT *&url,VARIANT *&Flags,VARIANT *&TargetFrameName,VARIANT *&PostData,VARIANT *&Headers,VARIANT_BOOL *&Cancel ) {}
    virtual void NavigateError(IDispatch *pDisp,VARIANT * &url,VARIANT *&TargetFrameName,VARIANT *&StatusCode,VARIANT_BOOL *&Cancel) {}
    virtual void NavigateComplete2(IDispatch *pDisp,VARIANT *&url){    }

    virtual void ProgressChange(LONG nProgress, LONG nProgressMax){}
    virtual void NewWindow3(IDispatch **pDisp, VARIANT_BOOL *&Cancel, DWORD dwFlags, BSTR bstrUrlContext, BSTR bstrUrl){}
    virtual void CommandStateChange(long Command,VARIANT_BOOL Enable){}

    // interface IDocHostUIHandler
    virtual HRESULT STDMETHODCALLTYPE ShowContextMenu(
        /* [in] */ DWORD dwID,
        /* [in] */ POINT __RPC_FAR *ppt,
        /* [in] */ IUnknown __RPC_FAR *pcmdtReserved,
        /* [in] */ IDispatch __RPC_FAR *pdispReserved)
    {
        return S_OK;
        //return S_FALSE
    }

    virtual HRESULT STDMETHODCALLTYPE GetHostInfo(
        /* [out][in] */ DOCHOSTUIINFO __RPC_FAR *pInfo)
    {
        if (pInfo != NULL)
        {        
            pInfo->cbSize = sizeof(DOCHOSTUIINFO);  
            pInfo->dwDoubleClick = DOCHOSTUIDBLCLK_DEFAULT;  
            pInfo->dwFlags |= DOCHOSTUIFLAG_NO3DBORDER | DOCHOSTUIFLAG_THEME | 
                DOCHOSTUIFLAG_NO3DOUTERBORDER | DOCHOSTUIFLAG_DIALOG |
                DOCHOSTUIFLAG_DISABLE_HELP_MENU;//| DOCHOSTUIFLAG_SCROLL_NO;;

            //這里還可以加其他代碼來控制網頁
             //LPWSTR m_pZoom = L"BODY{Zoom:100%;}";
            //pInfo->pchHostCss = (LPWSTR)::CoTaskMemAlloc((lstrlenW(m_pZoom)+1)*2);
            //lstrcpyW(pInfo->pchHostCss, m_pZoom);
        }

        return S_OK;
        
    }

    virtual HRESULT STDMETHODCALLTYPE ShowUI(
        /* [in] */ DWORD dwID,
        /* [in] */ IOleInPlaceActiveObject __RPC_FAR *pActiveObject,
        /* [in] */ IOleCommandTarget __RPC_FAR *pCommandTarget,
        /* [in] */ IOleInPlaceFrame __RPC_FAR *pFrame,
        /* [in] */ IOleInPlaceUIWindow __RPC_FAR *pDoc)
    {
        return S_FALSE;
    }

    virtual HRESULT STDMETHODCALLTYPE HideUI( void)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE UpdateUI( void)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE EnableModeless(
        /* [in] */ BOOL fEnable)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE OnDocWindowActivate(
        /* [in] */ BOOL fActivate)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE OnFrameWindowActivate(
        /* [in] */ BOOL fActivate)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE ResizeBorder(
        /* [in] */ LPCRECT prcBorder,
        /* [in] */ IOleInPlaceUIWindow __RPC_FAR *pUIWindow,
        /* [in] */ BOOL fRameWindow)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE TranslateAccelerator(
        /* [in] */ LPMSG lpMsg,
        /* [in] */ const GUID __RPC_FAR *pguidCmdGroup,
        /* [in] */ DWORD nCmdID)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE GetOptionKeyPath(
        /* [out] */ LPOLESTR __RPC_FAR *pchKey,
        /* [in] */ DWORD dw)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE GetDropTarget(
        /* [in] */ IDropTarget __RPC_FAR *pDropTarget,
        /* [out] */ IDropTarget __RPC_FAR *__RPC_FAR *ppDropTarget)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE GetExternal(
        /* [out] */ IDispatch __RPC_FAR *__RPC_FAR *ppDispatch)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE TranslateUrl(
        /* [in] */ DWORD dwTranslate,
        /* [in] */ OLECHAR __RPC_FAR *pchURLIn,
        /* [out] */ OLECHAR __RPC_FAR *__RPC_FAR *ppchURLOut)
    {
        return S_OK;
    }

    virtual HRESULT STDMETHODCALLTYPE FilterDataObject(
        /* [in] */ IDataObject __RPC_FAR *pDO,
        /* [out] */ IDataObject __RPC_FAR *__RPC_FAR *ppDORet)
    {
        return S_OK;
    }

    //     virtual HRESULT STDMETHODCALLTYPE GetOverrideKeyPath( 
    //         /* [annotation][out] */ 
    //         __deref_out  LPOLESTR *pchKey,
    //         /* [in] */ DWORD dw)
    //     {
    //         return E_NOTIMPL;
    //     }

    // IDownloadManager
    virtual HRESULT STDMETHODCALLTYPE Download( 
        /* [in] */ IMoniker *pmk,
        /* [in] */ IBindCtx *pbc,
        /* [in] */ DWORD dwBindVerb,
        /* [in] */ LONG grfBINDF,
        /* [in] */ BINDINFO *pBindInfo,
        /* [in] */ LPCOLESTR pszHeaders,
        /* [in] */ LPCOLESTR pszRedir,
        /* [in] */ UINT uiCP)
    {
        return S_OK;
    }
};

#endif //_CCUSTOM_WEBBROWSER_EVENT_HANDLER_H_

使用他的方法如下:

 

        首先在xml中寫入一個Webbrowser控件並且在c++代碼中通過FindControl找到這個控件的指針,然后寫類似的代碼:

    CWebBrowserUI* pActiveXUI = static_cast<CWebBrowserUI*>(m_PaintManager.FindControl(_T("ActiveXDemo1")));

    if( pActiveXUI ) 
    {
        pActiveXUI->SetDelayCreate(false);
        CCustomWebEventHandler *pWebHandle = new CCustomWebEventHandler;
        pActiveXUI->SetWebBrowserEventHandler(pWebHandle);
        pActiveXUI->Navigate2(L"about:blank");    //這行代碼,如果注釋掉,就不會去掉邊框,IE有bug,第二次加載網頁才會讓事件處理器有效
        pActiveXUI->Navigate2(L"http://www.kugou.com/");
    }

  我這里強調兩點

        第一、我這里只是示范,為了方便,我使用的是alberl的demo,簡單改了幾行代碼。可以看到我new了一個CCustomWebEventHandler,但是沒有去delete,所以自己使用時千萬要注意代碼規范!!

       第二、先加載了一個blank頁面,再跳轉到目標頁面,第一次加載頁面不會觸發事件處理器,第二次才會,為了不影響效率我直接加載blank。關於這個bug的說明,在微軟官網有,具體地址我忘了~~


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM