手把手教你使用CefSharp开发Winform(Winform中使用浏览器处理html页面) | 您所在的位置:网站首页 › 用ie浏览器怎么找到摄像头位置 › 手把手教你使用CefSharp开发Winform(Winform中使用浏览器处理html页面) |
第一步:了解什么是CefSharp CefSharp简单来说就是一款.Net编写的浏览器包,方便你在Winform和WPF中内嵌的Chrome浏览器组件,用过Chrome内核组件来加载处理html页面,以此实现你在winform中访问网页或处理html页面。 为什么要使用CefSharp?个人觉得有以下方面好处: 1)当你无法用winform控件来实现一些界面样式或者html才能实现的一些功能的时候,你就需要将你的winform界面改为html+js来处理,比如:echart丰富的报表,高大上的智慧中心大屏; 2)当你开发的是B/S架构的在线应用,但是在使用过程中又需要访问本地电脑的硬件的时候,普通的浏览器无法达到效果,就通过C#来处理与硬件的交互,并把处理方法暴露给前端html来通过JS调用,比如:调用读卡器,扫描仪,摄像头等; 3)你自己发挥想象,比如需要编写winform窗体与html页面混合的应用程序,并且需要进行交互的时候。 GitHub地址:传送门 wiki帮助文档地址:传送门 CefSharp最小的示例工程:传送门 gitter交流讨论区:传送门 第二步:准备搭建环境及工具 1)所需环境及工具: ① Visual Studio(个人建议2015及以上) ② CefSharp.WinForms及其依赖的包(我使用的最新版是84.0.0): CefSharp.WinForms Nuget包 CefSharp.Common Nuget包 cef.redist.x64 Nuget包 ③ .Net Framework4.5.2 2)创建Winform项目; 在VS中新建一个“Windows窗体应用程序”(Winform工程)。 3)引用CefSharp 网上有很多教程是教你如何将CefSharp.WinForms及其依赖包下载的本地再添加引用。其实没必要,nuget网速也不至于这么差。 直接在项目中通过程序包管理器的NuGet 命令来添加引用就行。 在程序包管理器控制台输入以下命令安装CefSharp.WinForms: Install-Package CefSharp.WinForms 在程序包管理器控制台输入以下命令安装CefSharp.Common: Install-Package CefSharp.Common 在安装CefSharp.Common的时候,nuget会自动安装cef.redist.x64和cef.redist.x86.所以真的不需要像其他文章说的那样,一个个下载下来手动安装; 4)修改.net 目标框架为4.5.2以上或以上版本
5)配置管理器选择目标平台 CefSharp在Any CPU平台下无法正常运行。所以要修改配置。选中解决方案名称右键,进入解决方案属性页。找到配置属性,然后将目标平台改为x86或者x64。;
第三步:开始搭建一个Winform浏览器 form窗体中添加一个变量; 然后在Form1方法中编写以下代码(注意,以下代码只能在Form窗体方法中添加,不能写在Form_Load方法中; // Start the browser after initialize global component CefSettings settings = new CefSettings(); string page = "http://baidu.com"; // Initialize cef with the provided settings Cef.Initialize(settings); // Create a browser component chromeBrowser = new ChromiumWebBrowser(page); // Add it to the form and fill it to the form window. this.Controls.Add(chromeBrowser); chromeBrowser.Dock = DockStyle.Fill; // Allow the use of local resources in the browser BrowserSettings browserSettings = new BrowserSettings(); browserSettings.FileAccessFromFileUrls = CefState.Enabled; browserSettings.UniversalAccessFromFileUrls = CefState.Enabled; chromeBrowser.BrowserSettings = browserSettings;然后运行就可以看到效果; 除了访问web在线网页以外,还可访问本地的html页面。只需要将网页链接地址替换为本地html页面地址(绝对路径),第四步会有讲到如何访问本地html页面;
第四步:使用JS调用C#方法进行交互 如果要访问本地的html页面,则可以将html页面文件放置在程序根目录,这样方便程序拷贝到任何地方,只要同路径都可以访问; 1)首先,我们将需要访问的html以及css样式文件,js脚本文件等拷贝到程序根目录下。 2)然后修改之前我们编写的代码。新建一个方法名InitializeChromium()。将我们之前写好的代码放入里面。并将访问页面改为本地html地址; /// /// 初始化浏览器并启动 /// public void InitializeChromium() { CefSettings settings = new CefSettings(); // 获取本地html路径地址 String page = string.Format(@"{0}\ViewData\html\Index.html", Application.StartupPath); if (!File.Exists(page)) { MessageBox.Show("Error The html file doesn't exists : " + page); } // Initialize cef with the provided settings Cef.Initialize(settings); // Create a browser component chromeBrowser = new ChromiumWebBrowser(page); // Add it to the form and fill it to the form window. this.Controls.Add(chromeBrowser); chromeBrowser.Dock = DockStyle.Fill; // Allow the use of local resources in the browser BrowserSettings browserSettings = new BrowserSettings(); browserSettings.FileAccessFromFileUrls = CefState.Enabled; browserSettings.UniversalAccessFromFileUrls = CefState.Enabled; chromeBrowser.BrowserSettings = browserSettings; }3)然后再Form1方法中调用InitializeChromium(); 4)接下来我们编写与前端JS交互的方法; 新建一个类,我取名为CefCustomObject。然后编写初始化类的代码和需要被调用方法的代码; public class CefCustomObject { // Declare a local instance of chromium and the main form in order to execute things from here in the main thread private static ChromiumWebBrowser _instanceBrowser = null; // The form class needs to be changed according to yours private static Form1 _instanceMainForm = null; public CefCustomObject(ChromiumWebBrowser originalBrowser, Form1 mainForm) { _instanceBrowser = originalBrowser; _instanceMainForm = mainForm; } /// /// 窗口加载完毕时需要出发的全局JS对象; /// public void OnFrameLoadEnd(object sender, FrameLoadEndEventArgs e) { if (e.Frame.IsMain) { _instanceBrowser.ExecuteScriptAsync(@" document.body.onmouseup = function() { bound.onSelected(window.getSelection().toString()); } "); } } /// /// 显示一个弹出对话框,前端JS调用的方法 /// /// 传入参数 public void showAlertMsg(string msg) { MessageBox.Show("The user selected some text [" + msg + "]"); } // 自定义被JS调用的方法,读取身份证信息 public string ReadIdCard() { // 具体调用读身份证读卡器的方法 // IDCardModel model=IDCardSdk.Read(); //将身份证信息返回给前端; // return model.ToJson(); return "调用失败"; } } }5)在Form1方法中再添加对暴露给前端JS调用的类进行注册的代码; bound为被前端调用方法的顶级函数名。CefCustomObject为需要被注册的类;下面代码的含义,可参照我另一篇文章新版本CefSharp.Winform 实现和js交互(JS调用C#方法); //需要添加此句代码,否则下面执行会报错 CefSharpSettings.LegacyJavascriptBindingEnabled = true; // 79.0.0以下旧方法注册 //chromeBrowser.RegisterJsObject("bound", new CefCustomObject(chromeBrowser, this), new CefSharp.BindingOptions { CamelCaseJavascriptNames = false }); // 79.0.0以上的新方法注册 CefSharpSettings.LegacyJavascriptBindingEnabled = true; CefSharpSettings.WcfEnabled = true; chromeBrowser.JavascriptObjectRepository.Register("bound", new CefCustomObject(chromeBrowser, this), isAsync: false, options: BindingOptions.DefaultBinder);至此,即可运行。html页面中调用bound.showAlertMsg("测试内容")。就会弹出对话框;调用成功。注意(前端调用的方法名必须为首字母小写,否则无后端方法无法被调用) 最后完整代码: 后端Form1窗体代码: using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.IO; using System.Windows.Forms; using CefSharp; using CefSharp.WinForms; namespace CefSharpWinformDemo { public partial class Form1 : Form { public ChromiumWebBrowser chromeBrowser; private CefCustomObject WebBrowserHelper; public Form1() { InitializeComponent(); // Start the browser after initialize global component InitializeChromium(); //需要添加此句代码,否则下面执行会报错 CefSharpSettings.LegacyJavascriptBindingEnabled = true; // 79.0.0以下旧方法注册 //chromeBrowser.RegisterJsObject("bound", new CefCustomObject(chromeBrowser, this), new CefSharp.BindingOptions { CamelCaseJavascriptNames = false }); // 79.0.0以上的新方法注册 CefSharpSettings.LegacyJavascriptBindingEnabled = true; CefSharpSettings.WcfEnabled = true; chromeBrowser.JavascriptObjectRepository.Register("bound", new CefCustomObject(chromeBrowser, this), isAsync: false, options: BindingOptions.DefaultBinder); } private void Form1_Load(object sender, EventArgs e) { } /// /// 初始化浏览器并启动 /// public void InitializeChromium() { CefSettings settings = new CefSettings(); String page = string.Format(@"{0}\ViewData\html\Index.html", Application.StartupPath); if (!File.Exists(page)) { MessageBox.Show("Error The html file doesn't exists : " + page); } // Initialize cef with the provided settings Cef.Initialize(settings); // Create a browser component chromeBrowser = new ChromiumWebBrowser(page); // Add it to the form and fill it to the form window. this.Controls.Add(chromeBrowser); chromeBrowser.Dock = DockStyle.Fill; // Allow the use of local resources in the browser BrowserSettings browserSettings = new BrowserSettings(); browserSettings.FileAccessFromFileUrls = CefState.Enabled; browserSettings.UniversalAccessFromFileUrls = CefState.Enabled; chromeBrowser.BrowserSettings = browserSettings; } /// /// 关闭窗口时释放浏览器资源 /// /// /// private void Form1_FormClosing(object sender, FormClosingEventArgs e) { // 关闭时注销释放内核 try { chromeBrowser.CloseDevTools(); chromeBrowser.GetBrowser().CloseBrowser(true); } catch { } try { if (chromeBrowser != null) { chromeBrowser.Dispose(); Cef.Shutdown(); } } catch { } } } }后端被JS调用的注册类的代码: using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; using CefSharp; using CefSharp.WinForms; using System.Diagnostics; namespace CefSharpWinformDemo { public class CefCustomObject { // Declare a local instance of chromium and the main form in order to execute things from here in the main thread private static ChromiumWebBrowser _instanceBrowser = null; // The form class needs to be changed according to yours private static Form1 _instanceMainForm = null; public CefCustomObject(ChromiumWebBrowser originalBrowser, Form1 mainForm) { _instanceBrowser = originalBrowser; _instanceMainForm = mainForm; } /// /// 窗口加载完毕时需要出发的全局JS对象; /// public void OnFrameLoadEnd(object sender, FrameLoadEndEventArgs e) { if (e.Frame.IsMain) { _instanceBrowser.ExecuteScriptAsync(@" document.body.onmouseup = function() { bound.onSelected(window.getSelection().toString()); } "); } } /// /// 显示一个弹出对话框,前端JS调用的方法 /// /// 传入参数 public void showAlertMsg(string msg) { MessageBox.Show("The user selected some text [" + msg + "]"); } public string ReadIdCard() { // 具体调用读身份证读卡器的方法 // IDCardModel model=IDCardSdk.Read(); //将身份证信息返回给前端; // return model.ToJson(); return "调用失败"; } } }前端html代码: 测试弹出框 读取身份证信息 身份证信息 function test1() { bound.showAlertMsg("测试内容"); } function test2() { var result = bound.readIdCard(); $("#idcardmsg").val(result); }运行之后的画面 |
CopyRight 2018-2019 实验室设备网 版权所有 |