⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mainwnd.cpp

📁 Windows CE 下的机顶盒应用实例
💻 CPP
📖 第 1 页 / 共 3 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this source code is subject to the terms of the Microsoft end-user
// license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
// If you did not accept the terms of the EULA, you are not authorized to use
// this source code. For a copy of the EULA, please see the LICENSE.RTF on your
// install media.
//
/*++
THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
PARTICULAR PURPOSE.

Module Name:  mainwnd.cpp

Abstract:  Implements the main window, the container for the webbrowser

Functions:

Notes: Most of the code resides here. The container and its interaction with the webbrowser control,
        commandbar, statusbar etc.

--*/
#include <windows.h>

#include "stdafx.h"
#include "stbihost.h"
#include "mainwnd.h"
#include "mshtmcid.h"
#include "resource.h"
#include "external.h"
#include "rctlkeys.h"

#define INITGUID
#include "initguid.h"
#include <hshell.h>

CComModule _Module;

BEGIN_OBJECT_MAP(ObjectMap)
    OBJECT_ENTRY_NON_CREATEABLE(CHostExternal)
END_OBJECT_MAP()

#define WINCLS_UUID TEXT("55efda90-063f-419c-9ce4-18c3d26c2ae2")	// window class
#define REG_ROOTKEY TEXT("SOFTWARE\\Microsoft\\Internet Explorer\\Main")
#define REG_WMPVALUE TEXT("Windows Media Page")
#define SAFEAREA_MARGIN 0.82	// SHDOCVW will display within this area of the container window

DEFINE_GUID(CLSID_WebBrowser,       0x8856F961L, 0x340A, 0x11D0, 0xA9, 0x6B, 0x00, 0xC0, 0x4F, 0xD7, 0x05, 0xA2);
DEFINE_GUID(IID_IWebBrowser,        0xEAB22AC1L, 0x30C1, 0x11CF, 0xA7, 0xEB, 0x00, 0x00, 0xC0, 0x5B, 0xAE, 0x0B);
DEFINE_GUID(IID_IWebBrowser2,       0xD30C1661L, 0xCDAF, 0x11D0, 0x8A, 0x3E, 0x00, 0xC0, 0x4F, 0xC9, 0xE2, 0x6E);
DEFINE_GUID(DIID_DWebBrowserEvents, 0xEAB22AC2L, 0x30C1, 0x11CF, 0xA7, 0xEB, 0x00, 0x00, 0xC0, 0x5B, 0xAE, 0x0B);
DEFINE_GUID(DIID_DWebBrowserEvents2, 0x34A715A0L, 0x6587, 0x11D0, 0x92, 0x4A, 0x00, 0x20, 0xAF, 0xC7, 0xAC, 0x4D);
DEFINE_GUID(IID_IWebBrowserApp,     0x0002DF05L, 0x0000, 0x0000, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46);

const GUID SID_SDocHost = { 0xc6504990, 0xd43e, 0x11cf, { 0x89, 0x3b, 0x00, 0xaa, 0x00, 0xbd, 0xce, 0x1a}};

LONG        glThreadCount	= 0;
HWND		ghWndAddressEdit= NULL;
HANDLE      ghExitEvent		= NULL;
HINSTANCE   g_hInstance		= NULL;
DWORD      g_dwMainWindowStackSize = 0x20000;

void GetProxyOption();


static HRESULT FindString();
HRESULT HandleNewWindow2(LPTSTR lpszUrl, DISPPARAMS FAR* pdparams);
BOOL RegisterMainWnd();


DWORD WINAPI NewWindow(LPVOID pParam)
{

    CMainWnd *pWnd = (CMainWnd *)pParam;
    MSG msg;
    BOOL fRet;

    HRESULT hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);

    fRet = pWnd->Create();

    SetEvent(pWnd->hEvent);

    if (!fRet)
    {
        pWnd->_pBrowser = NULL;
        return 0;
    }

    while (GetMessage( &msg, NULL, 0, 0 ) )
    {
        if(msg.message == WM_QUIT)
            break;

        if (!pWnd->PreTranslateMessage(&msg) && !(msg.message == WM_CHAR && msg.wParam == VK_TAB))
        {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
    }

    pWnd->Release();

    CoUninitialize();

    InterlockedDecrement(&glThreadCount);
    SetEvent(ghExitEvent);

    return msg.wParam;
}

int APIENTRY WinMain(HINSTANCE hInst, HINSTANCE hPrevInst, LPTSTR lpCmdLine, int nCmdShow)
{
	DEBUGMSG (1, (TEXT("\r\n\r\n### New instance of StbIHost ###\r\n")
				  TEXT("### Command line is: %s"), lpCmdLine));
	// allow only one instance
	HWND hWnd = FindWindow(WINCLS_UUID, NULL);	
	if (hWnd)
	{
		SetForegroundWindow((HWND)(((DWORD)hWnd) | 0x01));
		if (*lpCmdLine)
		{
			COPYDATASTRUCT cds = { 1,
								   sizeof(TCHAR)*(_tcslen(lpCmdLine) + 1),
								   lpCmdLine };
			SendMessage(hWnd, WM_COPYDATA, NULL, (LPARAM)&cds);
		}
		return 0;
	}

    INITCOMMONCONTROLSEX iccsex;
    HKEY hKey;
    DWORD dwSize = sizeof(DWORD);
    MSG msg;

    // HKCU is where IE\Main settings are
    if(ERROR_SUCCESS == RegOpenKeyEx(HKEY_CURRENT_USER, REG_ROOTKEY, 0, 0, &hKey))
    {
            RegQueryValueEx(hKey, TEXT("StackRes"), NULL, NULL, (LPBYTE)&g_dwMainWindowStackSize, &dwSize);
            RegCloseKey(hKey);
    }

    // provide a default stack size if the one given is too small or too large. 
    if(g_dwMainWindowStackSize < 0x10000 || g_dwMainWindowStackSize > 0x80000)
    {
            // default to 128k
            g_dwMainWindowStackSize = 0x20000;
    }
    RETAILMSG(1,(L"STBIHOST Using stack size: %x", g_dwMainWindowStackSize));


    HRESULT hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);
    if (FAILED(hr))
    {
        return FALSE;
    }

    hr = _Module.Init(ObjectMap, hInst, &LIBID_STBIHOSTLib);
    ASSERT(SUCCEEDED(hr));
    hr = _Module.RegisterClassObjects(CLSCTX_LOCAL_SERVER, REGCLS_MULTIPLEUSE);
    ASSERT(SUCCEEDED(hr));
    hr = _Module.RegisterTypeLib();
    ASSERT(SUCCEEDED(hr));

    if (!RegisterMainWnd())
        return FALSE;
    
    ghExitEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
    if (!ghExitEvent)
    {
        return FALSE;
    }

    iccsex.dwSize = sizeof(INITCOMMONCONTROLSEX);
    iccsex.dwICC = ICC_COOL_CLASSES;

    InitCommonControlsEx(&iccsex);

    g_hInstance = hInst;

    // Create  a message queue on this thread
    PeekMessage(&msg, NULL, 0,0,PM_NOREMOVE);

    if(HandleNewWindow2(lpCmdLine, NULL))
    {
        goto Cleanup;
    }


    while (glThreadCount > 0)
    {
        WaitForSingleObject(ghExitEvent, INFINITE);
    }
    
Cleanup:
	_Module.UnRegisterTypeLib();
	_Module.RevokeClassObjects();
	_Module.Term();
    CoUninitialize();

    RETAILMSG(1, (L"STBIHOST exited. Cmdline was: %s\r\n",lpCmdLine ? lpCmdLine : L""));

    return TRUE;
}


CMainWnd::CMainWnd()
{
    _ulRefs = 1;
    _hWnd = NULL;
    _pBrowser = NULL;
    _pObject = NULL;
    _pCP = NULL;
    _lpszUrl = NULL;
    _fEmpty = FALSE;
    _szTitle[0] = 0;
    _fSafeArea = FALSE;
    _lSafeWidth = 0;
	_lSafeHeight = 0;
	_ptSafe.x = 0;
	_ptSafe.y = 0;

    _wZoom = 2; // default zoom
    _wDLCCounter = 0; // counter for Download Completes

    _pUnkExternal = NULL;

    _hAccelTblNew = NULL;
    _cNewAccels = 0;
    _rgNewAccels = NULL;
    _fUseNewAccels = NULL;
}

CMainWnd::~CMainWnd()
{
	RETAILMSG(1,(L"STBIHOST Exiting ~CMainWnd\r\n"));

	if (_pBrowser)
		_pBrowser->Release();

	if (_pUnkExternal)
		_pUnkExternal->Release();

	if (_rgNewAccels)
		delete [] _rgNewAccels;

	if (_hAccelTblNew)
		DestroyAcceleratorTable(_hAccelTblNew);
}   

BOOL RegisterMainWnd()
{
    WNDCLASS        wc;
    wc.style         = 0;
    wc.lpfnWndProc   = (WNDPROC)CMainWnd::MainWndProc;
    wc.cbClsExtra    = 0;
    wc.cbWndExtra    = 0;
    wc.hInstance     = g_hInstance;
    wc.hIcon         = NULL; // LoadIcon(g_hInstance, MAKEINTRESOURCE(IDI_IE));
    wc.hCursor       = LoadCursor(NULL, IDC_ARROW);
    wc.hbrBackground = CreateSolidBrush(RGB(50,50,50));
    wc.lpszMenuName  = NULL;
    wc.lpszClassName = WINCLS_UUID;

    if (!(RegisterClass(&wc)))
        return FALSE;

    return TRUE;
}


BOOL CMainWnd::Create()
{
    RECT rcArea;

    DWORD dwStyle = WS_VISIBLE;
    DWORD dwExStyle = 0;

    HMENU hMenu = NULL;

    SystemParametersInfo(SPI_GETWORKAREA, 0, &rcArea, 0);

    _hWnd = ::CreateWindowEx(dwExStyle,
                             WINCLS_UUID,
                             (WCHAR *)LoadString(g_hInstance, IDS_STBIHOST, NULL, 0),
                             dwStyle,
                             rcArea.left,
                             rcArea.top,
                             rcArea.right - rcArea.left,
                             rcArea.bottom - rcArea.top,
                             NULL, hMenu, g_hInstance, 0);
    if (!_hWnd)
        return FALSE;

    SetWindowLong(_hWnd, GWL_USERDATA, (DWORD)this);
    GetWindowRect(_hWnd, &_rcWnd);

    // create a "safe area" to prevent the browser
    // control (and the progress bar) from displaying
    // graphics that bleed off the edges of the TV screen
    _lSafeWidth = (LONG)((_rcWnd.right - _rcWnd.left) * SAFEAREA_MARGIN);
    _lSafeHeight = (LONG)((_rcWnd.bottom - _rcWnd.top) * SAFEAREA_MARGIN);
    _ptSafe.x = (LONG)((_rcWnd.right - _rcWnd.left - _lSafeWidth)/2);
    _ptSafe.y = (LONG)((_rcWnd.bottom - _rcWnd.top - _lSafeHeight)/2);


    // create a progress bar
    _rcProgress.left = _ptSafe.x + 5;
    _rcProgress.top = _ptSafe.y + 5;
    _rcProgress.right = _rcProgress.left + _lSafeWidth/3;
    _rcProgress.bottom = _rcProgress.top + 15;

    _hwndProgress = CreateWindowEx(WS_EX_NOACTIVATE, PROGRESS_CLASS,
                                   _T(""), WS_CHILD|PBS_SMOOTH|WS_BORDER,
                                   _rcProgress.left, _rcProgress.top,
                                   _rcProgress.right-_rcProgress.left,
                                   _rcProgress.bottom-_rcProgress.top,
                                   _hWnd, NULL, g_hInstance, NULL);
    
    if (_hwndProgress)
        SendMessage(_hwndProgress, PBM_SETRANGE32, 0, 1000);

    if (!(_hWndBrowser = CreateBrowser()))
        return FALSE;

    // LONG lStyle = GetWindowLong(_hWndBrowser, GWL_STYLE);
    // SetWindowLong(_hWndBrowser, GWL_STYLE, lStyle|WS_BORDER);

	// use the safe area to resize the web control
	EnableSafeArea(TRUE);
 
	SetFocus(_hWnd);

    _hAccelTblDef = LoadAccelerators(g_hInstance, 
    					MAKEINTRESOURCE(IDR_ACCELERATOR));

    return TRUE;
}



void GetProxyOption()
{
	INTERNET_PER_CONN_OPTION_LIST	iOptionList;
	INTERNET_PER_CONN_OPTION		iOptions[3];
	ULONG							uSize = sizeof(iOptionList);

	iOptionList.dwSize			= uSize;
	iOptionList.pszConnection	= NULL;
	iOptionList.dwOptionCount	= 3;
	iOptionList.pOptions		= iOptions;

	// set proxy type direct or proxy server
	iOptions[0].dwOption	= INTERNET_PER_CONN_FLAGS;
	iOptions[1].dwOption	= INTERNET_PER_CONN_PROXY_SERVER;
	iOptions[2].dwOption	= INTERNET_PER_CONN_PROXY_BYPASS;
	
	if(InternetQueryOption(NULL,INTERNET_OPTION_PER_CONNECTION_OPTION ,(LPVOID)(&iOptionList),&uSize))
	{
		GlobalFree(iOptionList.pOptions[1].Value.pszValue);
		GlobalFree(iOptionList.pOptions[2].Value.pszValue);
	}
}

HWND CMainWnd::CreateBrowser()
{
    HRESULT hr;
    IUnknown *pUnk = NULL;
    IOleObject *pObject = NULL;


    if (!_pBrowser)
    {
		GetProxyOption();
        hr = CoCreateInstance(CLSID_WebBrowser, NULL,
                              CLSCTX_INPROC_SERVER | CLSCTX_INPROC_HANDLER,
                              IID_IUnknown, (LPVOID *)(&pUnk));
        if (hr)
            return FALSE;

        hr = pUnk->QueryInterface(IID_IOleObject, (LPVOID *)(&pObject));
        if (hr)
            goto Cleanup;

        DWORD dwFlags;
        hr = pObject->GetMiscStatus(DVASPECT_CONTENT, &dwFlags);
        if (hr)
            goto Cleanup;

        if (dwFlags & OLEMISC_SETCLIENTSITEFIRST)
        {
            IOleClientSite *pClientSite;
            hr = QueryInterface(IID_IOleClientSite, (LPVOID *)(&pClientSite));
            if (hr)
                goto Cleanup;

            hr = pObject->SetClientSite(pClientSite);
            pClientSite->Release();
            if (hr)
                goto Cleanup;
        }

        hr = Activate(pObject);
        if (hr)
            goto Cleanup;

        hr = _pObject->QueryInterface(IID_IWebBrowser2, (void **)&_pBrowser);
        if (hr)
            goto Cleanup;

        // See if there might be a url in lpszUrl
        hr = pUnk->QueryInterface(IID_IOleInPlaceActiveObject, (LPVOID *)(&_pIPActiveObj));
        if (S_OK!=hr)
			_pIPActiveObj = NULL;

        hr = S_FALSE;

        if (_fEmpty)
        {
            if (_lpszUrl)
            {
                LPTSTR lpszUrlAlpha = _lpszUrl;

                while (hr == S_FALSE && *lpszUrlAlpha != _T('\0'))
                {
                    if (_istalpha(*lpszUrlAlpha))
                        hr = S_OK;

                    lpszUrlAlpha++;
                }
            }

            if (hr == S_OK)
                _pBrowser->Navigate(_lpszUrl, NULL, NULL, NULL, NULL);
            else
                _pBrowser->GoHome();
        }
        hr = InitEvents();
    }

Cleanup:
    if (pUnk)
        pUnk->Release();
    if (pObject)
        pObject->Release();

    IOleWindow *pWnd = NULL;
    HWND hwndBrowser = NULL;

    if (_pBrowser)
    {
        hr = _pBrowser->QueryInterface(IID_IOleWindow, (LPVOID *)(&pWnd));
        if (hr)
            return NULL;
    }

    if (pWnd)
    {
        hr = pWnd->GetWindow(&hwndBrowser);
        pWnd->Release();
    }
    return hwndBrowser;
}

HRESULT CMainWnd::Activate(IOleObject *pObject)
{
    _pObject = pObject;
    _pObject->AddRef();

    RECT rc;
    ::GetClientRect(_hWnd, &rc);

    HRESULT hr;
    hr    =    _pObject->DoVerb(   OLEIVERB_UIACTIVATE,    NULL,    this,    0,    _hWnd,    &rc);

    if (hr)
        goto Cleanup;

    Cleanup:
    return hr;
}

HRESULT CMainWnd::InitEvents()
{
    HRESULT                     hr;
    IConnectionPointContainer  *pCPCont = NULL;
    DWebBrowserEvents          *pEvents = NULL;

    if (!_pBrowser)
        return S_FALSE;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -