安利介绍
上一篇介绍了,如何实现一个自定义内容高亮的插件,但是从产品的角度来看,并不完美,并不极致,并不好用。上一次主要实现的效果是这样的:
那么这一次我们来锦上添花,给工作区做扩展,让他能够记录每一次review的代码文件,并且能够点击列表跳到对应的文件里去。
锦上添花
先看效果:
主要是编辑器里高亮的部分可以在左侧的工作区,有一个面板能够记录当前review的文件地址,并且点击后能够快速跳转到对应的文件。
实现逻辑
新建面板
在vscode里新建一个工作区的面板,首先得在package.json里加一个字段。如下:
这样就会有一个自定义名称的面板出现。
构建面板需要的渲染数据
要在这个面板区域填充文件列表,需要准备他所需要的数据,参考官网地址
class TreeReview {
constructor(context) {
this.context = context;
this.initTree();
console.log("初始化review");
}
initTree() {
const registerData = createRegisterData(clickTemplateHandel);
registrationCommand(registerData);
vscode.window.createTreeView("reviewHistory", { treeDataProvider: nodeWithIdTreeDataProvider(), showCollapseAll: true });
}
}
reviewHistory为上面所定义的id,那么关键是实现treeDataProvider的这个函数,来为面板提供数据。
如图所示,我们要有一个类,然后提供他需要的四个方法,这里简单一点我直接用的js返回一个对象,然后对象里有这四个方法也是可以的。
function nodeWithIdTreeDataProvider() {
return {
getChildren: (element) => {
// 判断上级是否有父级节点,root根节点不算undefine
console.log(element, "根节点");
let children = [];
// let TreeData = providerData()
const providerData = createTree();
for (let index = 0; index < providerData.length; index++) {
const element = providerData[index];
var item = new vscode.TreeItem(element.label, vscode.TreeItemCollapsibleState.None);
item.command = element.command;
item.iconPath = iconPath;
item.id = element.id;
children[index] = item;
}
return children;
},
getTreeItem: (element) => {
return element;
},
};
}
- 每一个列表需要一个TreeItem实例,来显示列表的名称/图标/点击所需绑定的命令。
- 这里还有一个问题就是数据是哪来的,也就是代码上的providerData从哪来。
这里数据来源其实可以去新建一个json文件,然后读取这个json文件里的数据,来实现面板数据的来源,包括在删除编辑器里review的内容时,本质也是更新这个json文件里的数据,来进行更新。
构建json数据
新建一个json文件,内容可以如下:
"Guide\\GuideItem.tsx": { "filePath": "\\Guide\\GuideItem.tsx", "reviewNum": 1, "rootPath": "d:\\xx\\项目名称" }
这里的文件地址是用,editor.document.fileName里拿到的,所以写入进去的时候对斜杠会进行转义。方便点击的时候直接拿到fIlepath进行跳转。
面板跟工作区的通信
在上一节的setDecorationToData 函数里,对所有review的内容高亮后就需要进行更新json里的内容,本质就是天才json数据。
updateTreeReview() {
let filePath = this.editor.document.fileName;
let fileName = filePath.match(/\w+\\\w+\w+-?\w+(\.\w+)/g)[0];
let result = Object.keys(Tree).some((el) => {
return el === fileName;
});
if (!result) {
Tree[fileName] = {
filePath: filePath,
reviewNum: 1,
rootPath: rootPath,
};
}
}
writeFile(path.resolve(__dirname, "../TreeReview/reviewData.json"), JSON.stringify(Tree));
this.TreeRivew.initTree();
}
绑定对应的事件
终于到了最后一步,当点击列表的时候,需要跳转到对应的地址,之前在渲染json数据的时候,已经存入的filepath了,这个时候只要在点击的回调函数里,拿到那个item就能拿到所有的信息
function registrationCommand(arg) {
if (!Array.isArray(arg)) throw new Error("请传入数组");
let register = arg;
register.forEach((el) => {
const key = Object.keys(el)[0];
try {
vscode.commands.getCommands(false).then((res) => {
let isregister = res.includes(key);
console.log(isregister, "是否注册");
if (isregister === false) {
let result = vscode.commands.registerCommand(key, el[key]);
el.result = result;
}
});
} catch (error) {
console.log(error,'注册命令失败');
}
});
return register;
}
将json里的数据传入arg,然后**vscode.commands.registerCommand()方法 **注册所有命令,key为文件地址,el[key]为对应的item.
- 注意 这里每次注册前先要判断当前的文件地址是否已经被注册过了,否则会报错。
其他工具篇
插件名称叫apop-code,可以下载用用,欢迎交流
- 快速推送选择的代码片段到指定企业微信群:
通过设置webhook地址可以推送到指定群:
- 根据自定义文件模板快速创建文件夹
- 一键清空debugger/console
- 根据模板快速创建文件
vscode插件还有很多很多的api没有用到,还能做出更加好玩有趣的事情,提升效率,学习技术。为自己和他人创造价值是一件很酷的事情。目前在思考用插件下一步该做什么呢、