皮皮网

【021溯源码燕窝】【扫码签到 源码】【旺财考勤源码】cef源码版本

2024-12-29 01:53:00 来源:最好收银系统源码

1.使用CEF(四)— 在QT中集成CEF(1)基本集成
2.探索chrome二进制大小的码版变迁和剪裁chromium的一些思路
3.浅析Selenium-WebDriver
4.如何利用CEF3创建一个简单的应用程序
5.Qt中嵌入web网页的几种实现方式
6.chromium+embedded+framework能卸载吗?

cef源码版本

使用CEF(四)— 在QT中集成CEF(1)基本集成

       在QT,一个强大的码版跨平台C++开发框架,上构建基于CEF(Chrome Embedded Framework)的码版应用程序,我们之前的码版文章已经展示了基础的样例,但这些示例主要依赖原生或功能有限的码版CEF视图。本文将重新开始,码版021溯源码燕窝通过VS,码版实现一个结合QT和原生窗体的码版集成项目。

       环境搭建

       本文不依赖QtCreator,码版而是码版使用VS和Qt VS Tools来构建环境,前提是码版你已安装并熟悉QT。

       安装Qt VS Tools插件

       在VS扩展中搜索并安装相应的码版QT插件,安装后别忘了重启VS。码版

       配置Qt环境

       在Extensions - Qt VS Tools - Options中,码版配置Qt-VS编译设置。码版

       创建Qt项目

       在配置完成后,通过VS创建项目,Qt模板将自动出现。我们创建名为QtCefDemo的项目,Qt创建向导随即启动。

       项目结构

       创建完成后,项目的文件结构如下,展示了一个基本的VS IDE下的QT项目。

       集成CEF环境

       为了集成CEF,我们首先需要编译并准备相应的扫码签到 源码头文件、库文件和资源文件,包括libcef_dll_wrapper.lib(MDd和MD版本)。

       项目目录结构

       按照步骤,你会看到项目的文件夹结构,包括CefFiles文件夹及其内部的头文件、库文件和资源。

       配置manifest文件和VS设置

       为CEF项目配置manifest文件,以及头文件和库文件的路径,这里会根据Debug和Release环境自动调整。

       集成完成后的问题与解决方案

       在集成过程中,可能会遇到运行时的库文件问题。需要手动或通过脚本将相关文件复制到输出目录。初始运行可能存在问题,但后续文章将深入探讨解决方法。

       源码和资源

       项目源码可以在我的GitHub仓库找到,链接在此省略。此外,需要下载CefFiles文件夹,可以从网盘获取,链接同样省略。

探索chrome二进制大小的变迁和剪裁chromium的一些思路

       研究chromium源码的价值不仅在于学习,还在于商业应用,但随着版本升级,cef的旺财考勤源码大小从MB增长至MB,对注重安装包大小的开发者来说,寻求减小chromium内核尺寸是一个挑战。本文通过对比历史版本,探究chrome二进制文件的变化,为裁剪chromium提供策略。

       首先,对比不同版本chrome的Windows 位安装包,发现从MB增长到MB,我们挑选了变化显著的包进行详细分析(红色箭头标出)。解压后,逐版本对比安装包内的文件大小变化,以及各文件占总大小的百分比变化。

       chrome.dll的体积持续增长,占总大小的比例也不断提升,但其他模块总体趋势向小型化发展。在chrome.dll模块分析中,发现至版本,chrome_child.dll的合并抑制了体积增长;至版本,notification_helper.exe等模块的合并导致显著增长。这说明模块合并对整体体积控制有积极作用,但同时也增加了去除特定功能的难度。

       特别指出,3D模块的增长显著,删除支持3D相关的魂斗罗小程序源码文件可减小MB。snapshot技术优化带来体积减少,部分隐藏在chrome.dll中。资源相关的文件体积明显减小,如icudtl.dat,可通过裁剪减少到几十KB。

       关于裁剪思路,虽然chromium编译中间产物有3w多个obj文件,但我们通过分析Top 文件,发现v8和third_party模块的体积较大。通过一级目录聚合,可以看出v8和third_party\blink的体积不容忽视。进一步细分,blink的core和bindings模块对二进制贡献较大,而v8的优化则需更细致的处理。

       特别值得关注的是,perfetto的trace_processor模块和pdfium、libjxl、dawn、webrtc等第三方库对体积影响较大。考虑使用V8的V8Lite模式和裁剪jit、wasm模块,能有效减少V8体积。然而,这些基于编译中间产物的htm的游戏源码分析可能与最终dll大小存在偏差,一般能减小-%的体积。

       总的来说,理解chromium源码和运行方式有助于优化,对开发者来说,这是一次从不同角度深入了解chromium的机会。欢迎交流和学习。

浅析Selenium-WebDriver

       年,当时在ThoughtWorks工作的Jason Huggins开发了Selenium(Selenium RC)的第一版。年,Google工程师基于Selenium开发了WebDriver。年,Selenium和WebDriver合并,形成了Selenium2(Selenium WebDriver)。目前,Selenium WebDriver的模式已经升级到Selenium4,并有一个支线项目Selenium-Grid,能够与Selenium配合进行多任务运行(主要针对分布式执行,对于当前业务现状,使用到的可能性很小,本文不展开讲解)。

       使用现状:虽然无法直接统计出每个公司的使用现状,但我们可以通过搜索趋势来侧面验证。通过Google Trends查询的结果显示,Selenium WebDriver主导的方案占据主流地位,而Selenium RC的方案正在逐步被淘汰。

       Selenium RC:

       组成部分:Selenium RC主要由客户端和服务器两部分组成。

       工作原理:Selenium RC通过发送HTTP请求与服务器进行通信,服务器再将请求转发给浏览器执行。

       缺点:Selenium RC的执行速度较慢,且需要各个浏览器厂商提供支持。

       Selenium WebDriver:

       组成部分:WebDriver主要由WebDriver接口和对应的浏览器驱动程序组成。

       Web Driver:WebDriver提供了另一种与浏览器交互的方式,即利用浏览器原生的API,封装成一套面向对象的Selenium WebDriver API,直接操作浏览器页面里的元素,甚至操作浏览器本身(截屏、窗口大小、启动、关闭、安装插件、配置证书等)。由于使用的是浏览器的原生API,速度大大提高,但缺点是需要各个浏览器厂商各自提供。

       各种编程语言编写的客户端:向remote server发起请求。

       工作原理:底层通信包含以下两个过程:

       Selenium -> ChromeDriver server:这个通信过程是基于HTTP协议。

       例如,我们要打开一个浏览器页面,并访问www.google.com,先看下Selenium源码是怎么实现这个过程的。

       首次建立连接的过程:

       选择一个空闲的端口启动chromedriver。

       具体发请求的接口:

       最终的收口就是_request,发起一个blogs.com/uncleyong/p...

       [8] cloud.tencent.com/devel...

       [9] einverne.gitbook.io/sel...

如何利用CEF3创建一个简单的应用程序

       å¼€å§‹

       é¦–先,根据自身所使用的开发平台,可以去 这里 下载对应的发布版本。针对这个教程,我们需要下载或者更新的版本。当前支持的平台有Windows, Linux和Mac OS X。每一个版本都包含了当在特定平台上编译特定版本CEF3时所需要的所有文件和资源。您可以通过包含在里边的 REDME.txt 文件或者在Wiki上GeneralUsage 中的 Getting Started,了解每个发布版本的具体内容和细节。

       ç¼–译发布版本中的项目

       ä»¥CEF发布版本为基础开发的应用程序可以使用标准的平台编译工具进行编译执行。包括 Windows 平台下的 Visual Studio, Mac OS X 平台下的 Xcode, 以及 Linux 平台下的 gcc/make。针对平台的不同,项目的编译过程也有些许的不同和要求。

       Windows

       Windows 平台下编译 Cefsimple 步骤:

       1. 用对应的 Visual Studio 版本打开项目解决方案。举个例子,如果你安装的是 Visual Studio , 那么,打开的就是 cesimple.sln。

       2. 如果你下载的是 x版本,请确保你选择的是 x的开发平台。

       3. 开始编译。

       4. 如果编译通过,那么,在当前解决方案的目录下,将出现逗out/Debug地(或者 逗out/Release地)文件夹。

       5. 执行文件夹下 cefsimple.exe, 确保能正确运行。

       åŠ è½½ä¸€ä¸ªè‡ªå®šä¹‰URL

       cefsimple项目中默认加载的URL是 google.com,当然,你也可以用自定义的 URL 去替代它,最方便的就是通过命令行搞定。

       # Load the local file 逗c:\example\example.html地

       cefsimple.exe --url=file://c:/example/example.html

       é™¤äº†å‘½ä»¤è¡Œçš„方法,也可以通过直接修改在 cefsimple/simple.cpp 文件中的代码,达到你的目的。

       # Load the local file 逗c:\example\example.html地

       â€¦

        if (url.empty())

        url = file://c:/example/example.html;

       åº”用程序组成

       æ‰€æœ‰çš„ CEF 应用程序都有一下主要组成部分:

       1. CEF 的动态链接库 。(在 Windows 平台下就是 libcef.dll)

       2. 支持库。(ICU, FFMPEG等)

       3. 资源。(html/js/css, strings等)

       4. 客户端执行文件。(本教程中就是 cefsimple.exe.)

       è¦ç‚¹ï¼ˆå¿…看)

       1. CEF 使用的是多进程。应用程序主进程是浏览器进程,而其他子进程是由 renderer, plugins, GPU等创建。

       2. 在 Windows 和 Linux 平台下的执行文件可以被主进程和子进程使用。

       3. CEF 中所有进程都可以是多线程的。CEF提供了许多功能和接口在不同的线程中传递任务。

       4. 一些回调方法和函数只能在特定的进程或者线程中使用。在你第一次使用新的回调方法或者函数之前,请确保你已经阅读了 API 头文件中源码,看使用要求。

       æµç¨‹åˆ†æž

       cefsimple 应用程序首先初始化CEF,然后创建了一个简单的弹出浏览器窗口。当关闭了所有的浏览器窗口,应用程序就会结束。程序执行流程如下:

       1. 系统执行入口点函数(main or wWinMain),并创建浏览器进程。

       2. 入口点函数:

       1. 创建能够处理进程级别的回调方法的 SimpleApp 实例。

       2. 初始化 CEF,进入 CEF 消息循环。

       3. 初始化 CEF 之后,调用 SimpleApp::OnContextInitialized() 。这个方法中:

       1. 创建单例的 SimpleHandler 。

       2. 由 CefBrowserHost::CreateBrowsersync() 方法创建一个浏览器窗口。

       4. 所有的浏览器共享 SimpleHandler 实例, 此实例能定制浏览器行为、处理浏览器相关回调方法(life span, loading state, title display等)。

       5. 当一个浏览器窗口关闭的时候,调用 SimpleHandler::OnBeforeClose() 。当所有的浏览器窗口全部关闭时,OnBeforeClose() 函数就会执行跳出 CEF 消息循环的行为,退出应用程序。

       å…¥å£ç‚¹å‡½æ•°

       ç¨‹åºçš„运行开始于浏览器进程中的入口点函数。这个函数会初始化 CEF 以及所有跟操作系统有关的对象。

       Windows

       #include <windows.h>

       #include "cefsimple/simple_app.h"

       #include "include/cef_sandbox_win.h"

       // Set to 0 to disable sandbox support.

       #define CEF_ENABLE_SANDBOX 1

       #if CEF_ENABLE_SANDBOX

       // The cef_sandbox.lib static library is currently built with VS. 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);

        void* sandbox_info = NULL;

       #if CEF_ENABLE_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 !CEF_ENABLE_SANDBOX

        settings.no_sandbox = true;

       #endif

        // Initialize CEF.

        CefInitialize(main_args, settings, app.get(), sandbox_info);

        // Run the CEF message loop. This will block until CefQuitMessageLoop() is

        // called.

        CefRunMessageLoop();

        // Shut down CEF.

        CefShutdown();

        return 0;

       }

       SimpleApp

       SimpleApp 负责处理进程级别的回调方法。它会曝露出一些在多进程中共享或者被特定进程使用的接口和方法。CefBrowserProcessHandler 接口,在浏览器进程中调用。还有一个被分离出 CefBrowserProcessHandler 接口(例子项目没有展示)只会在渲染进程中被调用。由于 CefBrowserProcessHandler 不光实现了 CefApp, 同时还有 CefBrowserProcessHandler,所以它的返回值必须是[this]。

       // simple_app.h

       #include "include/cef_app.h"

       class SimpleApp : public CefApp,

        public CefBrowserProcessHandler {

        public:

        SimpleApp();

        // CefApp methods:

        virtual CefRefPtr<CefBrowserProcessHandler> GetBrowserProcessHandler()

        OVERRIDE { return this; }

        // CefBrowserProcessHandler methods:

        virtual void OnContextInitialized() OVERRIDE;

        private:

        // Include the default reference counting implementation.

        IMPLEMENT_REFCOUNTING(SimpleApp);

       };

       // simple_app.cpp

       #include "cefsimple/simple_app.h"

       #include <string>

       #include "cefsimple/simple_handler.h"

       #include "cefsimple/util.h"

       #include "include/cef_browser.h"

       #include "include/cef_command_line.h"

       SimpleApp::SimpleApp() {

       }

       void SimpleApp::OnContextInitialized() {

        REQUIRE_UI_THREAD();

        // Information used when creating the native window.

        CefWindowInfo window_info;

       #if defined(OS_WIN)

        // On Windows we need to specify certain flags that will be passed to

        // CreateWindowEx().

        window_info.SetAsPopup(NULL, "cefsimple");

       #endif

        // SimpleHandler implements browser-level callbacks.

        CefRefPtr<SimpleHandler> handler(new SimpleHandler());

        // Specify CEF browser settings here.

        CefBrowserSettings browser_settings;

        std::string url;

        // Check if a "--url=" value was provided via the command-line. If so, use

        // that instead of the default URL.

        CefRefPtr<CefCommandLine> command_line =

        CefCommandLine::GetGlobalCommandLine();

        url = command_line->GetSwitchValue("url");

        if (url.empty())

        url = "";

        // Create the first browser window.

        CefBrowserHost::CreateBrowserSync(window_info, handler.get(), url,

        browser_settings, NULL);

       }

       SimpleHandler

       SimpleHandler 负责处理浏览器级别的回调方法。这些回调方法会在浏览器进程中执行。在这个项目中,针对所有的浏览器使用相同的 CefClient 实例,但是如果你愿意,可以在自己的应用程序中使用不同的 CefClient实例的。

       // simple_handler.h

       #include "include/cef_client.h"

       #include <list>

       class SimpleHandler : public CefClient,

        public CefDisplayHandler,

        public CefLifeSpanHandler,

        public CefLoadHandler {

        public:

        SimpleHandler();

        ~SimpleHandler();

        // Provide access to the single global instance of this object.

        static SimpleHandler* GetInstance();

        // CefClient methods:

        virtual CefRefPtr<CefDisplayHandler> GetDisplayHandler() OVERRIDE {

        return this;

        }

        virtual CefRefPtr<CefLifeSpanHandler> GetLifeSpanHandler() OVERRIDE {

        return this;

        }

        virtual CefRefPtr<CefLoadHandler> GetLoadHandler() OVERRIDE {

        return this;

        }

        // CefDisplayHandler methods:

        virtual void OnTitleChange(CefRefPtr<CefBrowser> browser,

        const CefString& title) OVERRIDE;

        // CefLifeSpanHandler methods:

        virtual void OnAfterCreated(CefRefPtr<CefBrowser> browser) OVERRIDE;

        virtual void OnBeforeClose(CefRefPtr<CefBrowser> browser) OVERRIDE;

        // CefLoadHandler methods:

        virtual void OnLoadError(CefRefPtr<CefBrowser> browser,

        CefRefPtr<CefFrame> frame,

        ErrorCode errorCode,

        const CefString& errorText,

        const CefString& failedUrl) OVERRIDE;

        // Request that all existing browser windows close.

        void CloseAllBrowsers(bool force_close);

        private:

        // List of existing browser windows. Only accessed on the CEF UI thread.

        typedef std::list<CefRefPtr<CefBrowser> > BrowserList;

        BrowserList browser_list_;

        // Include the default reference counting implementation.

        IMPLEMENT_REFCOUNTING(SimpleHandler);

       };

       // simple_handler.cpp

       #include "cefsimple/simple_handler.h"

       #include <sstream>

       #include <string>

       #include "cefsimple/util.h"

       #include "include/cef_app.h"

       #include "include/cef_runnable.h"

       namespace {

       SimpleHandler* g_instance = NULL;

Qt中嵌入web网页的几种实现方式

       Web网页的界面交互相较于Qt客户端拥有较大优势,能提供丰富且便捷的用户体验,使得在客户端中嵌入web网页成为可能。这能结合web的优势与客户端特性,丰富界面功能。本文将介绍几种Qt客户端中嵌入web网页的实现方式及步骤。

       基于Qt自带控件实现

       Qt内置的控件用于访问网页,集成webkit内核与google引擎,类似简易版浏览器。此方案在Qt5.9.6中采用QWebEngineView。

       环境配置:Qt5.9.6 + VS

       检查webenginewidgets模块是否配置成功。

       开发流程:通过拖拽控件或直接new使用,代码示例与效果展示。

       总结:实现简单,但浏览器内核不支持视频解码,需编译源码解决,成本较高。

       嵌入Chrome.exe进程实现

       此方法启动本地Chrome浏览器,实现与本地浏览器功能等同。通过启动浏览器进程并传入参数,再获取窗口句柄,实现嵌入。

       环境配置:Qt5.9.6 + VS

       检测Chrome安装情况,获取Chrome.exe路径。

       开发流程:启动Chrome.exe,获取窗口句柄,转化为QWindow,嵌入界面。

       总结:功能完整,但浏览器状态与客户端状态耦合,用户行为影响嵌入界面显示。

       基于Chrome的CEF3实现

       Chromium Embedded Framework(CEF)提供嵌入式浏览器支持。此方案需下载编译包,参照官方文档,实现嵌入网页界面。

       环境配置:Qt5.9.6 + VS

       下载并配置CEF与chromium源码。

       开发流程:参考示例文档,配置工程,实现嵌入。

       总结:功能完整,但受限于源码编译环境,实际使用效果受限。

       基于微软的WebView2实现

       Microsoft Edge WebView2 控件允许嵌入Web技术(HTML、CSS、JavaScript)到本机应用程序。此方案通过读取进程窗口句柄实现嵌入。

       环境配置:Qt5.9.6 + VS,安装WebView2运行包。

       开发流程:下载示例文档,配置NuGet包,启动WebView2进程,读取窗口句柄,嵌入界面。

       总结:实现简单,功能与用户体验较好,但无法国产化。

       总结

       根据需求选择不同方案:仅显示网页时,推荐基于Qt自带控件;需视频播放时,考虑基于CEF的实现;受限环境,可选用WebView2。嵌入Chrome.exe方案存在不可控因素,不适合作为常规方案。通过比较不同方法的优缺点,可选最优方案满足需求。

chromium+embedded+framework能卸载吗?

       Chromium Embedded Framework(CEF)本身是一个开源的框架,可以通过GitHub等开源平台获取其源代码。由于其是一个框架,因此不是一个独立的应用程序,而是被其他应用程序(例如Web浏览器)所使用。因此,CEF本身无法被卸载。

       如果您想卸载使用CEF构建的应用程序,可以通过以下方式进行:

       在操作系统中找到该应用程序的卸载程序,一般可以在“控制面板”或者应用程序的安装目录中找到。运行卸载程序后,该应用程序及其使用的CEF框架将被卸载。

       如果无法通过卸载程序进行卸载,可以尝试使用第三方卸载工具,例如Revo Uninstaller等。

       需要注意的是,在卸载使用CEF构建的应用程序之前,请确保该应用程序中的所有数据已经备份或者转移至其他地方,以免造成数据丢失。