Click here to Skip to main content
16,016,736 members
Articles / Web Development / HTML
Tip/Trick

Embedded WebBrowser (IWebBrowser2) in Pure C++ (no MFC, etc)

Rate me:
Please Sign up or sign in to vote.
4.71/5 (17 votes)
30 Jul 2014CPOL 66.5K   6.7K   33   14
Simple WebBrowser (IE) class in Pure C++

Introduction

This is IWebBrowser2 (Internet Explorer core), embedded into a window, like WebView in MFC or WebBrowser in .NET, by using interfaces IOleClientSiteIOleInPlaceSite, and IStorage.

Screenshot

Code

This is the WebBrowser class header.

C++
#include <comdef.h>
#include <Exdisp.h>
#include <string>
#include <tchar.h>
#include <Windows.h>

using namespace std;

class WebBrowser :
    public IOleClientSite,
    public IOleInPlaceSite,
    public IStorage
{

public:

    WebBrowser(HWND hWndParent);

    bool CreateBrowser();

    RECT PixelToHiMetric(const RECT& _rc);

    virtual void SetRect(const RECT& _rc);

    // ----- Control methods -----

    void GoBack();

    void GoForward();

    void Refresh();
    
    void Navigate(wstring szUrl);

    // ----- IUnknown -----

    virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid,
        void**ppvObject) override;

    virtual ULONG STDMETHODCALLTYPE AddRef(void);

    virtual ULONG STDMETHODCALLTYPE Release(void);

    // ---------- IOleWindow ----------

    virtual HRESULT STDMETHODCALLTYPE GetWindow( 
        __RPC__deref_out_opt HWND *phwnd) override;

    virtual HRESULT STDMETHODCALLTYPE ContextSensitiveHelp( 
        BOOL fEnterMode) override;

    // ---------- IOleInPlaceSite ----------

    virtual HRESULT STDMETHODCALLTYPE CanInPlaceActivate( void) override;

    virtual HRESULT STDMETHODCALLTYPE OnInPlaceActivate( void) override;

    virtual HRESULT STDMETHODCALLTYPE OnUIActivate( void) override;

    virtual HRESULT STDMETHODCALLTYPE GetWindowContext( 
        __RPC__deref_out_opt IOleInPlaceFrame **ppFrame,
        __RPC__deref_out_opt IOleInPlaceUIWindow **ppDoc,
        __RPC__out LPRECT lprcPosRect,
        __RPC__out LPRECT lprcClipRect,
        __RPC__inout LPOLEINPLACEFRAMEINFO lpFrameInfo) override;

    virtual HRESULT STDMETHODCALLTYPE Scroll( 
        SIZE scrollExtant) override;

    virtual HRESULT STDMETHODCALLTYPE OnUIDeactivate( 
        BOOL fUndoable) override;

    virtual HWND GetControlWindow();

    virtual HRESULT STDMETHODCALLTYPE OnInPlaceDeactivate( void) override;

    virtual HRESULT STDMETHODCALLTYPE DiscardUndoState( void) override;

    virtual HRESULT STDMETHODCALLTYPE DeactivateAndUndo( void) override;

    virtual HRESULT STDMETHODCALLTYPE OnPosRectChange( 
        __RPC__in LPCRECT lprcPosRect) override;

    // ---------- IOleClientSite ----------

    virtual HRESULT STDMETHODCALLTYPE SaveObject( void) override;

    virtual HRESULT STDMETHODCALLTYPE GetMoniker( 
        DWORD dwAssign,
        DWORD dwWhichMoniker,
        __RPC__deref_out_opt IMoniker **ppmk) override;

    virtual HRESULT STDMETHODCALLTYPE GetContainer( 
        __RPC__deref_out_opt IOleContainer **ppContainer) override;

    virtual HRESULT STDMETHODCALLTYPE ShowObject( void) override;
    virtual HRESULT STDMETHODCALLTYPE OnShowWindow( 
        BOOL fShow) override;

    virtual HRESULT STDMETHODCALLTYPE RequestNewObjectLayout( void) override;

    // ----- IStorage -----

    virtual HRESULT STDMETHODCALLTYPE CreateStream( 
        __RPC__in_string const OLECHAR *pwcsName,
        DWORD grfMode,
        DWORD reserved1,
        DWORD reserved2,
        __RPC__deref_out_opt IStream **ppstm) override;

    virtual HRESULT STDMETHODCALLTYPE OpenStream( 
        const OLECHAR *pwcsName,
        void *reserved1,
        DWORD grfMode,
        DWORD reserved2,
        IStream **ppstm) override;

    virtual HRESULT STDMETHODCALLTYPE CreateStorage( 
        __RPC__in_string const OLECHAR *pwcsName,
        DWORD grfMode,
        DWORD reserved1,
        DWORD reserved2,
        __RPC__deref_out_opt IStorage **ppstg) override;

    virtual HRESULT STDMETHODCALLTYPE OpenStorage( 
        __RPC__in_opt_string const OLECHAR *pwcsName,
        __RPC__in_opt IStorage *pstgPriority,
        DWORD grfMode,
        __RPC__deref_opt_in_opt SNB snbExclude,
        DWORD reserved,
        __RPC__deref_out_opt IStorage **ppstg) override;

    virtual HRESULT STDMETHODCALLTYPE CopyTo( 
        DWORD ciidExclude,
        const IID *rgiidExclude,
        __RPC__in_opt  SNB snbExclude,
        IStorage *pstgDest) override;

    virtual HRESULT STDMETHODCALLTYPE MoveElementTo( 
        __RPC__in_string const OLECHAR *pwcsName,
        __RPC__in_opt IStorage *pstgDest,
        __RPC__in_string const OLECHAR *pwcsNewName,
        DWORD grfFlags) override;

    virtual HRESULT STDMETHODCALLTYPE Commit( 
        DWORD grfCommitFlags) override;

    virtual HRESULT STDMETHODCALLTYPE Revert( void) override;

    virtual HRESULT STDMETHODCALLTYPE EnumElements( 
        DWORD reserved1,
        void *reserved2,
        DWORD reserved3,
        IEnumSTATSTG **ppenum) override;

    virtual HRESULT STDMETHODCALLTYPE DestroyElement( 
        __RPC__in_string const OLECHAR *pwcsName) override;

    virtual HRESULT STDMETHODCALLTYPE RenameElement( 
        __RPC__in_string const OLECHAR *pwcsOldName,
        __RPC__in_string const OLECHAR *pwcsNewName) override;

    virtual HRESULT STDMETHODCALLTYPE SetElementTimes( 
        __RPC__in_opt_string const OLECHAR *pwcsName,
        __RPC__in_opt const FILETIME *pctime,
        __RPC__in_opt const FILETIME *patime,
        __RPC__in_opt const FILETIME *pmtime) override;

    virtual HRESULT STDMETHODCALLTYPE SetClass( 
        __RPC__in REFCLSID clsid) override;
    virtual HRESULT STDMETHODCALLTYPE SetStateBits( 
        DWORD grfStateBits,
        DWORD grfMask) override;

    virtual HRESULT STDMETHODCALLTYPE Stat( 
        __RPC__out STATSTG *pstatstg,
        DWORD grfStatFlag) override;

protected:

    IOleObject* oleObject;
    IOleInPlaceObject* oleInPlaceObject;

    IWebBrowser2* webBrowser2;

    LONG iComRefCount;

    RECT rObject;

    HWND hWndParent;
    HWND hWndControl;

};

As you can see, it inherits classes IOleClientSite, IOleInPlaceSite and IStorage, and implements their methods.

Most methods are definited by default, such as

C++
HRESULT STDMETHODCALLTYPE WebBrowser::DiscardUndoState(void)
{
    return E_NOTIMPL;
}

or

C++
HRESULT STDMETHODCALLTYPE WebBrowser::OnUIDeactivate( 
    BOOL fUndoable)
{
    return S_OK;
}

But some methods' code is changed, to integrate with IWebBrowser2 and parent window, such as

C++
HRESULT STDMETHODCALLTYPE WebBrowser::GetWindowContext( 
    __RPC__deref_out_opt IOleInPlaceFrame **ppFrame,
    __RPC__deref_out_opt IOleInPlaceUIWindow **ppDoc,
    __RPC__out LPRECT lprcPosRect,
    __RPC__out LPRECT lprcClipRect,
    __RPC__inout LPOLEINPLACEFRAMEINFO lpFrameInfo)
{
    HWND hwnd = hWndParent;

    (*ppFrame) = NULL;
    (*ppDoc) = NULL;
    (*lprcPosRect).left = rObject.left;
    (*lprcPosRect).top = rObject.top;
    (*lprcPosRect).right = rObject.right;
    (*lprcPosRect).bottom = rObject.bottom;
    *lprcClipRect = *lprcPosRect;

    lpFrameInfo->fMDIApp = false;
    lpFrameInfo->hwndFrame = hwnd;
    lpFrameInfo->haccel = NULL;
    lpFrameInfo->cAccelEntries = 0;

    return S_OK;
}

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



Comments and Discussions

 
Questionscript errors Pin
Michael Haephrati16-Nov-20 10:19
professionalMichael Haephrati16-Nov-20 10:19 
SuggestionResource page relative paths Pin
Adamanteus18-Sep-18 16:16
Adamanteus18-Sep-18 16:16 
That's possible to add Navigate2 call for WebBrowser class, but urls from resource HTML, will lose current directory Frown | :-(
Question is how to inform WebBrowser of current directory, for binded to resources pages ?
QuestionProblem with sites with Javascritp Pin
lamerjack27-Oct-15 0:09
lamerjack27-Oct-15 0:09 
AnswerRe: Problem with sites with Javascritp Pin
lamerjack27-Oct-15 5:04
lamerjack27-Oct-15 5:04 
QuestionWorked brilliantly Pin
MarkHenryC8-Jun-15 17:28
MarkHenryC8-Jun-15 17:28 
Suggestionunnecessary files Pin
danel8-Mar-15 3:43
danel8-Mar-15 3:43 
QuestionThanks for article Pin
dnomyar26-Aug-14 17:16
dnomyar26-Aug-14 17:16 
GeneralMy vote of 4 Pin
Claude "CodeAngry" Adrian25-Jul-14 6:08
Claude "CodeAngry" Adrian25-Jul-14 6:08 
BugThis code will most likely crash. Pin
Claude "CodeAngry" Adrian25-Jul-14 4:27
Claude "CodeAngry" Adrian25-Jul-14 4:27 
GeneralRe: This code will most likely crash. Pin
Emiliarge25-Jul-14 6:04
professionalEmiliarge25-Jul-14 6:04 
GeneralRe: This code will most likely crash. Pin
Claude "CodeAngry" Adrian25-Jul-14 6:08
Claude "CodeAngry" Adrian25-Jul-14 6:08 
SuggestionI hope you improve it... Pin
Cristian Amarie25-Jul-14 3:24
Cristian Amarie25-Jul-14 3:24 
GeneralRe: I hope you improve it... Pin
Emiliarge25-Jul-14 3:44
professionalEmiliarge25-Jul-14 3:44 
QuestionImages offsite Pin
Wendelius25-Jul-14 2:24
mentorWendelius25-Jul-14 2:24 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.