译-在Web上构建专业的设计工具-Figma

[译]在Web上构建专业的设计工具

原文地址 Evan Wallace, CTO at Figma发布于2015年12月7日 (C:译者注释)

我们对未来设计工具的愿景是任何平台的任何人, 都可以轻松地利用设计工具和使用设计内容。这就是我们为什么将Figma,(一个协作式界面设计工具)构建为基于浏览器的云服务。当我们着手开发Figma时,我们知道它将是个挑战。要真正取得成功,它必须提供专业人士愿意接受的高保真编辑体验以及在任何平台如出一辙的操作体验。

要实现这一点真的很难。我们基本上最后是在浏览器上构建另一个浏览器。

之所以很难,是因为Web并非被设计为通用计算平台。它最初是作为一种主要用于文档以及基于文档的应用程序开发的技术合集。Web这些技术通常使用针对一次性生效的特定API形式,而不是提供可用于实现各种事情的通用原语(C:可以理解为元素的原始数据)比如:

Web上缺少通用原语的情况正在开始改变,现在有诸如WebGL和asm.js之类的技术可以使开发人员跳过浏览器并直接与硬件对话。正是这种进步最终使基于Web的高性能图形应用程序变得可实现。开发人员不再需要等待将其添加到Web的新标准,他们可以自己构建这些功能!

Emscripten

我们的编辑器是用C ++编写的,并使用emscripten交叉编译器交叉编译为JavaScript 。emscripten编译器针对asm.js 一个JavaScript子集,该子集提供了一种使JavaScript的JIT产生可预测的简洁机器代码的方法,并且在所有现代浏览器中均得到广泛支持。这具有以下好处:

  • 我们能完全控制内存布局,并且可以在适当时使用紧凑的32-bit float或64-bit double,而不是JavaScript的64-bit double。这对于像我们这样使用大量数据的应用程序非常重要。
  • 生成的代码完全由分配控制,这可以避免GC带来的暂停,从而更轻松地达到60fps。所有C ++对象只是预分配类型数组中的保留范围,因此从不涉及JavaScript GC。
  • 使用LLVM的高级优化器对生成的代码进行了预优化。这与C ++模板专业化相结合,可以生成非常有效的代码,该代码的性能本机性能2或更高
  • 确保所有asm.js代码都没有负优化点,因此JIT可以提前进行编译并提供可预测的性能。常规的JavaScript代码改为依赖JIT启发式,有时在同一代码的后续运行之间,性能有时会大相径庭。

这并不是说emscripten是完美的。与任何新技术一样,开发之路上也有很多坎。对我们来说,一个大问题是某些浏览器配置无法为包含整个脚本存储空间的巨大类型数组分配大范围的连续地址空间。最坏的情况是Windows上的32位Chrome,有时甚至无法分配256mb类型的数组,因为ASLR正在分割地址空间。此后已解决。(C:当时Chrome限制64位为1.4GB,32位为512MB)

一个有用的技巧是使用句柄为大量资源(如图像和几何缓冲区)使用堆外数据。我们有一个称为IndirectBuffer的内部API(我们在这里开放源代码),该API引用一个外部类型的数组并将其提供给C ++。将大型分配移出主堆可减少长时间运行的会话的内存碎片问题,使我们能够在32位浏览器中使用更多有限的地址空间,并允许我们突破64位中31位类型化数组大小限制位浏览器。

渲染

我们已经实现了自己的渲染引擎,以确保内容能够在平台之间快速,一致地渲染。浏览器具有惊人的图形实现,我们最初尝试使用它们,而不是构建新的渲染引擎。如果没有低级API来访问浏览器的渲染树,则可用的选项是HTML,SVG或2D画布。这些选择都不令人满意,原因有很多:

  • HTML和SVG包含很多负担,并且由于DOM访问,通常比2D canvas API要慢得多。这些通常是针对滚动而不是缩放进行优化的,并且每次缩放比例更改后,几何形状通常都会重新细分(C:Tessellation将很多高阶的图元变成很多小图元的过程)。
  • 无法保证GPU的加速,并且许多东西仍在CPU上渲染,在某些情况下这可能会非常慢。
  • 在HTML和SVG中,对遮罩,模糊和混合模式的支持在浏览器之间千差万别,在高DPI显示器上通常不抗锯齿或分辨率太低。
  • 2D canvas API是立即模式API,而不是保留模式API,因此必须将每帧的所有几何图形重新上传到显卡。这是不必要的浪费,并且可能成为瓶颈。
  • 文本布局在浏览器之间不一致的,甚至在不同平台上同一浏览器之间也是不一致的。
  • 我们希望能够添加任何这些渲染API均不支持的功能,例如角度渐变

我们并没有试着使用HTML,SVG或者2D画布解决上面问题,而是使用WebGL从头开始实现了所有功能。我们的渲染器是高度优化的基于图块的引擎,支持遮罩,模糊,抖动渐变,混合模式,嵌套层不透明度等。所有渲染均在GPU上完成,并且完全抗锯齿。在内部,我们的代码看起来很像浏览器内部的浏览器;我们有自己的DOM,我们的合成器,我们自己的文本布局引擎,并且我们正在考虑添加一个渲染树,就像一个浏览器用来渲染HTML一样。

浏览器

Web平台的功能一直在追赶原生平台,不幸的是目前仍然存在一些差距。尽管我们没有足够的资源来填补一些较大的空白,但我仍然会尽力解决可能的问题。

在开始使用Figma之前,高DPI自定义光标在Web上确实被broken了。我必须手动修复ChromeFirefoxWebKit,因为它们都以不同的方式broken。仍然没有统一的方法(Firefox使用SVG,Chrome浏览器和WebKit使用-webkit-image-set以及IE使用古老的.cur格式),但至少现在有可能。

我还修复了一些严重的 性能可用性错误,以使我们的产品更好。有时,Web可能令人沮丧,但是浏览器并不是黑匣子(嗯,除了那个浏览器)。通常,解决烦人的Web问题需要泡在浏览器代码一整个下午,或者在一个patch上折腾一天,然后需要等待几个月才发布。

Web平台还有更多的潜力可以使Figma变得更好:

  • 我们最大的难点是缺乏进入字形轮廓和字距调整表,其中有目前没有任何方法 在得到的。最主要的问题之一就是字体指纹识别(C:字体指纹概念),但是那场战斗已经失败了。我们希望可以像其他隐私敏感型API一样,在用户权限提示后公开对字体数据的访问。Chrome浏览器提出了一个正在开发中的修复程序提案(它们确实很有帮助!),但是其他浏览器没有其他的可预见性了。
  • 我们很想增加对常见剪贴板格式(.ai,.pdf等)的支持,但是Web上却没有办法做到这一点。规范中唯一的格式是text / plain和text / html(我们的Figma剪贴板“格式”是text / html,二进制数据编码为HTML注释)。
  • 我们面临的另一个问题是缺乏对OS X触控板捏合手势的支持。Chrome浏览器添加了一个鲜为人知的技巧,其中捏手势使用ctrlKey向下发送wheel事件,并调用preventDefault()允许页面对其进行处理。这真是太神奇了,它使Figma的缩放和平移变得自然而轻松。我试图将其添加到Firefox中,但该尝试目前仍停留。在Safari中进行捏合会导致缩放行为,这确实使用户感到困惑,并且无法禁用

总结

性能和质量是我们最重要的功能。它们与正常功能有所不同,因为您只会在不存在它们时才注意到它们,但它们却与众不同。

我很高兴终于向世界展示Figma。该产品尚未向公众开放,但您可以注册我们的候补名单并尽快试用。让我们知道您的想法!