Awesome Chrome Form UI - 框架设计与基础实现

Money is not evil by itself.

Its just paper with perceived value to obtain other things we value in other ways.

If not money what is evil you may ask?

Evil is the unquenchable, obsessive and moral bending desire for more.

Evil is the bottomless,soulless and obsessive compulsive pursuit of some pot of gold at the end of some rainbow which doesnt exist.

Evil is having a price tag for your heart and soul in exchange for financial success at any cost.

Evil is trying to buy happiness, again and again until all of those fake, short lived mirages of emotions are gone.

——《Time》 MKJ

一、ACF UI 简介

是什么?

Awesome Chrome Form UI:简称 ACF UI,基于 CefSharp 库进行插件化封装,它提供接口的默认实现(预设)和常用 Attribute 特性(注解),开发者可以开箱即用,无需过多配置即可使用  Web 技术快速构建一个桌面应用。

应用场景:WinForm 嵌入式浏览器解决方案。

客户端嵌入浏览器的框架很多,首选肯定是 Electron,如果有 Rust 基础,可以考虑使用 Tauri 。在 WinForm 框架上,可以选择 WinFormium(曾用名:NanUI),一个经过了 9 年迭代的框架。

如果你想使用 Vue 等前端技术栈构建 Window 桌面应用,并且使用的是 CefSharp 实现,那么你可以考虑使用 ACF UI。

为什么?

该框架的核心是:通过解耦来简化配置,降低开发难度。类似于 SpringBoot 通过注解实现依赖注入和控制反转等功能,ACF UI 提供 Attribute 实现同样的效果,从而提高应用程序的灵活性和可维护性。

 荔枝 例子:使用 Attribute 

直接使用 CefSharp 导出 DotNet 方法时,除了需要编码 CommonUtil 类,还需要添加 Browser 处理逻辑,

引入 ACF UI 后,导出方法只需要加上  [JavascriptObject] 特性,框架会帮你添加 Browser 处理逻辑,

二、框架主流程 V1.0.0 设计

主流程也非常简单:

  1. 初始化 CEF 配置
  2. 初始化基础窗口
  3. 初始化 Browser 配置
  4. 关闭 CEF

三个初始化阶段的操作相同,都是通过反射机制扫描 Attribute 进行配置初始化,如果没有自定义实现配置则采用预设值。

三、框架主流程 V1.0.0 实现

1、AwesomeChromeFormUI 插件模块

配置目标平台,指定 x86 或者 x64 都可以,

删除框架生成的 Class1.cs ,新增 BaseForm.cs ,

using System.Windows.Forms;namespace AwesomeChromeFormUI.ChromiumForms
{public partial class BaseForm : Form{}
}

2、引入 CefSharp 库

CefSharp.WinForms.119.1.20

3、ControlExtensions

在 UI 线程上异步执行 Action,

using System;
using System.Windows.Forms;namespace AwesomeChromeFormUI.CommonExtensions
{public static class ControlExtensions{/// <summary>/// Executes the Action asynchronously on the UI thread, does not block execution on the calling thread./// </summary>/// <param name="control">the control for which the update is required</param>/// <param name="action">action to be performed on the control</param>public static void InvokeOnUiThreadIfRequired(this Control control, Action action){//If you are planning on using a similar function in your own code then please be sure to//have a quick read over https://stackoverflow.com/questions/1874728/avoid-calling-invoke-when-the-control-is-disposed//No actionif (control.Disposing || control.IsDisposed || !control.IsHandleCreated){return;}if (control.InvokeRequired){control.BeginInvoke(action);}else{action.Invoke();}}}
}

4、ConfigurationAttribute 配置特性

规则:ConfigurationAttribute 所标记的类只能被应用一次,并且只能应用于类的定义上,

using System;namespace AwesomeChromeFormUI.Attributes
{/// <summary>/// 自定义 BaseForm 配置注解/// </summary>[AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]public class BaseFormConfigurationAttribute : Attribute{}
}
using System;namespace AwesomeChromeFormUI.Attributes
{/// <summary>/// 自定义 Cef 配置注解/// </summary>[AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]public class CefConfigurationAttribute : Attribute{}
}
using System;namespace AwesomeChromeFormUI.Attributes
{/// <summary>/// 自定义 Browser 配置注解/// </summary>[AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]public class BrowserConfigurationAttribute : Attribute {}
}

5、Configuration 配置类封装

规则:提供常见的属性作为字段,并通过无参构造函数为属性赋默认值,

using AwesomeChromeFormUI.Constants;
using System.Drawing;
using System.Windows.Forms;namespace AwesomeChromeFormUI.Configs
{public class BaseFormConfiguration{/// <summary>/// 宽度/// </summary>public int Width { get; set; }/// <summary>/// 高度/// </summary>public int Height { get; set; }/// <summary>/// 标题文本/// </summary>public string Text { get; set; }/// <summary>/// Logo/// </summary>public Icon Icon { get; set; }/// <summary>/// 窗口边框样式/// </summary>public FormBorderStyle FormBorderStyle { get; set; }/// <summary>/// 启动位置/// </summary>public FormStartPosition StartPosition { get; set; }/// <summary>/// 窗口状态/// </summary>public FormWindowState WindowState { get; set; }public BaseFormConfiguration(){this.Width = BaseFormConstant.DEFAULT_WIDTH;this.Height = BaseFormConstant.DEFAULT_HEIGHT;this.Text = BaseFormConstant.DEFAULT_TITLE;this.Icon = new Icon(BaseFormConstant.DEFAULT_ICON);this.StartPosition = FormStartPosition.CenterScreen;this.FormBorderStyle = FormBorderStyle.Sizable;this.WindowState = FormWindowState.Normal;}}
}
using CefSharp;
using CefSharp.SchemeHandler;
using CefSharp.WinForms;
using System;
using System.IO;namespace AwesomeChromeFormUI.Configs
{public class CefConfiguration{/// <summary>/// 默认前端文件夹/// </summary>private string _defaultFrontendFolderPath;public CefSettingsBase CefSettings { get; set; }public bool PerformDependencyCheck { get; set; }public IBrowserProcessHandler BrowserProcessHandler { get; set; }public CefConfiguration(){CreateDefaultFrontendFolderPath();// Pseudo code; you probably need more in your CefSettings also.var settings = new CefSettings(){

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/2660708.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

解决VSCode中C/C++ Project Generator插件创建的项目只能运行单个程序的问题

初六&#xff0c;履霜&#xff0c;坚冰至。 释意&#xff1a;初六&#xff0c;当你踩着微霜之时&#xff0c;严寒与坚冰也就即将到来。 目录 一、前言 二、问题描述 三、解决方案 1、思路总结 2、思考过程 3、解决方案&#xff08;直接用&#xff0c;报错找我(&#xff8…

超声功率放大器怎么用

超声功率放大器是一种用于放大超声信号的设备&#xff0c;广泛应用于医疗领域、工业领域和科学研究中。它能够将超声信号的能量增加到足够大的水平&#xff0c;以便进行高强度超声疗法、材料加工和实验研究等应用。下面将详细介绍超声功率放大器的使用方法和其工作原理。 首先&…

数据结构——红黑树 and B-树

红黑树 根据平衡条件第4、5两点 最短路径&#xff0c;都是黑色 最长路径&#xff0c;红黑相间 最长是最短的两倍 B-树

《深入理解Java虚拟机(第三版)》读书笔记:Java内存区域与内存溢出异常、垃圾收集器与内存分配策略

下文是阅读《深入理解Java虚拟机&#xff08;第3版&#xff09;》这本书的读书笔记&#xff0c;如有侵权&#xff0c;请联系删除。 文章目录 第2章 Java内存区域与内存溢出异常2.2 运行时数据区域2.3 HotSpot虚拟机对象探秘 第3章 垃圾收集器与内存分配策略3.2 对象已死&…

安装Node修改Node镜像地址搭建Vue脚手架创建Vue项目

1、安装VSCode和Node 下载VSCode Visual Studio Code - Code Editing. Redefined 下载Node Node.js (nodejs.org) 检验是否安装成功&#xff0c;WinR,输入cmd命令&#xff0c;使用node -v可以查看到其版本号 2、修改镜像地址 安装好node之后&#xff0c;开始修改镜像地址 …

【 YOLOv5】目标检测 YOLOv5 开源代码项目调试与讲解实战(4)-自制数据集及训练(使用makesense标注数据集)

如何制作和训练自己的数据集 看yolov5官网创建数据集1.搜索需要的图片2.创建标签标注数据集地址&#xff1a;放入图片后选择目标检测创建文档&#xff0c;每个标签写在单独的一行上传结果此处可以编辑类别把车框选选择类别即可导出数据 3.新建一个目录放数据写yaml文件 4. 测试…

重装系统以后无法git跟踪

总结&#xff1a;权限问题 故障定位 解决方案&#xff1a; 复制一份新的文件夹。&#xff08;新建的文件创建和写入权限都变了&#xff09; 修改文件为新的用户 执行提示的命令

docker +gitee+ jenkins +maven项目 (一)

jenkins环境和插件配置 文章目录 jenkins环境和插件配置前言一、环境版本二、jenkins插件三、环境安装总结 前言 现在基本都是走自动化运维&#xff0c;想到用docker 来部署jenkins &#xff0c;然后jenkins来部署java代码&#xff0c;做到了开箱即用&#xff0c;自动发布代码…

磁盘相关知识

一、硬盘数据结构 1.扇区&#xff1a; 盘片被分为多个扇形区域&#xff0c;每个扇区存放512字节的数据&#xff08;扇区越多容量越大&#xff09; 存放数据的最小单位 512字节 &#xff08;硬盘最小的存储单位是扇区&#xff0c;512 个字节&#xff0c;八个扇区组成一块&…

H5向微信小程序发送信息(小程序web-view打开H5)

引入weixin-js-sdk npm i weixin-js-sdk 页面引入 // 引入wxjsimport wx from "weixin-js-sdk"; 点击触发方法 methods: {goweap(id){console.log(wx);// H5传递数据 &#xff08;navigateBack&#xff09;wx.miniProgram.navigateBack({delta: 1});wx.min…

Android APK未签名提醒

最近新建了一个项目&#xff0c;在build.gradle中配置好了签名&#xff0c;在执行打包的时候打出的包显示已签名&#xff0c;但是在上传市场的时候提示未签名。于是排查了好久&#xff0c;发现在build.gradle中配置的minsdk 24&#xff0c;会导致不使用V1签名&#xff0c;于是我…

redis容灾的方案设计

背景 今年各个大厂的机房事故频繁&#xff0c;其中关键组件Redis是重灾区&#xff0c;本文就来看下怎么做Redis的多机房容灾 Redis多机房容灾方案 1.首先最最直观的是直接利用Redis内部的主从数据同步来进行灾备&#xff0c;但是由于Redis内部的主从实现对机房间的网络延迟等…

[OCR]Python 3 下的文字识别CnOCR

目录 1 CnOCR 2 安装 3 实践 1 CnOCR CnOCR 是 Python 3 下的文字识别&#xff08;Optical Character Recognition&#xff0c;简称OCR&#xff09;工具包。 工具包支持简体中文、繁体中文&#xff08;部分模型&#xff09;、英文和数字的常见字符识别&#xff0c;支持竖…

文件下载输出zip文件

文件下载输出成zip文件&#xff1a; 1、前端整个按钮&#xff0c;调js方法&#xff1a;&#xff08;参数&#xff1a;param,需要下载的id&#xff0c;用逗号拼接&#xff09; var param "?dto.id";//需要自己拼接param window.location.href "<%basePat…

OSFP协议配置实验

实验目的&#xff1a; &#xff08;1&#xff09;理解OSPF&#xff1b; &#xff08;2&#xff09;掌握OSPF的配置方法&#xff1b; &#xff08;3&#xff09;掌握查看OSPF协议的相关信息。 实验器材&#xff1a; Cisco packet 实验内容&#xff1a; 实验步骤&#xff1…

简单的vxlan实验

拓扑如下 如上拓扑&#xff0c;PC1与PC3在同一个大二层广播域&#xff0c;PC2与PC4在同一个大二层广播域&#xff0c;我们要把PC1到PC3通过vxlan做通&#xff0c;PC2与PC4做通。 1.接入交换机SW1配置 vlan batch 10 20 interface GigabitEthernet0/0/1 port link-type trun…

时序预测 | Matlab实现SSA-CNN-GRU麻雀算法优化卷积门控循环单元时间序列预测

时序预测 | Matlab实现SSA-CNN-GRU麻雀算法优化卷积门控循环单元时间序列预测 目录 时序预测 | Matlab实现SSA-CNN-GRU麻雀算法优化卷积门控循环单元时间序列预测预测效果基本介绍程序设计参考资料 预测效果 基本介绍 Matlab实现SSA-CNN-GRU麻雀算法优化卷积门控循环单元时间序…

postman win7 低版本 postman7.0.9win64 postman7.0.9win32

百度网盘&#xff1a; postman7.0.9win64&#xff1a; 链接: https://pan.baidu.com/s/18ck9tI0r9Pqoz36MOwwnnQ 提取码: rkf7 postman7.0.9win32&#xff1a; 链接: https://pan.baidu.com/s/1HrpGPrgvVzyAcjdHuwVOpA 提取码: ke5k win7系统安装postman&#xff0c;可能会…

python-39-flask+nginx+Gunicorn的组合应用

flask nginx Gunicorn 王炸 1 flasknginxgunicornsupervisor 1.1 myapp.py from flask import Flask app Flask(__name__)app.route("/") def test_link():return "the link is very good"if __name__"__main__":app.run()默认是5000端口…

什么是Wi-Fi Halow,它是基于什么标准,它的主要优势在哪

文章目录 1.1 背景1.2 技术前景2.1 Wi-Fi HaLow主要优势2.2 Wi-Fi HaLow技术特性2.3 具体技术特点2.4 支持频段介绍3.1 应用场景3.2 WiFi-HaLow芯片厂商3.3 基于WiFi-HaLow芯片网关与模组商1.1 背景 Wi-Fi HaLow是2021年11月Wi-Fi联盟发布的一项基于IEEE 802.11ah最新标准,专…