代码内选择器、代码区域 (idea)
代码内选择器、代码区域 (idea)
需求
像一些类对象/html类型的逻辑,会是下面这样的,分块上很清晰:
class C {
public a { // 折叠开始位置
...
} // 折叠结束位置
public b {
...
}
}但一些混合范式的代码,或者一个函数中内容很多,需要区分很多部分时。vscode有没有什么好用的代码折叠/分区插件,例如:
// 全局存储部分
...
...
// 自动更新 - 避免双向同步无限循环
...
...
// 自动更新 - string -> data
...
...例如我这里的代码,我想根据注释头,可以将这里分成成三个部分,就像三个函数那样。
最好能通过插件很自然地表示出这个三区域,能方便地折叠、跳转、维护
从Markdown中获取灵感
对于md来说,指定多个区域,使区域之间区分明显/高亮/可折叠,这通常可以通过一些方法来完成:
- markdown标题
- html detail块
- callout块
- markdown-it-container 选择器
- anyblock选择器 (包括
:::的markdown-it-container头尾选择器)
而对于代码来说,这些方案可以参考借鉴,但会更受限,因为必须通过注释进行标注!
调研了一番,确实存在一些方案
方案 - region 相关
region 也叫 “代码区域”,语法如下:
| Language | Region start | Region end |
|---|---|---|
| Bat | ::#region [name] or REM #region [name] | ::#endregion or REM #endregion |
| C# | #region [name] | #endregion |
| C/C++ | #pragma region [name] | #pragma endregion |
| CSS / Less / SCSS | /*#region [name]*/ | /*#endregion*/ |
| Coffeescript | #region [name] | #endregion |
| F# | //#region [name] or (#region [name]) | //#endregion or (#endregion) |
| Go | //#region [name] | //#endregion |
| HTML / XML | <!-- #region [name] --> | <!-- #endregion --> |
| Java | //#region [name] | //#endregion |
| Markdown | <!-- #region [name] --> | <!-- #endregion --> |
| Perl5 | #region [name] | #endregion |
| PHP | #region [name] | #endregion |
| PowerShell | #region [name] | #endregion |
| Python | #region [name] or # region [name] | #endregion or # endregion |
| Shellscript | #region [name] or # region [name] | #endregion or # endregion |
| TypeScript / JavaScript | //#region [name] | //#endregion |
| Visual Basic | #Region [name] | #End Region |
| Yaml | #region [name] or # region [name] | #endregion or # endregion |
region (原生)
特点:
- 原生支持方案
- 无需插件
- 支持侧边栏大纲导航 (但我没有看到,估计是我之前设置过大纲的显示内容,给屏蔽了)
- 操作:头尾注释。有点像 markdown-it
// #region 一个打印测试
console.log('测试1')
console.log('测试2')
console.log('测试3')
// #endregionregion 升级版 (仅语法设计)
region 方案其实也不错,还是原生的。
但是我感觉需要尾注释进行结束标识这点,还是过于臃肿了。所以我想,不需要尾注释也能正常工作的的标注语法 (就像markdown插件anyblock会自动选择结束位置那样)
function a () {
// #region t1 // 规则有点类似于markdown的标题/列表
// 这里的开头是两个空格,那么结束标志就是:(不含结束标志那一行)
// 1. 同级别的reegion标识
// 2. 一直往下找到开头少于两空格的非空行 (即不属于当前作用域)
console.log('测试1')
console.log('测试2')
// #region t2
console.log('测试1')
console.log('测试2')
}region folding for VS Code
110,077down, 2023-03-23
增强:
- 快捷键
- 设置头尾标识规则
配置
"maptz.regionfolder": {
"[ahk]": { // 语言支持
"foldEnd": "; #endregion", // 插入在折页末尾的文本
"foldEndRegex": ";[\\s]*#endregion", // 用于查找折叠结束文本的正则表达式
"foldStart": "; #region [NAME]", // 在折叠开始处插入的文本
// 使用 `[NAME]` 占位符来指示光标在插入后应该放置的位置
"foldStartRegex": ";[\\s]*#region[\\s]*(.*)", // 用于查找折叠起始文本的正则表达式
"disableFolding": false // 关闭该语言的#区域折叠
}
}region Highlighter
19,876down, 2022-01-05
- 快捷键
- 着色增强
Region Folder
- 功能:
- 给
#region添加 🌟 图标标识 - 支持自定义区域折叠样式
- 自动折叠/展开指定层级
- 给
- 配置建议:
"regionFolder.icons": { "start": "🌐", // 自定义起始图标 "end": "🔚" // 自定义结束图标 }
方案 - 其他
空 {}
有时我会选择使用 空 {} 和 立即执行函数的技巧,也可以达到分块、以及提供折叠的选项。
但这需要前提:
{}语法:需要支持{}(如js/c/java等支持,但像python这种靠缩进的就不支持了)
// t1
;{
console.log('测试1')
console.log('测试2')
}
// t2
;{
console.log('测试1')
console.log('测试2')
}
// t3
;(() => {
console.log('测试1')
console.log('测试2')
})()
// t4
;(() => {
console.log('测试1')
console.log('测试2')
})()立即执行函数
有时我会选择使用 空 {} 和 立即执行函数的技巧,也可以达到分块、以及提供折叠的选项。
但这需要前提:
- 立即执行函数:需要支持嵌套局部函数、最好能支持简洁的lambda语法(对于不支持嵌套局部函数的,按我的个人习惯,也可以用
rawFunction_subName()的方式来约定这是一个子函数)
// t1
;{
console.log('测试1')
console.log('测试2')
}
// t2
;{
console.log('测试1')
console.log('测试2')
}
// t3
;(() => {
console.log('测试1')
console.log('测试2')
})()
// t4
;(() => {
console.log('测试1')
console.log('测试2')
})()Better Comments
类似于 obsidian 中的 callout-list 插件,
也有点类似于vitepress中的一个代码块高亮行插件的语法:[!code]/[+code]/[-code]
- 功能:
- 通过不同颜色高亮注释分类(如
//! 重要//? 疑问) - 虽然不直接支持折叠,但能增强注释可读性
- 通过不同颜色高亮注释分类(如
Bookmarks
- 功能:
- 在注释处添加书签标记(
//bookmark) - 支持侧边栏导航和快捷键跳转
- 适合需要高频跳转的场景
- 在注释处添加书签标记(
总结
个人按优雅程度排个序,就是:
头注释 > 空{} > 两端注释 > 局部立即执行函数 > 拆多个函数
基于函数的方案较于基于注释的方法,一个做不到的事就是有些东西放不进函数里。例如要声明一些不在局部的作用变量,又例如一些import语句、宏之类的。如下
// 块1
var v1;
;(() => {
console.log('测试1')
console.log('测试2')
v1 = 1;
})()
// #region 块2
var v2;
console.log('测试1')
console.log('测试2')
v2 = 1;像 python 的 jupyter notebook 就是一个神奇的分块。
他所有块的区分都很明显,也能分别运行。看起来是分别在不同的函数里。但他们的变量却又是共享的,作用域其实都在根部。这种形式就不错
泛用性
take from deepseek
是的,#region 注释折叠功能在多种编程语言中均被支持,但具体实现方式和兼容性因语言和开发工具而异。以下是主要语言的支持情况总结:
| 工具/语言 | 原生支持 | 需插件/配置 |
|---|---|---|
| VS Code | C#、C++、TS/JS、Python、CSS | 无 |
| Visual Studio | C#、C++ | JS/CSS(JSEnhancements) |
| PyCharm | 有限(依赖代码结构) | 需特殊注释格式 |
| JetBrains系列 | Lua、Java | 自定义区域标记 |