我们已经在Windows上实现了从零构建一个CEF3项目。现在我们在其基础上实现Duilib图形。
Of Course,你可以理解为 在Duilib的基础上嵌入Cef浏览器。
获取Duilib源码,请到Duilib -Github
关于如何编译Duilib库,请参考资料duilib入门简明教程 -Albert
文件导入
以下以Unicode Debug为例。
将Duilib编译后生成的 DuiLib_ud.lib
文件添加到 C:\workspace\cef3\MyCef\lib
文件夹内。
将Duilib源码 include文件夹
添加到 C:\workspace\cef3\MyCef
文件夹内。
将Duilib_ud.dll
文件添加到解决方案跟目录的Debug文件夹内。
解决方案属性设置
打开解决方案属性页面,选择 VC++目录 → 包含目录 添加../include
,如下图:
image.png
修改 simple_app.cc
替换 simple_app.cc 文件中此方法代码(就是删了剩下的,只留了一行)
void SimpleApp::OnContextInitialized() {
CEF_REQUIRE_UI_THREAD();
}
编写主窗口类
新建类 CMainFrame 。
【MainFrame.h 代码清单】
#pragma once
#ifdef _DEBUG
# ifdef _UNICODE
# pragma comment(lib, "DuiLib_ud.lib")
# else
# pragma comment(lib, "DuiLib_d.lib")
# endif
#else
# ifdef _UNICODE
# pragma comment(lib, "DuiLib_u.lib")
# else
# pragma comment(lib, "DuiLib.lib")
# endif
#endif
#include <UIlib.h>
using namespace DuiLib;
class CMainFrame :
public WindowImplBase
{
public:
CMainFrame();
~CMainFrame();
LPCTSTR GetWindowClassName() const;
virtual CDuiString GetSkinFile();
virtual CDuiString GetSkinFolder();
virtual void InitWindow();
};
【MainFrame.cpp 代码清单】
#include "cefsimple\simple_app.h"
#include "cefsimple\simple_handler.h"
#include "MainFrame.h"
CefRefPtr<SimpleHandler> g_handler(new SimpleHandler());
CMainFrame::CMainFrame()
{
}
CMainFrame::~CMainFrame()
{
}
LPCTSTR CMainFrame::GetWindowClassName() const
{
return _T("DuilibCef");
}
CDuiString CMainFrame::GetSkinFile()
{
return _T("skin\\MainWindow.xml");
}
CDuiString CMainFrame::GetSkinFolder()
{
return _T("");
}
void CMainFrame::InitWindow()
{
RECT rect;
GetClientRect(this->m_hWnd, &rect);
int nCx = GetSystemMetrics(SM_CXFULLSCREEN);
int nCy = GetSystemMetrics(SM_CYFULLSCREEN);
RECT rt;
rt.left = rect.left + 0;
rt.top = rect.top + 0;
rt.bottom = rt.top + 600;
rt.right = rt.left + 800;
CefBrowserSettings browser_settings;
CefWindowInfo window_info;
window_info.SetAsChild(m_hWnd, rt);
BOOL bSucced = CefBrowserHost::CreateBrowser(window_info
, g_handler
, _T("http://www.baidu.com/")
, browser_settings
, NULL);
}
修改入口文件
【cefsimple_win.cc 代码清单】
// Copyright (c) 2013 The Chromium Embedded Framework Authors. All rights
// reserved. Use of this source code is governed by a BSD-style license that
// can be found in the LICENSE file.
#pragma comment(lib, "libcef_dll_wrapper.lib")
#pragma comment(lib, "cef_sandbox.lib")
#pragma comment(lib, "libcef.lib")
#include <windows.h>
#include "cefsimple/simple_app.h"
#include "include/cef_sandbox_win.h"
#include "MainFrame.h"
// When generating projects with CMake the CEF_USE_SANDBOX value will be defined
// automatically if using the required compiler version. Pass -DUSE_SANDBOX=OFF
// to the CMake command-line to disable use of the sandbox.
// Uncomment this line to manually enable sandbox support.
// #define CEF_USE_SANDBOX 1
#if defined(CEF_USE_SANDBOX)
// The cef_sandbox.lib static library is currently built with VS2013. It may not
// link successfully with other VS versions.
#pragma comment(lib, "cef_sandbox.lib")
#endif
// Entry point function for all processes.
int APIENTRY wWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow) {
/* UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);*/
CPaintManagerUI::SetInstance(hInstance);
#if defined(WIN32) && !defined(UNDER_CE)
HRESULT Hr = ::CoInitialize(NULL);
#else
HRESULT Hr = ::CoInitializeEx(NULL, COINIT_MULTITHREADED);
#endif
if (FAILED(Hr)) return 0;
// Enable High-DPI support on Windows 7 or newer.
CefEnableHighDPISupport();
void* sandbox_info = NULL;
#if defined(CEF_USE_SANDBOX)
// Manage the life span of the sandbox information object. This is necessary
// for sandbox support on Windows. See cef_sandbox_win.h for complete details.
CefScopedSandboxInfo scoped_sandbox;
sandbox_info = scoped_sandbox.sandbox_info();
#endif
// Provide CEF with command-line arguments.
CefMainArgs main_args(hInstance);
// SimpleApp implements application-level callbacks. It will create the first
// browser instance in OnContextInitialized() after CEF has initialized.
CefRefPtr<SimpleApp> app(new SimpleApp);
// CEF applications have multiple sub-processes (render, plugin, GPU, etc)
// that share the same executable. This function checks the command-line and,
// if this is a sub-process, executes the appropriate logic.
int exit_code = CefExecuteProcess(main_args, app.get(), sandbox_info);
if (exit_code >= 0) {
// The sub-process has completed so return here.
return exit_code;
}
// Specify CEF global settings here.
CefSettings settings;
#if !defined(CEF_USE_SANDBOX)
settings.no_sandbox = true;
#endif
// Initialize CEF.
CefInitialize(main_args, settings, app.get(), sandbox_info);
CMainFrame* pFrame = new CMainFrame();
if (pFrame == NULL) return 0;
HANDLE mainHandle = NULL;
#if defined(WIN32) && !defined(UNDER_CE)
mainHandle = pFrame->Create(NULL, _T("PLApp"), UI_WNDSTYLE_FRAME, WS_EX_STATICEDGE | WS_EX_APPWINDOW, 0, 0, 600, 800);
#else
mainHandle = pFrame->Create(NULL, _T("PLApp"), UI_WNDSTYLE_DIALOG, WS_EX_TOPMOST, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN));
#endif
pFrame->CenterWindow();
::ShowWindow(*pFrame, SW_SHOW);
// Run the CEF message loop. This will block until CefQuitMessageLoop() is
// called.
CefRunMessageLoop();
// Shut down CEF.
CefShutdown();
return 0;
}