如何在编辑器中开发一个画图功能
VS Code API
vscode
module
catScratchEdit
实现表情生成功能,点击button会随机生成一个猫咪的表情,通过这个例子
- 了解webview和插件通信
- 如何注册编辑器事件和registerCustomEditorProvider提供者
- vsCode.Range的使用
// catScratch.js
const addButtonContainer = document.querySelector('.add-button');
addButtonContainer.querySelector('button').addEventListener('click', () => {
vscode.postMessage({
type: 'add'
});
})
// 插件接收webview消息
webviewPanel.webview.onDidReceiveMessage(e => {
switch (e.type) {
case 'add':
this.addNewScratch(document);
return;
case 'delete':
this.deleteScratch(document, e.id);
return;
}
});
点击button给webview
发送添加的消息,webview
接收消息后,执行插件addNewScratch
方法,将要添加表情。
public static register(context: vscode.ExtensionContext): vscode.Disposable {
const provider = new CatScratchEditorProvider(context);
const providerRegistration = vscode.window.registerCustomEditorProvider(CatScratchEditorProvider.viewType, provider);
return providerRegistration;
}
// package.json
"activationEvents": [
"onCustomEditor:catCustoms.catScratch",
],
注册编辑器事件,传入provider
提供者,并且package.json
加入贡献点,激活事件。
private updateTextDocument(document: vscode.TextDocument, json: any) {
const edit = new vscode.WorkspaceEdit();
// Just replace the entire document every time for this example extension.
// A more complete extension should compute minimal edits instead.
edit.replace(
document.uri,
new vscode.Range(0, 0, document.lineCount, 0),
JSON.stringify(json, null, 2));
return vscode.workspace.applyEdit(edit);
}
// 通知webview
function updateWebview() {
webviewPanel.webview.postMessage({
type: 'update',
text: document.getText(),
});
}
随机一个表情,根据document.uri
和Rang
替换成新的表情,更新后通知webview
更新了。
pawDrawEditor
实现在编辑器中可以对图片涂鸦,通过这个例子可以了解
- 如何实现二进制文件的自定义编辑器
webview
应用- 使用CustomDocuments存储多个自定义编辑器之间共享的信息
- 实现保存、撤消、重做和还原
- 备份自定义编辑器
初始化canvas
后,通知插件准备好,执行openCustomDocument
。
第一次打开给定CustomEditorProvider
编辑器时,会调用openCustomDocument
,然后将文档传递给resolveCustomEditor
,以便向用户显示编辑器,。
插件给webview
发送getFileData
,画布插入初始化图片完成后回传ready
。
webview
收到ready
发送init
vscode.postMessage({ type: 'ready' }); // 初始化canvs后,通知插件准备好,执行openCustomDocument
async openCustomDocument(
uri: vscode.Uri,
openContext: { backupId?: string },
_token: vscode.CancellationToken
): Promise<PawDrawDocument> {
const document: PawDrawDocument = await PawDrawDocument.create(uri, openContext.backupId, {
getFileData: async () => {
const webviewsForDocument = Array.from(this.webviews.get(document.uri));
if (!webviewsForDocument.length) {
throw new Error('Could not find webview to save for');
}
const panel = webviewsForDocument[0];
const response = await this.postMessageWithResponse<number[]>(panel, 'getFileData', {});
return new Uint8Array(response);
}
});
webview
执行初始化事件绑定,setable
是所有按钮实现点击
_initElements(/** @type {HTMLElement} */ parent) {
const colorButtons = /** @type {NodeListOf<HTMLButtonElement>} */ (document.querySelectorAll('.drawing-controls button'));
for (const colorButton of colorButtons) {
colorButton.addEventListener('click', e => {
e.stopPropagation();
colorButtons.forEach(button => button.classList.remove('active'));
colorButton.classList.add('active');
this.drawingColor = colorButton.dataset['color'];
});
}
设置retainContextWhenHidden
后,将webview
一直处于激活状态,存储的数据会被保存下来。
默认情况下,VS Code 只允许每个自定义文档有一个编辑器,如果想要多个需要开启supportsMultipleEditorsPerDocument
。
return vscode.window.registerCustomEditorProvider(
PawDrawEditorProvider.viewType,
new PawDrawEditorProvider(context),
{
// For this demo extension, we enable `retainContextWhenHidden` which keeps the
// webview alive even when it is not visible. You should avoid using this setting
// unless is absolutely required as it does have memory overhead.
webviewOptions: {
retainContextWhenHidden: true,
},
supportsMultipleEditorsPerDocument: false,
});