使用 vscode-page 简化 vscode 插件的 Webview 开发

栏目: IT技术 · 发布时间: 4年前

内容简介:vscode 是时下最流行的开发工具之一,高逼格的 UI 和各种酷酷的插件,不仅提高了使用者的开发效率,还让他们的形象大为改善,不再是人们眼中的“死肥宅”。使用 vscode 很潮,但更潮的就是为它开发插件。作为今年的兴趣点,我也投身于 vscode 插件开发者大军之中。vscode 的插件开发并不需要太高深的技术,就是普通的开发技术的组合。因为面向的用户就是开发者,所以一般情况下主要是对开发者工作现场(如编辑文本框)的增强,并搭配完成任务的各种命令,很少需要复杂的 UI 。但凡事总有例外,当需要 GUI

vscode 是时下最流行的开发 工具 之一,高逼格的 UI 和各种酷酷的插件,不仅提高了使用者的开发效率,还让他们的形象大为改善,不再是人们眼中的“死肥宅”。使用 vscode 很潮,但更潮的就是为它开发插件。作为今年的兴趣点,我也投身于 vscode 插件开发者大军之中。

vscode 的插件开发并不需要太高深的技术,就是普通的开发技术的组合。因为面向的用户就是开发者,所以一般情况下主要是对开发者工作现场(如编辑文本框)的增强,并搭配完成任务的各种命令,很少需要复杂的 UI 。但凡事总有例外,当需要 GUI 加持的时候,就轮到 Webview 出场了。

Webview 开发本身也很简单,就两个任务:

  • 负责 GUI 部分的 HTML 页面
  • 充当 vscode 和 HTML 页面之间桥梁的 vscode.WebviewPanel

可是,就算是简单的任务,做多了你也会发现还是存在一些值得优化的空间,避免在每个新页面开发都重复以下的事情:

  • 设置 html 的 resource root 。
  • createOrShow 逻辑:即有则显示,无则创建。
  • 隐藏时保存之前页面的状态。
  • html 与 WebviewPanel 之间交互涉及的 boilerplate code:开发者只需考虑两者之间的消息格式和处理逻辑就好了。

这样做有助于设定一个简单的开发模型,处理好消息、处理和展示三者的关系,不必每次开发新页面时“copy - paste - change”,而是采用一致的模型并促进组内协作。

于是, vscode-page 应运而生。

设计原理

简单地讲,vscode-page 是一个针对 vscode Webview 开发的轻量级页面微框架,抽象了 html 与 WebviewPanel 之间的通信交互,使得开发者只需要关心具体业务逻辑。其整个架构图如下:

使用 vscode-page 简化 vscode 插件的 Webview 开发

看到这张图,熟悉 Web 开发框架的同学应该已经秒懂整个设计:

  • vscode-page 充当消息 dispatcher 。
  • MessageMapping 定义消息、处理器和页面模板(采用流行的 handlebars.js )这三者的关系。
  • Response 的 html 片段用于更新指定 element 的 innerHTML。

更详细的说明请参见 README

这里没有采用花哨的 Angular 、React 和 Vue ,主要就是为了简单和轻量。并且,在 vscode Webview 这种受限的环境下,使用传统的 jQuery + BootStrap + Handlebars 就是最佳选择,而且一般情况下插件的 GUI 也不会太复杂,前面的几个工具已经足以应对。

使用指南

vscode-page 的使用很简单:

定义页面和 WebviewPanel 之间的消息交互。

在这里定义消息请求和响应内容,其中:

  • 请求:command + parameters
  • 响应:command + ( contents 或 result )

编写页面

这里有几点注意,在每个页面前面添加以下两行:

<base href="{{base}}" />
<script type="text/javascript">
  "{{init}}"
</script>
  • 前者用于初始化资源根目录,这样后面的资源引用可以直接引用相对路径即可。
  • 后者会注入一个 EventListerner 函数定义。

一般情况下,你直接调用:initEventListener() 来完成初始化就行了,它实现了:

  • 若消息的 command 为 Response 结尾且有 contents 属性,则为消息中指定的 element 替换 innerHTML 。
  • 对于不满足上面条件的消息,则丢弃。

假如你想处理,则可以换一种初始化方式,传入处理函数:

initEventListener(message => {...});

此时,你可以从 message.result 拿到结果。

定义 MessageMapping 。

这个过程没有什么复杂的,就是定义三个属性:

  • command,与请求中的 command 对应
  • handler,处理逻辑
  • templates,请求完毕后要显示的模板定义

详细例子,参见:https://github.com/DTeam-Top/vscode-page/blob/master/example/src/home.ts 。

值得一提的是,MessageMapping 还支持 forward 模式,即请求处理之后,直接转到另一个 command ,以它的处理结果为最终处理结果,类似 Web 开发中的 forward 模式。

{
    command: "submitRepositories",
    handler: async parameters => {
      ……
    },
    forward: "ready"
  },

上面的 ready 就是另一个 MessageMapping 定义的 command 名。

创建 WebviewPannel

这个最简单,就一句话:

createOrShowPage(
  'name',
  'ext.home',
  'Sample Page',
  'pages',
  'home.html',
  context,
  messageMappings
);

定义了 title、根目录和需要加载的页面。

关于使用的完整例子请结合 README样例工程 来看,后者是我们即将试水发布的一个 vscode 插件,用于帮助开发者或企业搭建自己的私有插件仓库。因为总有些时候会需要私有插件仓库,:)

关于 vscode 插件开发

资源根目录

虽然插件开发指南已经很详尽,但初学者总是会遗漏一些细节,在开发时才发现文档中早有提及。这里尤其值得一提的就是 Webview 的资源加载问题,因为它浪费了我一些时间。

最简单的方案,当然就是直接使用 vscode-page 插件就行了,它已经替你 cover 了一些细节,你只需照常使用就行,你可以查看 这个页面

假如不使用 vscode-page ,我也没打算藏着掖着,只需要复制下面的几行代码即可:

const rootString = path.join(context.extensionPath, base);
const localResourceRoots = vscode.Uri.file(path.join(rootString, '/')).with(
  {
    scheme: 'vscode-resource',
  }
);
panel = vscode.window.createWebviewPanel(
  viewType,
  title,
  vscode.ViewColumn.One,
  {
    enableScripts: true,
    retainContextWhenHidden: true,
    localResourceRoots: [localResourceRoots],
  }
);
const pagePath = path.join(rootString, page);
panel.webview.html = fs
  .readFileSync(pagePath, 'utf-8')
  .replace('{{base}}', localResourceRoots.toString());

当然,你得记得在页面中在添加一行:

<base href="{{base}}" />

从代码中我相信你已经看出来一些端倪:scheme: ‘vscode-resource’,它并非一般 Web 开发中的 file: 。同时也要记得设置 localResourceRoots 属性。在开发 vscode-page 时发现使用 vscode-page 的插件总是没法加载自己的资源,报:ERR_ACCESS_DENIED ,后来发现是因为没有设置这个属性。

调试工具

开发 Webview 肯定需要类似 Web Dev Tools 那样的浏览器查看工具,vscode 也有。输入:Open Webview Developer Tools 就能激活。

工程相关

因为本质上 vscode 插件开发是前端工程的范畴,并且我们团队主要采用 TypeScript ,因此用到的插件和规范如下:

代码风格:

风格可商量余地:

  • “strict”: true + “no-any”: false,允许

相关插件:

  • ESLint
  • Bracket Pair Colorizer 2
  • Prettier
  • markdownlint
  • indent-rainbow
  • Path Intellisense
  • Peacock

写在最后

作为插件发布的前奏,vscode-page 已经发布(0.0.1),工程路径:https://github.com/DTeam-Top/vscode-page ,欢迎加星或使用,:smile:。


以上所述就是小编给大家介绍的《使用 vscode-page 简化 vscode 插件的 Webview 开发》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

jQuery基础教程(第3版)

jQuery基础教程(第3版)

[美] Jonathan Chaffer、[美] Karl Swedberg / 李松峰 / 人民邮电出版社 / 2012-4 / 59.00元

内容简介: jQuery是功能强大却又简洁明快的轻量级JavaScript库,出自名家之手。在DOM操作、事件处理、Ajax特性以及动画特效等方面的出色表现,使它迅速从众多JavaScript库中脱颖而出,成为一颗闪亮的明星。 本书是《jQuery基础教程(第2版)》的升级版,涵盖了jQuery 1.6及1.7的各种新特性,内容源自著名jQuery资源网站LearningjQuery.......一起来看看 《jQuery基础教程(第3版)》 这本书的介绍吧!

CSS 压缩/解压工具
CSS 压缩/解压工具

在线压缩/解压 CSS 代码

html转js在线工具
html转js在线工具

html转js在线工具

HEX CMYK 转换工具
HEX CMYK 转换工具

HEX CMYK 互转工具