C# 利用XejeN框架源码,编写一个在 Winform 界面上的语法高亮的编辑器,使用 Monaco 编辑器
析锦基于Monaco技术实现的Winform语法高亮编辑器
winform中,我们有时需要高亮显示基于某种语言的语法编辑器。
目前比较强大且UI现代化的,无疑是宇宙最强IDE的兄弟:VS Code。
类似 VS Code 的体验,可以考虑使用 Monaco Editor(VS Code 使用的编辑器)。虽然它主要用于 Web,但你可以在 WPF 或者 Winform 中嵌入一个浏览器控件(如 WebView2)并加载 Monaco Editor。
当然,适用于Winform的这种语法高亮的编辑器,除了Monaco外,还有AvalonEdit、ScintillaNET等,都可以用于复杂需求的高亮显示。
今天,我们只讲 Monaco 如何引入到 Winform 中。
本文是基于 XejeN 的 C/S 框架编写的,若您想了解 XejeN 的 C/S 框架,可以阅读此文章:
https://blog.csdn.net/mazhiyuan1981/article/details/138852326
若您想直接下载XejeN的 C/S 框架,可以访问:https://gitee.com/mazhiyuan1981/xejen-open.git
好的,下面我们开始介绍如何将 Monaco 编辑器引入到 Winform 中。
一、新建一个 Winform 项目

二、创建一个 Winform 窗体

窗体留出一个Panel控件,用于承载 Monaco 编辑器
三、安装必要的 Winform 浏览网页的 WebView2 控件

四、创建一个承载编辑器的网页界面
此为重点,这个html页面,将会显示和编辑数据内容,并能获取编辑器内容。
主要是通过setEditorContent和getEditorContent这两个方法完成的
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Monaco Editor</title><link rel="stylesheet" data-name="vs/editor/editor.main" href="https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.31.1/min/vs/editor/editor.main.css"><style>html, body, #container {width: 100%;height: 100%;margin: 0;padding: 0;overflow: hidden;}#container {display: flex;}</style>
</head>
<body><div id="container"></div><script src="https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.31.1/min/vs/loader.js"></script><script>require.config({ paths: { 'vs': 'https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.31.1/min/vs' } });window.MonacoEnvironment = { getWorkerUrl: function (workerId, label) { return `data:text/javascript;base64,${btoa("self.MonacoEnvironment = { baseUrl: 'https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.31.1/min/' }; importScripts('https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.31.1/min/vs/base/worker/workerMain.js');")}` } };require(['vs/editor/editor.main'], function () {window.editor = monaco.editor.create(document.getElementById('container'), {value: "",language: 'plaintext',automaticLayout: true // This line ensures the editor adjusts to its container's size});window.addEventListener('resize', () => {window.editor.layout(); // Adjust editor layout on window resize});window.chrome.webview.postMessage('initialized');});window.setEditorContent = function (content, language) {window.editor.setValue(content);monaco.editor.setModelLanguage(window.editor.getModel(), language);};window.getEditorContent = function () {return window.editor.getValue();};</script>
</body>
</html>
五、在 Winform 窗体界面中,加载编辑器并执行
private void LoadEditorAsync(){if (string.IsNullOrEmpty(Data)) return;string content;string language;if (Data.IsJson()){content = Data.FormatJson();language = "json";}else if (Data.IsXml()){content = Data.FormatXml();language = "xml";}else{content = Data;language = "plaintext";}string htmlPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "monaco-editor.html");DataTextBox.CoreWebView2InitializationCompleted += (sender, args) =>{if (!args.IsSuccess){MessageBox.Show("WebView2 initialization failed.");return;}DataTextBox.CoreWebView2.WebMessageReceived += (sender2, args2) =>{if (args2.TryGetWebMessageAsString() == "initialized"){DataTextBox.CoreWebView2.ExecuteScriptAsync($"setEditorContent({JsonConvert.SerializeObject(content)}, '{_language ?? language}');");SaveButton.Enabled = true;}};DataTextBox.CoreWebView2.NavigateToString(File.ReadAllText(htmlPath));};DataTextBox.Source = new Uri(htmlPath);}
六、获取编辑器修改后的内容
/// <summary>/// 获取文本数据内容/// </summary>/// <returns></returns>public async Task<string> GetDataAsync(){return JsonConvert.DeserializeObject(await DataTextBox.CoreWebView2.ExecuteScriptAsync("getEditorContent();")).ToString();}
使用GetDataAsync方法,去调用html页面的js方法getEditorContent,便可以取到编辑器的内容
七、将monaco-editor.html设置为:如果较新则复制

完整源码位置在:

完整Demo演示位置在:

源码位置:https://gitee.com/mazhiyuan1981/xejen-open.git
祝您用餐愉快。
相关文章:
C# 利用XejeN框架源码,编写一个在 Winform 界面上的语法高亮的编辑器,使用 Monaco 编辑器
析锦基于Monaco技术实现的Winform语法高亮编辑器 winform中,我们有时需要高亮显示基于某种语言的语法编辑器。 目前比较强大且UI现代化的,无疑是宇宙最强IDE的兄弟:VS Code。 类似 VS Code 的体验,可以考虑使用 Monaco Editor&a…...
03- jQuery事件处理和动画效果
1. jQuery的事件处理 1.1 绑定事件处理函数 on() 将一个或多个事件的处理方法绑定到被选择的元素上。on()方法适用于当前或未来的元素,如用脚本创建的新元素。 $(selector).on(event,childSelector,data,function) 参数描述event必需。规定要从被选元素添加的一…...
RabbitMQ 入门
目录 一:什么是MQ 二:安装RabbitMQ 三:在Java中如何实现MQ的使用 RabbitMQ的五种消息模型 1.基本消息队列(BasicQueue) 2.工作消息队列(WorkQueue) 3. 发布订阅(Publish、S…...
物联网协议应用
目录 前言一、WIFI简介二、NTP协议2.1 NTP简介2.2 NTP实现 三、HTTP协议3.1 HTTP协议简介3.2 HTTP服务器 四、MQTT协议4.1 MQTT协议简介4.1.1 MQTT通信模型4.1.2 MQTT协议实现原理4.1.3 MQTT 控制报文 4.2 移植MQTT协议 前言 本文主要介绍一下物联网协议如NTP协议、HTTP协议和M…...
十分钟学会微调大语言模型
有同学给我留言说想知道怎么训练自己的大语言模型,让它更贴合自己的业务场景。完整的大语言模型训练成本比较高昂,不是我们业余玩家能搞的,如果我们只是想在某个业务场景或者垂直的方面加强大模型的能力,可以进行微调训练。 本文…...
结合简单工厂和工厂方法模式:实现灵活的对象创建
前言 在软件开发过程中,创建对象的方式直接影响代码的灵活性和可维护性。设计模式提供了一种解决复杂问题的方法,其中简单工厂模式和工厂方法模式是两种常用的创建型模式。在这篇文章中,我们将结合这两种模式,通过一个实际案例&a…...
网抑云特殊版,登录即永久
前言 今天分享一款特殊版本的音乐软件,相信大家在听网抑云的时候会有两大烦恼, 一是歌曲需要开通VIP才可以收听,不管怎么说也是国内厂商普遍操作 但是第二种烦恼你万万想不到的是,开通了会员后,惊奇的发现ÿ…...
Kotlin 实战小记:No-Arg 引用解决 No constructor found的问题
一、问题 新的项目试用一下kotlin, 调用数据库查询数据的时候报了这个问题:org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.executor.ExecutorException: No constructor found in com.neusoft.collect.entity.cm.CmRoom matc…...
HTML(5)——列表表格
列表 无序列表 作用:布局排列整齐的不需要规定顺序的区域。 标签:ul嵌套il,ul是无序列表,li是列表条目 注:ul标签只能包裹li标签,li标签可以包含任何内容 有序列表 作用:布局排列整齐的需…...
FreeBSD通过CBSD管理低资源容器jail来安装Ubuntu子系统实践
简介 FreeBSD、CBSD、Jail和Ubuntu,四者的组合方案可以说是强强联合,极具性价比和竞争力!同时安装简单方便,整体方案非常先进。 CBSD是为FreeBSD jail子系统、bhyve、QEMU/NVMM和Xen编写的管理层。该项目定位为一个综合解决方案…...
SpringCloud总结(springcloud alibaba)
目录 版本说明(很重要) springcloud alibaba对应组件版本说明 简述 spring cloud albaba 几大模块 周会讨论 - spring cloud alibaba每周都会有周会讨论,社区活跃 spring cloud alibaba官网 注册配置中心 简单介绍 nacos 步骤 示例代码 依赖…...
轻轻松松上手的LangChain学习说明书
本文为笔者学习LangChain时对官方文档以及一系列资料进行一些总结~覆盖对Langchain的核心六大模块的理解与核心使用方法,全文篇幅较长,共计50000字,可先码住辅助用于学习Langchain。 一、Langchain是什么? 如今各类AI…...
全面对比与选择指南:Milvus、PGVector、Zilliz及其他向量数据库
本文全面探讨了Milvus、PGVector、Zilliz等向量数据库的特性、性能、应用场景及选型建议,通过详细的对比分析,帮助开发者和架构师根据具体需求选择最合适的向量数据库解决方案。 文章目录 向量数据库概述向量数据库的关键功能向量数据库的扩展和选择向量…...
svm 超参数
https://www.cnblogs.com/ChevisZhang/p/12932674.html https://wenku.baidu.com/view/b8a2c73cfd4733687e21af45b307e87100f6f861.html?wkts1718332423081&bdQuerysvm%E7%9A%84%E8%B6%85%E5%8F%82%E6%95%B0 用交叉验证找到最好的参数 C 和γ 。使用 RBF 核时,…...
001-基于Sklearn的机器学习入门:Sklearn库基本功能和标准数据集
本节将介绍Sklearn库基本功能,以及其自带的几个标准数据集的调用方法。本节是学习后面内容的基础,如果您已经对本节内容相当熟悉,可跳过本节内容。 1.1 Sklearn库基本功能 的 1.2 Sklearn库标准数据集 Sklearn自带许多标准数据集ÿ…...
充电学习—7、BC1.2 PD协议
BC1.2(battery charging)充电端口识别机制: SDP、CDP、DCP 1、VBUS detect:vbus检测 PD(portable device,便携式设备)中有个检测VBUS是否有效的电路,电路有个参考值,高…...
技术点梳理0618
ann建库,分布式建库,性能优化,precision recall参数优化 hnsw,图索引 1. build a)确定层:类似跳表思路建立多层,对每一个插入的节点,random层号l,从图的起始点search_…...
石英砂酸洗提纯方法和工艺
石英砂酸洗提纯方法和工艺是石英砂加工中至关重要的一个环节,其目的是通过化学手段去除石英砂中的杂质,提升其纯度。以下将详细介绍石英砂酸洗提纯的方法和工艺,以便更好地理解和应用这一技术。 一、概述 石英砂酸洗提纯主要是利用酸液对石英…...
linux安装dgl
1.DGL官网、选择与自己cuda、python版本匹配的dgl的whl文件CUDA11.8、python10并下载 2.用pip install运行 pip install /home/u2023170749/download/dgl-2.2.0cu118-cp310-cp310-manylinux1_x86_64.whl或者直接安装https://blog.csdn.net/weixin_44017989/article/details/13…...
【SAP-ABAP】-权限批导-批量给某个角色导入事务码权限
需求:SAP期初上线的时候,业务顾问经常会遇到批量创建角色和分配角色权限的情况 岗位需求:一般是业务顾问定义权限,BASIS进行后期运维,今天讲两个批导功能,方便期初上线 主要函数:PRGN_READ_ROLE…...
30/50/20分期怎么设?SAP付款条件Z028实战案例详解(附基准日期避坑指南)
SAP非等额分期付款实战指南:30/50/20比例配置与基准日期避坑 在工程项目、大额设备采购等业务场景中,分期付款是常见的交易方式。不同于标准的等额分期,工程类合同常采用30/50/20这类非对称比例,首期支付30%预付款,中期…...
告别规则几何!用Python+Matlab为gprMax创建任意复杂地质模型(附HDF5文件生成代码)
突破几何限制:用PythonMatlab构建gprMax复杂地质模型的完整指南 地质雷达模拟领域的研究者常面临一个尴尬困境:脑海中的地质结构复杂多变,但建模工具却只能生成规则几何体。本文将彻底解决这一矛盾,带您掌握跨平台协作建模技术&am…...
Python AOT编译面试通关手册(仅限2026 Q1–Q3内推通道开放期|含6家头部公司真实压轴题及参考实现)
第一章:Python AOT编译技术演进与2026面试全景图Python 长期以来以解释执行和 JIT(如 PyPy)为主流,但面向云原生、边缘计算与安全敏感场景,AOT(Ahead-of-Time)编译正加速进入主流视野。从早期的…...
C++标准库算法与自定义迭代器的适配器模式实现技巧
C标准库算法与迭代器适配技巧 C标准库提供了丰富的泛型算法,如sort、find、transform等,这些算法通过迭代器与容器解耦,极大提升了代码复用性。但当标准迭代器无法满足特殊需求时,适配器模式成为连接算法与自定义数据结构的桥梁。…...
实战教程:3分钟掌握高效抖音内容保存方案
实战教程:3分钟掌握高效抖音内容保存方案 【免费下载链接】douyin-downloader 项目地址: https://gitcode.com/GitHub_Trending/do/douyin-downloader 还在为喜欢的抖音内容无法保存而烦恼吗?这款完全免费的抖音下载工具正是你需要的专业解决方案…...
OpCore-Simplify终极指南:如何快速构建完美的OpenCore EFI配置
OpCore-Simplify终极指南:如何快速构建完美的OpenCore EFI配置 【免费下载链接】OpCore-Simplify A tool designed to simplify the creation of OpenCore EFI 项目地址: https://gitcode.com/GitHub_Trending/op/OpCore-Simplify 还在为复杂的Hackintosh配置…...
最近折腾了一波心音信号(PCG)分类的小项目,踩了不少坑也攒了点能直接跑的代码,今天掏出来跟大伙唠唠
MATLAB环境下一种基于连续小波变换和GoogLeNet的PCG信号分类算法 算法运行环境为MATLAB r2021b,共5种PCG信号,即normal, AR,AS,MR,MS五类 算法可迁移至金融时间序列,地震信号,语音信号,声信号,生理信号&…...
突破大文件传输瓶颈:aliyunpan快传链接技术全解析
突破大文件传输瓶颈:aliyunpan快传链接技术全解析 【免费下载链接】aliyunpan 阿里云盘命令行客户端,支持JavaScript插件,支持同步备份功能。 项目地址: https://gitcode.com/GitHub_Trending/ali/aliyunpan 大文件传输的现实痛点&…...
破解金融分析复杂性:TradingAgents-CN多智能体协作框架的实战价值与落地指南
破解金融分析复杂性:TradingAgents-CN多智能体协作框架的实战价值与落地指南 【免费下载链接】TradingAgents-CN 基于多智能体LLM的中文金融交易框架 - TradingAgents中文增强版 项目地址: https://gitcode.com/GitHub_Trending/tr/TradingAgents-CN 价值定位…...
用ESP32和2.13寸墨水屏,我把汉朔电子价签改造成了桌面网络时钟(附完整代码)
用ESP32和2.13寸墨水屏打造极简网络时钟:从电子价签到桌面艺术 在智能硬件爱好者的世界里,总有一些被遗忘的电子元件等待重生。汉朔电子价签的2.13寸墨水屏就是这样一个被低估的宝藏——它低功耗、高对比度的特性,配合ESP32的强大无线功能&am…...
