自定义菜单
自定义菜单可以通过package.json
中的contributes.menu
来进行配置, 直接贴配置:
// pageage.json
"activationEvents": [
"onCommand:learn-vscode-extends.helloWorld",
"onCommand:learn-vscode-extends.editorTitle",
"onCommand:learn-vscode-extends.explorerContext"
],
"contributes": {
"commands": [
{
"command": "learn-vscode-extends.helloWorld",
"title": "helloWorld",
"icon": "$(getting-started-setup)"
},
{
"command": "learn-vscode-extends.editorTitle",
"title": "编辑器标题",
"icon": "$(tools)" // 指定icon(当被菜单绑定时显示, 否则显示 title)
},
{
"command": "learn-vscode-extends.explorerContext",
"title": "资源右键菜单"
}
],
"menus": {
"editor/title": [ //编辑器标题
{
"command": "learn-vscode-extends.editorTitle", // 点击触发的事件id
"alt": "learn-vscode-extends.helloWorld", // 按住 ait 键显示切换到那个命令
"group": "navigation", // 指定分组 "navigation" 总是被排序到菜单的顶部/开头, 详细的分组信息见这里 https://code.visualstudio.com/api/references/contribution-points#Sorting-of-groups
"when": "editorFocus && resourceLangId == typescript" // 编辑器具有焦点,并且打开的是ts文件才会出现
}
],
"explorer/context": [ // 资源管理器右键菜单
{
"command": "learn-vscode-extends.explorerContext",
"group": "6_copypath" // 详细的分组信息见这里 https://code.visualstudio.com/api/references/contribution-points#Sorting-of-groups
}
]
}
},
对应的注册命令代码:
// src/extension.ts
import * as vscode from "vscode";
export function activate(context: vscode.ExtensionContext) {
// helloWorld 命令
context.subscriptions.push(
vscode.commands.registerCommand("learn-vscode-extends.helloWorld", () => {
vscode.window.showInformationMessage("hello world");
})
);
context.subscriptions.push(
vscode.commands.registerCommand("learn-vscode-extends.editorTitle", () => {
vscode.window.showInformationMessage("编译器标题菜单");
})
);
// 资源右键菜单的回调可以拿到当前点击和所有选中的 Uri 信息(通过命令触发则没有)
// clickFileUrl: 当前选中的 Uri 信息
// filePaths: 所欲选中的 Uri 信息
context.subscriptions.push(
vscode.commands.registerCommand("learn-vscode-extends.explorerContext", (clickFileUrl: vscode.Uri, filePaths: vscode.Uri[]) => {
vscode.window.showInformationMessage("资源右键菜单");
if (Array.isArray(filePaths)) {
// "\n" + 路径 拼成字符串
const msg = filePaths.map(url => ("\n" + url.fsPath)).join("");
vscode.window.showInformationMessage("选中的文件路径: " + msg);
}
})
);
}
export function deactivate() { }
编辑器菜单点击效果
注意: 编辑器需要获取焦点, 并且这个文件需要是
ts
文件才会出现(详细了解见when)
编辑器菜单alt
+点击效果
资源右键菜单效果
悬停提示
悬停提示可以使用vscode.languages.registerHoverProvider
, 如下:
// src/extension.ts
import * as vscode from "vscode";
export function activate(context: vscode.ExtensionContext) {
console.log("activate run ...");
vscode.languages.registerHoverProvider(
{ scheme: "file", language: "json", }, // 匹配 json 文件
{
provideHover(doc: vscode.TextDocument, position: vscode.Position, token: vscode.CancellationToken) {
// 当前文件类型
console.log(doc.languageId);
// 文件是否未保存更改
console.log(doc.isDirty);
// 获取当前文件
console.log(doc.fileName);
// 获取当前hover的单词
const word = doc.getText(
doc.getWordRangeAtPosition(position)
);
// 对 json 文件中的 description 单词进行悬停提示
if (/\bdescription\b/.test(word)) {
return new vscode.Hover("悬停提示: 填写描述信息");
}
},
});
}
export function deactivate() { }
到这里如果使用F5
运行, 会发现没有效果, activate
的console.log
没有输出, 修改pageage.json
中的activationEvents
, 如下:
"activationEvents": [
"onLanguage:json" // 当碰到 json 文件时激活扩展(调用`activate`函数)
],
扩展激活相关的详细可以见 Activation Events
效果如下:
代码片段
扩展中设置代码片段, 在package.json
中的contributes.snippets
设置:
// package.json
"contributes": {
"snippets": [
{
"language": "javascript", // 指定语言
"path": "./src/snippets/js.json" // 设置代码片段的路径
}
]
},
对应的src/snippets/js.json
文件配置, 跟在vscode自定义代码片段是一样的, 如下:
{
"console.log": {
"prefix": ["log", "logv"], // 代码片段匹配的前缀
"body": "console.log(\"${0} :\", ${0});", // 代码块(可以是数组), ${n} 表示是第几个光标, 0 表示最后一个光标
"description": "打印变量" // 对应描述
}
}
效果:
下面是一些常用的代码片段语法:
${n}
: 表示是第几个光标(多个光标通过tab
跳到下一个光标),${0}
则表示最后一个光标${1:hello}
: 第一个光标中的默认值为hello
${1|one,two,three|}
: 第一个光标中提供三个下拉单选值, 默认为one
下面是两个代码片段对应了生成vue2
和vue3
的模块:
{
"vue2-template": {
"prefix": "vue2-template",
"body": [
"<template>",
"\t<div></div>",
"</template>",
"",
"<script>",
"export default {",
"\tname: \"${1}\",",
"\tdata() {",
"\t\treturn {",
"\t\t\t$0",
"\t\t};",
"\t},",
"};",
"</script>",
"",
"<style lang=\"${2|scss,less|}\" ${3:scoped}>",
"</style>"
],
"description": "vue2 模板"
},
"vue3-template": {
"prefix": "vue3-template",
"body": [
"<template>",
"$0",
"</template>",
"",
"<script ${1:lang=\"ts\"} setup>",
"import { ref, reactive, computed, watch, nextTick, onMounted } from \"vue\";",
"defineProps({});",
"defineEmits([]);",
"",
"</script>",
"",
"<style ${2:scoped} ${3:module}>",
"",
"</style>"
],
"description": "vue3 模板"
}
}
想了解更多可以见 snippet-syntax