Ynote Classic - 文本和源代码编辑器






4.89/5 (8投票s)
一款多功能开源文本编辑器和源代码编辑器,支持语法高亮、代码折叠、自动缩进等功能
引言
我开始 ynote 是为了学习 .NET Framework 的一个项目。第一个 ynote 版本什么都没有,只是一个 TextBox
控件和一些基本命令——剪切、复制等。然后我看到了 FastColoredTextBox
控件。FastColoredTextBox
控件最初包含在 v2.0 中,只支持 5 种语言。现在,它拥有一个完美的代码编辑器所能拥有的一切。另一个原因是想了解 .NET 的能力,因为我没有找到任何使用 .NET 平台编写的体面的文本编辑器(不包括 C++),所以我制作了 “Ynote Classic” —— 用 .NET 编写的文本编辑器。
特点
Ynote 拥有大量功能,使其用户友好且交互性强
- 约 40 种语言的语法高亮、代码折叠和自动缩进
- 多光标和多选
- 宏录制和回放以自动化任务
- 可通过配色方案、脚本、命令、插件和自定义快捷方式进行扩展
- 分屏、全屏和无干扰编辑
- 使用正则表达式进行强大的搜索和替换
- 惊人的多窗口和单窗口环境
- 代码片段以提高生产力
- 文档地图和标尺
这只是一个基本功能列表,深入了解更多。
Using the Code
语法高亮
Ynote Classic 的核心是 FastColoredTextBox 控件,它用于语法高亮、自动缩进和代码折叠。FastColoredTextBox 使用样式,并借助正则表达式将它们添加到具有开始和结束位置的 TextBox 范围。
Ynote 使用其内置高亮器高亮代码,也可以使用 ynotesyntax 文件进行扩展。
颜色方案
Ynote 支持各种配色方案。
配色方案是一个扩展名为 .ynotetheme 的 XML 文档,用于设置语法高亮和控件的样式。
ynote 有两个主要标签。“Key
”标签和“Style
”标签。Style
标签用于设置语法高亮器的样式,Key
标签用于设置 textArea
的样式。
各种样式包括
注释
字符串
关键字
变量
存储
恒定
TagName
TagBracket
AttributeName
AttributeValue
DoctypeDeclaration
CSSProperty
CSSPropertyValue
CSSSelector
预处理器
Punctuation
LibraryFunction
LibraryClass
键
背景
Foreground
Caret
LineNumber
LineNumberPadding
CurrentLine
选择
ServicesLine
书签
FoldingIndication
SameWords
BracketStyle
BracketStyle2
它是如何工作的?
请参阅 YnoteThemeReader.cs。
当 ynote 加载主题文件时,键值会被解析并分配给 FastColoredTextBox
。
请参阅 SyntaxHighlighter.cs。它有各种公共样式(来自 FastColoredTextBoxNS.Style
),值被分配给这些样式,并且语法高亮器只使用该样式。例如
public void HighlightSyntax(Range r)
{
r.tb.CommentPrefix = "#";
r.ClearStyle(Comment, String);
r.SetStyle(Comment, @"#.*$", RegexOptions.Multiline)
r.SetStyle(String, @"""""|@""""|''|@"".*?""|(?<!@)(?<range>"".*?[^\\]"")|'.*?[^\\]'")
}
停靠
Ynote Classic 使用 DockPanelSuite
进行停靠,并采用 VS2012 浅色主题。
代码片段
Ynote Classic 支持从 .ynotesnippet 文件加载的代码片段。每个代码片段具有以下属性
TabTrigger
:当用户在{TabTrigger}
后按下 Tab 键时,将调用代码片段Content
:代码片段的内容Scope
:代码片段的范围(HTML、CSS、CSharp 等)
创建代码片段
任何人都可以创建代码片段以简化工作流程。YnoteSnippet 内容的语法是
^
:插入代码片段后光标的位置$selection
:触发代码片段时选定的文本$current_line
:触发代码片段时当前行的文本$file_name
:正在编辑的文件名$file_name_extension
:正在编辑的文件的名称和扩展名$clipboard
:剪贴板上的文本$eol
:行尾文字以获取当前行尾$choose_file
:加载OpenFileDialog
并替换为选定的文件
编辑
Ynote 可以让您的编辑体验非常棒。一些功能包括
多光标/多选
使用 Ctrl+单击 添加另一个光标或选择并开始编辑。Ynote 目前不支持同一行上的多个光标。
垂直/列选择
使用 Alt+拖动 或 Alt+Shift+箭头键选择一个区域并开始编辑文本。
分屏编辑
分屏编辑是充分利用宽屏显示器的最佳方式。Ynote 支持带可停靠窗口的分屏编辑。您可以通过以下方式分屏编辑文件:
- 视图 -> 分割 -> 在下方分割 - 在活动文档下方分割文档
- 视图 -> 分割 -> 在旁边分割 - 在活动文档旁边分割文档
- 视图 -> 分割 -> 同步滚动分割 - 同步滚动分割文档
Ynote 中的分屏编辑
搜索/替换
Ynote 具有强大的搜索和替换功能。它支持“查找下一个”、“查找上一个”、“在文件夹中查找”、“在项目中查找”以及带正则表达式的“增量搜索”。
它还可以使用 Alt+F+{char} 查找字符。
宏
Ynote 使用 FastColoredTextBox
的技术通过存储按下的键来录制和执行宏。
Ynote 宏以 .ynotemacro 扩展名存储在 $ynotedata\ 目录中的任何位置。
录制宏
可以通过按 Ctrl+M 并执行一些操作来录制宏。
注意:鼠标操作不被记录在宏中
使用 Ctrl+M 停止录制宏
执行宏
可以使用 Ctrl+E 播放宏。
您也可以保存宏以供以后执行。它应该保存在 $ynotedata\
目录中,扩展名为 .ynotemacro。
宏快捷方式
所以你想用快捷方式执行宏?Ynote 可以做到。在 $ynotedata
目录下创建一个名为 User.ynotekeys 的文件。
您可以逐行输入 YnoteCommands
形式的快捷方式。例如(我的 User.ynotekeys
)
Ctrl+Shift+Q=Macro:AddLineBefore
Ctrl+Shfit+M=Script:ColorPicker
您需要按照它在 Commander 中显示的方式输入命令。它可以包含任何命令。快捷方式应由换行符(\r\n
)分隔。
脚本
我非常喜欢 ynote 的原因之一是脚本功能。脚本功能是通过 CSScript 库实现的。
脚本在 Ynote 中以 .ys 文件存储。在 ynote 中,脚本已被用于
- Ynote 命令(Commander)——位于 $ynotedata\Commands 目录
- Ynote 脚本——位于 $ynotedata\Scripts 目录
- 运行脚本任务——位于 $ynotedata\RunScripts\Tasks
- 上下文菜单——位于 $ynotedata\ContextMenu.ys
脚本被编译成 .ysc 文件以加快执行速度。
命令器
Ynote Commander 是一款将所有有用命令置于您指尖的工具。只需使用 Ctrl+Shift+P
,Commander 就会弹出。开始输入您想要的任何内容。
使用命令器
自定义命令
Ynote 支持从 $ynotedata\Commands 目录添加自定义命令。
Ynote 命令是一个 C# 脚本,扩展名为 .ynotecommand。它包含一个带参数 IYnote
的方法 GetCommand
。当被调用时,它应该返回 ICommand
接口的一个实例。
namespace SS.Ynote.Classic
{
/// <summary>
/// A Ynote Command which when executed
/// is stored in a YnoteCommand
/// </summary>
public interface ICommand
{
/// <summary>
/// Command Key
/// </summary>
string Key { get; }
/// <summary>
/// Possible Commands
/// </summary>
string[] Commands { get; }
/// <summary>
/// Processes Command
/// </summary>
/// <param name="val"></param>
/// <param name="ynote"></param>
void ProcessCommand(string val, IYnote ynote);
}
}
Key
- Key 是命令的类,例如 - 在命令SetSyntax:CSharp
中,SetSyntax
是 Key,CSharp 是值。Commands
- 可能的命令列表(用于自动补全)ProcessCommand(string,IYnote)
- 处理值为val
的命令。
构建系统 (RunScripts)
Ynote 使用 JSON 格式的 RunScripts 作为构建系统。每个 RunScript
可以调用一个或多个 Tasks
。示例 RunScript
// Run Script to Run a python file
{
// Path of the task and arguments (task specific) from $ynotedata directory
"RunScripts\\Tasks\\Cmd": [
"python",
"$source"
]
}
通过 Commander->Run:{runscript 名称} 运行
此 RunScript 调用存储在 $ynotedata\RunScripts\Tasks\ 目录中的任务 Cmd.runtask
。
您可以添加无限个任务,它们将一个接一个地被调用。
变量
$source
- 正在编辑的活动文件$source_dir
- 正在编辑的活动文件的目录$source_name
- 正在编辑的活动文件的名称$source_extension
- 正在编辑的活动文件的扩展名$project_dir
- 当前打开项目的目录$project_name
- 当前打开项目的名称
自定义任务
Ynote 任务不过是一段 C# 代码。
它应该包含一个带有 string
数组作为参数的 RunTask
方法。例如
// RunScript Task to Create A Directory
using System.IO;
// Cmd Run Script Task
public void RunTask(string[] arguments)
{
if(arguments.Length == 0)
return;
string dir = arguments[0];
if(!Directory.Exists(dir))
Directory.CreateDirectory(dir);
}
RunTasks 存储在 $ynotedata\RunScripts\Tasks 目录中,扩展名为 .runtask。您可以将其存储在任何目录中,但必须在 $ynotedata 中。
符号列表
这对我来说是一个挑战。我以为这会让我的程序变得庞大。但是,我后来想到了使用 Regular Expressions
的想法。它让我的任务变得更轻松。这就是 ynote 的工作方式。它将文本与正则表达式匹配以获取函数/类等的列表。
正则表达式是完全可定制的。位于 $ynotedata
\Symbols.json。
Symbols.json(预览)
{
"CSharp": {
"Pattern": "\\b(class|struct|enum|interface|void)\\s+(?<range>\\w+?)\\b",
"Options": 0
},
"C": {
"Pattern": "\\b(class|struct|enum|interface|void|int|bool)\\s+(?<range>\\w+?)\\b",
"Options": 0
},
"CPP": {
"Pattern": "\\b(class|struct|enum|interface|void|int|bool)\\s+(?<range>\\w+?)\\b",
"Options": 0
},
"VB": {
"Pattern": "\\b(Class|Sub|Interface)\\s+(?<range>\\w+?)\\b",
"Options": 0nn
},
"D": {
按键绑定
Ynote 使用 .ynotekeys 文件存储 KeyBindings
。其格式为
{Key}:{Command}
* 它们由换行符分隔。
Editor.ynotekeys
编辑器按键绑定是 FastColoredTextBox
控件的按键绑定。可以通过热键编辑器或从 $ynotedata\Editor.ynotekeys 目录打开 Editor.ynotekeys
进行编辑。
User.ynotekeys
User.ynotekeys 文件默认不存在。可以通过“工具”->“用户按键”菜单创建。它执行在 Commander 中找到的 YnoteCommands
。例如:
Ctrl+Shift+K=Script:ColorPicker
当您按下 Ctrl+Shift+K 时,它会执行 ColorPicker.ys,该脚本会显示一个颜色选择器并插入所选颜色。
软件包
Ynote 包是一个包含索引文件的归档文件。它包含用于扩展 ynote 的资源文件,例如
- 插件
- 配色方案
- Ynote脚本
- 片段
- 运行脚本
- 运行脚本任务
- Ynote命令
- 语法文件
- 宏
- 上下文菜单等等。
包如何工作?
ynote 包文件是一个 zip 文件,在根目录中包含所有必需文件和一个索引文件。索引文件包含文件安装后应放置位置的信息。安装包时,第一个提取的文件是索引文件。Ynote 使用 ZipStorer
管理 zip 文件。以下代码生成一个字典,指示文件应放置的位置。
internal static IDictionary<string, string> GenerateDictionary(string manifest)
{
IDictionary<string,string> dic = new Dictionary<string,string>();
string[] lines = File.ReadAllLines(manifest);
foreach (var line in lines)
{
var command = YnoteCommand.FromString(line);
command.Value = command.Value.Replace("$ynotedata", GlobalSettings.SettingsDir);
if (command.Value.IndexOf("$ynotedir") != -1)
command.Value = command.Value.Replace("$ynotedir", Application.StartupPath);
dic.Add(command.Key, command.Value);
}
return dic;
}
它使用 YnoteCommand
类来解析 string
,因为它也是 {key}
:{value}
格式。
安装软件包
Ynote 内置支持通过使用 Package Manager
安装软件包。
工具->包管理器 将为您提供可用包列表。它是一键下载和安装。
您也可以从文件安装软件包。使用“从文件安装”来从文件安装软件包。
创建包
您可以使用 Package Manager
创建包。
转到“工具”->“包管理器”,选择“已安装包”选项卡,然后单击“创建包”。
选择一个输出文件并添加您想要的文件及其输出目的地
$ynotedata
- %appdata%\Ynote Classic 或便携版中的 {install dir}\Packages$ynotedir
- {安装目录}\(便携版和安装版相同,用于复制所需的程序集。如果使用此选项,您应该以管理员身份安装包,因为用户可能已将 ynote 安装在 Program Files 目录中)
提交包
您可以通过在 ynotepackages 仓库中创建拉取请求来提交您的包。请参阅仓库中的 README.md 文件以获取信息。
待办事项
Ynote 必须日复一日,版本接版本地改进。我可能在下一个版本 (2.9) 中添加的一些内容如下所示
- 改进代码片段 - 像 Textmate 的那样
- 更好的性能和启动时间
- 切换到 IronPython 进行脚本编写(也许)并改进 API
- 改进多光标和多选支持
- 可主题化的停靠面板
- 更好的语法高亮界面
- 改进的项目 TreeView GUI
- 改进的设置框架
- 改进的 Commander
外部资源
历史
- 首次发布
- 更新的文章 ( 2.8.5 Beta )