AvalonEdit 是一个基于 WPF 的文本编辑器组件。它是由 Daniel GrunwaldSharpDevelop 编写的。从 5.0 版开始,AvalonEdit 根据MIT许可证发布。



通过使用 AvalonEdit ,小伙伴们可以很容易的在自己的程序中集成代码编辑器。AvalonEdit 在路遥工具箱中有着广泛的运用。

安装 AvalonEdit

首先,通过 NuGet 安装 AvalonEdit ,地址是:https://www.nuget.org/packages/AvalonEdit

接着将以下代码粘贴到 XAML 文件中,即可创建一个最简单的 AvalonEdit 控件:

<avalonEdit:TextEditor
xmlns:avalonEdit="http://icsharpcode.net/sharpdevelop/avalonedit"
Name="TextEditor"
SyntaxHighlighting="C#"
FontFamily="Consolas"
FontSize="10pt"
LineNumbersForeground="Black"
ShowLineNumbers="True">
</avalonEdit:TextEditor>

第二行的 xmlns:avalonEdit="http://icsharpcode.net/sharpdevelop/avalonedit" 是 AvalonEdit 的命名空间,属于硬编码。

AvalonEdit 内置了多种语法高亮规则,SyntaxHighlighting="C#" 的意思是对 C# 进行代码高亮。如果需要对 XML 代码进行高亮,仅需将 C# 改为 XML 即可:SyntaxHighlighting="XML"

第九行的 ShowLineNumbers="True" 代表展示每行的行号,这在展示单行过长的文字时非常有用,默认为 False 。

使用 JetBrand Mono 字体展示代码

JetBrand Mono 字体非常适合用来展示代码,且该字体文件非常小巧(仅有 200K 左右),可以直接嵌入在应用中。

首先,将下载到的 JetBrand Mono 字体文件 JetBrainsMono.ttf 复制到项目的 Resources 文件夹,设置文件的”生成操作“为”资源“。

接着设置 TextEditor 的 FontFamily 属性即可:

pack://application:,,,/{程序集名称};component/Resources/#JetBrains Mono

其中,{程序集名称} 需要替换为你自己的应用程序信息。

对 AvalonEdit 进行 MVVM 绑定

我们可以通过 TextEditor 的 Text 属性来获取或设置代码编辑器中的内容,但该属性不是一个依赖属性,所以我们不能直接将其绑定到 ViewModel 上。

一个针对 AvalonEdit 的 Behavior 可以协助解决该问题:

using ICSharpCode.AvalonEdit;
using Microsoft.Xaml.Behaviors;
using System;
using System.Windows; public sealed class AvalonEditBehaviour : Behavior<TextEditor>
{
public static readonly DependencyProperty CodeTextProperty =
DependencyProperty.Register("CodeText", typeof(string), typeof(AvalonEditBehaviour),
new FrameworkPropertyMetadata(default(string), FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, PropertyChangedCallback)); public string CodeText
{
get { return (string)GetValue(CodeTextProperty); }
set { SetValue(CodeTextProperty, value); }
} protected override void OnAttached()
{
base.OnAttached();
if (AssociatedObject != null)
AssociatedObject.TextChanged += AssociatedObjectOnTextChanged;
} protected override void OnDetaching()
{
base.OnDetaching();
if (AssociatedObject != null)
AssociatedObject.TextChanged -= AssociatedObjectOnTextChanged;
} private void AssociatedObjectOnTextChanged(object sender, EventArgs eventArgs)
{
if (sender is TextEditor textEditor)
{
if (textEditor.Document != null)
CodeText = textEditor.Document.Text;
}
} private static void PropertyChangedCallback(
DependencyObject dependencyObject,
DependencyPropertyChangedEventArgs dependencyPropertyChangedEventArgs)
{
var behavior = dependencyObject as AvalonEditBehaviour;
if (behavior.AssociatedObject != null)
{
var editor = behavior.AssociatedObject;
if (editor.Document != null)
{
var caretOffset = editor.CaretOffset;
editor.Document.Text = dependencyPropertyChangedEventArgs.NewValue.ToString();
if (caretOffset <= editor.Document.Text.Length) editor.CaretOffset = caretOffset;
}
}
}
}

假设上述代码存在于 Behaviors 命名空间下,且 ViewModel 有一个名为 Code 的通知属性。则 XAML 代码如下:

 <avalonEdit:TextEditor xmlns:avalonEdit="http://icsharpcode.net/sharpdevelop/avalonedit">
<i:Interaction.Behaviors xmlns:i="http://schemas.microsoft.com/xaml/behaviors">
<bh:AvalonEditBehaviour xmlns:bh="clr-namespace:Behaviors" CodeText="{Binding Code}"/>
</i:Interaction.Behaviors>
</avalonEdit:TextEditor>

开启快速搜索框

在使用 ILSpy 查看程序集源代码时,可以通过快捷键 ” CTRL + F “ 打开一个快速搜索框,要搜索的文字会高亮显示,同时支持对搜索结果进行导航:

ILSpy 的快速搜索功能

事实上 ILSpy 使用的也是 AvalonEdit 控件,开启搜索面板仅需一行代码:

ICSharpCode.AvalonEdit.Search.SearchPanel.Install(TextEditor);

以上代码在 XAML 的后置代码构造函数中 InitializeComponent 方法后调用即可。

代码折叠功能

代码折叠是一些文本编辑器,源代码编辑器和IDE的一个功能,它允许用户有选择地隐藏和显示 – “折叠” – 当前编辑文件的各个部分作为例行编辑操作的一部分。 这允许用户管理大量文本,同时仅查看在任何给定时间特别相关的文本子部分。

路遥工具箱的代码折叠功能

针对 XML 语言的代码折叠,需要用到 FlodingManager 和 XmlFoldingStrategy 。

<avalonedit:TextEditor SyntaxHighlighting="XML" TextChanged="CodeEditor_TextChanged" ShowLineNumbers="True" WordWrap="True" x:Name="CodeEditor">
<avalonedit:TextEditor.ContextMenu>
<ContextMenu>
<MenuItem Header="全部折叠" x:Name="CloseMenuItem" Click="CloseMenuItem_Click"></MenuItem>
<MenuItem Header="全部展开" x:Name="OpenMenuItem" Click="OpenMenuItem_Click"></MenuItem>
</ContextMenu>
</avalonedit:TextEditor.ContextMenu>
</avalonedit:TextEditor>

对应的后置代码如下:

using ICSharpCode.AvalonEdit.Folding;
using System;
using System.Windows;
using System.Windows.Controls; public MyUserControl() //构造函数
{
InitializeComponent();
foldingManager = FoldingManager.Install(CodeEditor.TextArea);
} FoldingManager foldingManager = null;
XmlFoldingStrategy foldingStrategy = new XmlFoldingStrategy(); private void CodeEditor_TextChanged(object sender, EventArgs e)
{
if (foldingManager == null) return;
foldingStrategy.UpdateFoldings(foldingManager, CodeEditor.Document);
}
private void CloseMenuItem_Click(object sender, RoutedEventArgs e)
{
if (foldingManager == null) return;
var isFrist = true;
foreach (var item in foldingManager.AllFoldings)
{
if (isFrist)
{
isFrist = false;
continue;
}
item.IsFolded = true;
}
}
private void OpenMenuItem_Click(object sender, RoutedEventArgs e)
{
if (foldingManager == null) return;
foreach (var item in foldingManager.AllFoldings)
{
item.IsFolded = false;
}
}

结束

以上就是本片的全部内容,本文展示的所有代码均可以在路遥工具箱中找到运用。

WPF学习笔记(四):AvalonEdit 代码高亮编辑控件专题的更多相关文章

  1. IOS学习笔记(四)之UITextField和UITextView控件学习

    IOS学习笔记(四)之UITextField和UITextView控件学习(博客地址:http://blog.csdn.net/developer_jiangqq) Author:hmjiangqq ...

  2. .NET MVC 学习笔记(七)— 控制input控件

    .NET MVC 学习笔记(七)— 控制input控件 画面中有时候需要输入数字,这时就需要控制input的输入.以下为保留两位有效数字. /* * 初始化数字输入 */ function initD ...

  3. Winform控件学习笔记【第二天】——常用控件

    背景:期末考试刚过就感冒了,嗓子火辣辣的,好难受.但是一想起要学习总结就打起精神来了,Winform控件网上也没有多少使用教程,大部分都是自己在网上零零散散的学的,大部分用的熟了,不总结会很容易忘得. ...

  4. WPF学习笔记四之命令

    1.概念 对于程序来说,命令就是一个个任务,例如保存,复制,剪切这些操作都可以理解为一个个命令.即当我们点击一个复杂按钮时,此时就相当于发出了一个复制的命令,即告诉文本框执行一个复杂选中内容的操作,然 ...

  5. 【WPF学习】第二十二章 文本控件

    WPF提供了三个用于输入文本的控件:TextBox.RichTextBox和PasswordBox.PasswordBox控件直接继承自Control类.TextBox和RichTextBox控件间接 ...

  6. Android学习笔记(九)——布局和控件的自定义

    //此系列博文是<第一行Android代码>的学习笔记,如有错漏,欢迎指正! View是 Android中一种最基本的 UI组件,它可以在屏幕上绘制一块矩形区域,并能响应这块区域的各种事件 ...

  7. Dynamic CRM 2013学习笔记(八)过滤查找控件 (类似省市联动)

    我们经常要实现类似省市联动一样的功能,常见的就是二个查找控件,一个选择了省后,另一个市的查找控件就自动过滤了,只显示当前省下的市,而不是所有的市.当然这是最简单的,实际工作中还有更复杂的功能要通过过滤 ...

  8. 【AngularJS学习笔记】封装一些简单的控件(封装成Html标签)

    bootstrap有强大的指令系统,可以自定义一些属性,基本知识请移步:http://angularjs.cn/A00r  http://www.cnblogs.com/lvdabao/p/33916 ...

  9. WPF学习之路(十二)控件(HeaderedContent控件)

    GroupBox 用来组织多种控件的常见控件,因为是内容空间,只能直接包含一项,需要使用面板一类的中间空间. Header和Content可以是任意元素 <GroupBox> <Gr ...

随机推荐

  1. C++基础之自增和自减运算符的重载

    1. 格式 1.1 分为前置和后置格式: int x = 0; int y = 0; // 后置自增运算符 x++; // 前置自增运算符 ++x; // 后置自减运算符 y--; // 前置自减运算 ...

  2. spoj-ORDERS - Ordering the Soldiers

    ORDERS - Ordering the Soldiers As you are probably well aware, in Byteland it is always the military ...

  3. 【剑指Offer】二叉树中和为某一值的路径 解题报告(Python)

    [剑指Offer]二叉树中和为某一值的路径 解题报告(Python) 标签(空格分隔): 剑指Offer 题目地址:https://www.nowcoder.com/ta/coding-intervi ...

  4. idea使用教程-常用设置

    [1]进入设置: [2]设置主题: [3]编辑区的字体变大或者变小: [4]鼠标悬浮在代码上有提示: [5]自动导包和优化多余的包: 手动导包:快捷键:alt+enter 自动导包和优化多余的包: [ ...

  5. BUG 记录:移位运算与扩展欧几里得算法

    BUG 记录:移位运算与扩展欧几里得算法 起因 上个月就开始打算用C++写一个ECC的轮子(为什么?折磨自己呗!),奈何自己水平有点差,拖到现在才算写完底层的大数运算.在实现欧几里得算法的时候,我开始 ...

  6. Exploring Architectural Ingredients of Adversarially Robust Deep Neural Networks

    目录 概 主要内容 深度 宽度 代码 Huang H., Wang Y., Erfani S., Gu Q., Bailey J. and Ma X. Exploring architectural ...

  7. 想看Vue文档,cn放错位置,误入xx网站...

    昨晚,DD在微信群(点击加入)里看到有小伙伴说,想去Vue官网看中文文档,不当心把cn写错了位置,结果进入了xx网站... 老司机们应该都知道,Vue官网的中文文档地址是:https://cn.vue ...

  8. ios离线打包报错Showing Recent Messages :-1: HBuilder has conflicting provisioning settings. HBuilder is automatically signed for development, but a conflicting code signing identity iPhone Distribution has

    1.解决方案找到项目工程文件右击->显示包内容->双击project.pbxproj->搜索distribution改写成Developer

  9. ImageNet2017文件下载

    ImageNet2017文件下载 文件说明 imagenet_object_localization.tar.gz包含训练集和验证集的图像数据和地面实况,以及测试集的图像数据. 图像注释以PASCAL ...

  10. CS5218DP转HDMI转接方案|CS5218说明|CS5218

    Capstone CS5218是一款单端口HDMI/DVI电平移位器/中继器,具有重新定时功能.它支持交流和直流耦合信号高达3.0-Gbps的操作与可编程均衡和抖动清洗.它包括2路双模DP电缆适配器寄 ...