ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

Visual Studio Code 用户自定义代码片段(Snippets)完全指南:从内置片段、自定义 JSON 到变量转换与作用域控制

Visual Studio Code 用户自定义代码片段(Snippets)完全指南:从内置片段、自定义 JSON 到变量转换与作用域控制 文档教程【免费下载链接】vscode-docsPublic documentation for Visual Studio Code项目地址https://gitcode.com/gh_mirrors/vs/vscode-docs点击查看免费下载代码片段Snippets是 VS Code 中用来快速输入重复代码模式的模板例如循环、条件语句或一段完整的日志输出。本文以官方文档 docs/editing/userdefinedsnippets.md 为主体系统讲解代码片段在内置、Marketplace 扩展、用户自定义三种来源下的使用方式并深入剖析片段文件的 JSON 结构、prefix/body/description字段、占位符与 Tabstop 跳转机制、完整变量与变量转换语法以及语言、项目、文件模式三种作用域控制手段。读完本文你将能够独立编写、调试、共享和打包自己的代码片段并把片段绑定到自定义键盘快捷键上。什么是代码片段代码片段是预先写好的、可复用的代码模板用于加速重复代码模式的输入——比如for循环、if-else分支、函数定义或样板注释。在 VS Code 中片段会以两种方式呈现混入 IntelliSense 建议列表与普通补全建议一起出现可通过触发智能提示的快捷键kb(editor.action.triggerSuggest)唤起独立的片段选择器在命令面板中运行Insert Snippet命令可列出当前文件语言可用的全部片段。此外 VS Code 还支持Tab 补全tab-completion在设置中启用editor.tabCompletion: on后输入片段的prefix触发文本并按下插入片段的快捷键kb(insertSnippet)通常为 Tab即可直接插入该片段。代码片段的语法遵循 TextMate 片段语法但有两个例外interpolated shell code插值 shell 代码与\u转义均不支持。使用内置代码片段VS Code 为多种语言内置了开箱即用的代码片段例如 JavaScript、TypeScript、Markdown 和 PHP。要查看某个语言当前可用的全部片段可以打开命令面板kb(workbench.action.showCommands)运行Insert Snippet命令在列表中查看当前文件语言对应的全部片段。需要注意这个列表不仅包含内置片段还会混入你自己定义的用户片段以及已安装扩展提供的片段。如果希望只看某一类来源可以结合下文的作用域与隐藏机制来管理。从 Marketplace 安装代码片段扩展许多 VS Code 扩展都会随包附带代码片段例如语言支持、框架工具类扩展。查找这类扩展的方法是打开扩展视图kb(workbench.view.extensions)在搜索框中输入过滤器category:snippets浏览结果并安装你需要的扩展。安装完成后重启 VS Code新片段即可生效。这种方式适合直接复用社区维护好的片段集合而无需自己编写。创建自己的代码片段不依赖任何扩展你可以直接在 VS Code 中定义自己的片段。操作路径如下菜单FilePreferencesConfigure Snippets即命令Snippets: Configure Snippets在弹出的下拉菜单中选择一种语言按语言标识符区分例如javascript、typescript、python片段只会在该语言文件中出现或选择New Global Snippets file新建全局代码片段文件片段适用于所有语言也可以选择New Snippets file for folder-name...创建项目级片段文件详见下文项目片段作用域。选择后 VS Code 会自动创建/刷新对应的片段 JSON 文件你只需写入内容即可。片段文件以 JSON 编写、支持 C 风格注释//、/* */并且可以定义不限数量的片段。以下是一个针对 JavaScript 的for循环片段示例位于用户片段文件Code/User/snippets/javascript.json// in file Code/User/snippets/javascript.json { For Loop: { prefix: [ for, for-const ], body: [ for (const ${2:element} of ${1:array}) {, \t$0, } ], description: A for loop. } }各字段含义如下片段名此例为For Loop片段在列表中的显示名称。如果未提供description片段名会直接显示在 IntelliSense 中prefix一个或多个触发词。当输入这些文本时片段会出现在 IntelliSense 中。匹配采用子串匹配因此本例中fc也能匹配到for-constbody一行或多行内容插入时会被拼接为多行文本。其中的换行与嵌入制表符会根据插入位置的上下文自动格式化缩进description可选的描述文本由 IntelliSense 显示帮助区分同名片段。示例body中包含三个占位符按遍历顺序${1:array}、${2:element}和$0。插入片段后你可以用跳转到下一个占位符的快捷键kb(jumpToNextSnippetPlaceholder)默认 Tab快速在占位符间移动并编辑。冒号:后的字符串是默认文本例如${2:element}中的element。占位符的遍历顺序按编号从小到大从1开始$0是可选的特殊位置总是最后访问到达后退出片段模式并将光标停在指定位置。文件模板片段如果某个片段的本意是填充或替换整个文件的内容例如新建文件时的样板模板可以为其添加isFileTemplate属性{ My File Template: { prefix: template-name, body: [ # ${1:title}, , ${0} ], isFileTemplate: true } }标记为文件模板的片段会在你于新文件或已有文件中运行Snippets: Fill File with Snippet命令时出现在一个专门的下拉列表中方便按模板一键生成文件内容。代码片段作用域片段是有作用域的VS Code 只会建议与当前上下文相关的片段。作用域可以从两个维度控制语言片段适用于哪些语言可能是全部语言项目片段适用于哪些项目通常适用于全部项目。此外还有更细粒度的文件模式控制include/exclude。语言片段作用域每个片段都会根据其定义位置被限定到一个、多个或全部全局语言单语言片段定义在某个特定语言的片段文件中例如javascript.json可通过Snippets: Configure Snippets按语言标识符访问。这类片段仅在编辑该语言文件时可用多语言 / 全局片段定义在全局片段文件中JSON 文件后缀为.code-snippets同样通过Snippets: Configure Snippets访问。在全局片段文件中片段定义可以增加一个可选的scope属性取值为一个或多个语言标识符从而将片段限制到指定语言如果省略scope则该全局片段对所有语言可用。大多数用户自定义片段是单语言的因此通常定义在语言专属片段文件中。若需多语言共享或全局可用则使用.code-snippets文件配合scope。项目片段作用域你还可以将全局片段文件.code-snippets限定到某个项目。项目级片段通过Snippets: Configure Snippets下拉菜单中的New Snippets file for folder-name...创建存放于项目根目录的.vscode文件夹中。项目片段适合与参与该项目的所有开发者共享配合版本控制提交其行为与全局片段类似也可以通过scope属性限定到特定语言。文件模式作用域include与exclude两个可选属性可以进一步控制片段出现的位置它们同时适用于语言专属片段文件和全局片段文件并可与scope属性组合以实现更精确的控制include一个 glob 模式或 glob 模式数组指定片段应出现在哪些文件中exclude一个 glob 模式或 glob 模式数组指定片段不应出现在哪些文件中。模式匹配规则如下仅文件名模式例如*.test.ts仅基于文件名匹配与文件在项目中的位置无关基于路径的模式例如**/*.test.ts或**/dist/**匹配完整文件路径若某个文件同时命中include与excludeexclude优先若两者都未指定则片段根据scope属性出现在所有适用文件中。示例测试片段仅出现在 TypeScript 测试文件中{ Test Block: { prefix: test, body: [ test(${1:description}, () {, \t${0}, }); ], description: Insert a test block, scope: typescript, include: [**/*.test.ts, **/*.spec.ts] } }示例排除目录出现在所有 JavaScript 文件中但排除dist与node_modules目录{ Console Log: { prefix: log, body: console.log(${0});, description: Insert console.log, scope: javascript, exclude: [**/dist/**, **/node_modules/**] } }示例配置文件片段使用仅文件名模式仅出现在travis.yml中{ Travis CI Node: { prefix: travis-node, body: [ language: node_js, node_js:, - ${1:18} ], description: Travis CI Node.js configuration, scope: yaml, include: [travis.yml] } }合理使用include/exclude可以显著减少 IntelliSense 中的干扰项让片段只在其真正相关的文件中出现。代码片段语法详解片段的body可以使用多种特殊结构来控制光标位置与插入文本其核心语法遵循 TextMate 片段规范去掉不支持的 shell 插值与\u。Tabstops制表位使用$1、$2指定光标位置数字表示访问顺序$0表示最终光标位置。同一 Tabstop 的多次出现是关联同步的——编辑其中一个其余位置会同步更新。{ Print: { prefix: print, body: console.log($1)$0 } }Placeholders占位符占位符是带默认值的 Tabstop语法为${1:foo}。插入片段时默认文本会被选中方便直接输入替换。占位符支持嵌套例如${1:another ${2:placeholder}}。Choice选项占位符的值可以是可选项列表语法为用管道符|包围、逗号分隔的枚举例如${1|one,two,three|}。片段插入并选中该占位符时VS Code 会提示用户在候选项中挑选一个。Variables变量使用$name或${name:default}可插入变量的值变量未设置时插入其default值若提供或空字符串变量未知名字未定义时插入变量名本身并将其转换为占位符。可用变量分为以下几类。文档与光标相关变量变量含义TM_SELECTED_TEXT当前选中的文本或空字符串TM_CURRENT_LINE当前行的内容TM_CURRENT_WORD光标所在单词的内容或空字符串TM_LINE_INDEX基于 0 的行号TM_LINE_NUMBER基于 1 的行号TM_FILENAME当前文档的文件名TM_FILENAME_BASE当前文档不含扩展名的文件名TM_DIRECTORY当前文档所在目录TM_FILEPATH当前文档的完整文件路径RELATIVE_FILEPATH相对于打开的工作区或文件夹的当前文档路径CLIPBOARD剪贴板内容WORKSPACE_NAME打开的工作区或文件夹的名称WORKSPACE_FOLDER打开的工作区或文件夹的路径CURSOR_INDEX基于 0 的光标编号CURSOR_NUMBER基于 1 的光标编号当前日期与时间变量变量含义CURRENT_YEAR当前年份CURRENT_YEAR_SHORT当前年份的后两位CURRENT_MONTH两位数字的月份如02CURRENT_MONTH_NAME月份完整名称如JulyCURRENT_MONTH_NAME_SHORT月份简称如JulCURRENT_DATE两位数字的当月日期如08CURRENT_DAY_NAME星期完整名称如MondayCURRENT_DAY_NAME_SHORT星期简称如MonCURRENT_HOUR24 小时制当前小时CURRENT_MINUTE两位数字的当前分钟CURRENT_SECOND两位数字的当前秒CURRENT_MILLISECOND三位数字的当前毫秒如078CURRENT_SECONDS_UNIX自 Unix 纪元以来的秒数CURRENT_MILLISECONDS_UNIX自 Unix 纪元以来的毫秒数CURRENT_TIMEZONE_OFFSET当前 UTC 时区偏移格式HH:MM或-HH:MM如-07:00CURRENT_TIMEZONE_NAME当前时区的 IANA 名称如America/Los_Angeles随机值变量变量含义RANDOM6 位随机十进制数字RANDOM_HEX6 位随机十六进制数字UUID一个 Version 4 UUID行注释 / 块注释变量自动匹配当前语言变量示例输出BLOCK_COMMENT_STARTPHP 中为/*HTML 中为!--BLOCK_COMMENT_ENDPHP 中为*/HTML 中为--LINE_COMMENTPHP 中为//下面的片段会在 JavaScript 文件中插入/* Hello World */在 HTML 文件中插入!-- Hello World --{ hello: { scope: javascript,html, prefix: hello, body: $BLOCK_COMMENT_START Hello World $BLOCK_COMMENT_END } }变量转换Variable transforms转换允许在插入前修改变量的值。一个转换由三部分组成正则表达式与变量值匹配变量无法解析时匹配空字符串格式字符串引用正则的匹配分组支持条件插入与简单改写选项传递给正则表达式的选项如g、i等。以下示例取出当前文件名并去掉扩展名将foo.txt转换为foo${TM_FILENAME/(.*)\\..$/$1/} | | | | | | | |- no options | | | | | |- references the contents of the first | | capture group | | | |- regex to capture everything before | the final .suffix | |- resolves to the filename占位符转换Placeholder-Transform与变量转换类似占位符转换允许在跳转到下一个 Tabstop 时改写占位符中已插入的文本插入的文本与正则表达式匹配匹配结果取决于选项被替换为指定的替换格式文本。每个占位符出现处都可以基于第一个占位符的值独立定义自己的转换其格式与变量转换完全相同。转换示例下面的示例以双引号形式展示即片段 body 中的真实写法以说明某些字符需要双重转义。转换作用于文件名example-123.456-TEST.js示例输出说明${TM_FILENAME/[\\.]/_/}example-123_456-TEST.js将第一个.替换为_${TM_FILENAME/[\\.-]/_/g}example_123_456_TEST_js将每个.或-替换为_${TM_FILENAME/(.*)/${1:/upcase}/}EXAMPLE-123.456-TEST.JS全部转为大写${TM_FILENAME/[^0-9a-z]//gi}example123456TESTjs删除所有非字母数字字符文法Grammar片段语法可用下面的 EBNF扩展巴科斯范式完整描述。使用反斜杠\可以转义$、}和\。在 choice 元素内部反斜杠还可转义逗号与管道符。只有必须转义的字符才需要转义因此在这些结构中$不应转义在 choice 结构内部$与}都不应转义。any :: tabstop | placeholder | choice | variable | text tabstop :: $ int | ${ int } | ${ int transform } placeholder :: ${ int : any } choice :: ${ int | text (, text)* |} variable :: $ var | ${ var } | ${ var : any } | ${ var transform } transform :: / regex / (format | text) / options format :: $ int | ${ int } | ${ int : /upcase | /downcase | /capitalize | /camelcase | /pascalcase | /snakecase | /kebabcase } | ${ int : if } | ${ int :? if : else } | ${ int :- else } | ${ int : else } regex :: JavaScript Regular Expression value (ctor-string) options :: JavaScript Regular Expression option (ctor-options) var :: [_a-zA-Z] [_a-zA-Z0-9]* int :: [0-9] text :: .* if :: text else :: text从该文法可以看出format中除了引用分组编号外还内置了upcase、downcase、capitalize、camelcase、pascalcase、snakecase、kebabcase等大小写/命名风格转换以及:存在时插入、:?条件二选一、:-缺省值等条件格式。使用 TextMate 代码片段如果手头已有现成的 TextMate 片段.tmSnippets文件也可以直接用于 VS Code。推荐的方式是将它们打包为扩展具体流程见 API 文档中的 TextMate 片段章节。打包后VS Code 会负责将.tmSnippets转换为自身的片段格式并加载。将片段打包为扩展进行共享除了给自己使用片段还可以打包成扩展上传到扩展市场与团队或社区共享。完整的操作流程记录在 api/language-extensions/snippet-guide.md 中核心步骤如下先用Snippets: Configure User Snippets命令创建并测试你的片段满意后把整个 JSON 片段文件复制到扩展目录中例如snippets.json在扩展的package.json中通过contributes.snippets贡献点声明片段文件{ contributes: { snippets: [ { language: javascript, path: ./snippets.json } ] } }其中language为语言标识符path为片段文件的相对路径文件内容即本文介绍的 VS Code 片段 JSON 格式。提示在package.json中加入以下配置将扩展标记为代码片段类扩展便于在市场上被category:snippets检索到{ categories: [Snippets] }此外也可以使用yo code扩展生成器New Code Snippets选项直接指向一个包含多个.tmSnippets文件的文件夹生成器会将其打包为 VS Code 片段扩展同时支持 Sublime 片段.sublime-snippets。生成结果包含两个文件扩展清单package.json和转换后的snippets.json. ├── snippets // VS Code integration │ └── snippets.json // The JSON file w/ the snippets └── package.json // extensions manifest将生成的snippets文件夹复制到.vscode/extensions下的新目录并重启 VS Code 即可生效。为代码片段分配键盘快捷键你可以通过自定义键盘快捷键直接插入指定片段。打开keybindings.json命令Preferences: Open Keyboard Shortcuts File添加一条将snippet作为额外参数传给editor.action.insertSnippet的键绑定{ key: cmdk 1, command: editor.action.insertSnippet, when: editorTextFocus, args: { snippet: console.log($1)$0 } }这样按下该快捷键时会直接执行Insert Snippet命令但不再弹出选择列表而是插入args.snippet中定义的片段文本。键绑定与普通快捷键一样由键盘组合、命令 ID 和可选的 when clause 上下文控制快捷键何时生效组成。除了内联定义片段还可以通过langId与name参数引用已有片段langId指定片段所属语言name指定片段名称。下面的示例会在按下快捷键时插入csharp语言中名为myFavSnippet的片段{ key: cmdk 1, command: editor.action.insertSnippet, when: editorTextFocus, args: { langId: csharp, name: myFavSnippet } }值得注意的是jumpToNextSnippetPlaceholder跳转到下一个占位符默认绑定在 Tab 键上并可通过keybindings.json调整或移除相关说明见 docs/configure/keybindings.md。常见问题如何在插入的脚本中放入一个变量如果希望片段插入后保留$variable形式的字面文本需要转义$使其不会被片段展开阶段解析为变量。例如VariableSnippet:{ prefix: _Var, body: \\$MyVar 2, description: A basic snippet that places a variable into script with the $ prefix }插入结果为$MyVar 2如何从 IntelliSense 中移除某个片段可以隐藏特定片段使其不再出现在 IntelliSense补全列表中在Insert Snippet命令的下拉列表中点击片段条目右侧的Hide from IntelliSense按钮即可。隐藏后你仍可通过Insert Snippet命令选择该片段但它不会出现在 IntelliSense 建议中。下一步命令行界面VS Code 提供丰富的命令行接口可打开/比较文件、安装扩展扩展 API了解扩展 VS Code 的更多方式Snippet Guide学习如何将片段打包为扩展在 VS Code 中使用。赞分享文档教程【免费下载链接】vscode-docsPublic documentation for Visual Studio Code项目地址https://gitcode.com/gh_mirrors/vs/vscode-docs点击查看免费下载相关推荐10分钟掌握Visual Studio Code代码片段自定义模板与智能触发全指南10分钟掌握Visual Studio Code代码片段自定义模板与智能触发全指南 Visual Studio CodeVS Code作为最受欢迎的代码编开发工具代码编辑器如何高效使用Atom代码片段自定义语言模板与动态变量完全指南如何高效使用Atom代码片段自定义语言模板与动态变量完全指南 Atom作为一款高度可定制的文本编辑器其代码片段Snippets功能能显著提升开发效率。本代码编辑器桌面应用开发工具Onivim 2 代码片段Snippets完整指南补全、占位符导航与自定义Onivim 2 代码片段Snippets完整指南补全、占位符导航与自定义 代码片段Snippets是文本模板用于简化常见源码块的输入尤其适合那些开发工具代码编辑器桌面应用上一篇番茄小说下载器终极指南一键下载EPUB有声书完整方案下一篇番茄小说下载器3分钟学会免费下载小说生成EPUB有声书完整方案创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进