在 WebGL 中渲染带符号距离场的文本

Rendering Text with Signed Distance Fields in WebGL

核心问题:

我想在 WebGL 中呈现文本。

我不想通过 "overlayed" HTML DOM 元素执行此操作。

我希望在 WebGL 中进行实际的文本渲染。

初始解决方案 1

将每个字符渲染为大量四边形。 这不好,因为我需要渲染很多字符。

初始解决方案 2(实施 + 尝试了这个)。

使用 Canvas,将所有字符渲染为 "atlas/map"。

将 Canvas 转换为 WebGL 纹理。

当我需要渲染角色时,只需将其从纹理中拉出即可。

问题:即使 Canvas 以 80 号字体渲染字体,而 WebGL 以 20 号字体渲染字体,由于各种原因,仍然模糊抗锯齿、插值和其他任何形式 post 处理。

我认为是正确的解决方案。 (不确定,这可能是错误的)。

有符号距离场:https://www.youtube.com/watch?v=CGZRHJvJYIg

对于每个像素,存储到最近边界的距离。

问题

我无法找到符号距离字段的任何 WebGL 实现。

  1. SDF 能否与 WebGL 一起使用,或者 WebGL 是否存在某些限制,导致 SDF 无法正常工作。

  2. 如果是这样,是否有一些图书馆需要:

    • 用于渲染 SDF 的实际着色器 AND
    • 可以采用一种字体并生成渲染所需的 SDF 吗?

编辑:有人可以验证以下是完整的 SDF 着色器吗?

(从 https://www.mapbox.com/blog/text-signed-distance-fields/ 复制)

precision mediump float;

uniform sampler2D u_texture;
uniform vec4 u_color;
uniform float u_buffer;
uniform float u_gamma;

varying vec2 v_texcoord;

void main() {
    float dist = texture2D(u_texture, v_texcoord).r;
    float alpha = smoothstep(u_buffer - u_gamma, u_buffer + u_gamma, dist);
    gl_FragColor = vec4(u_color.rgb, alpha * u_color.a);
}

是的,SDF 非常适合 WebGL 应用程序。比如Mapboxuses吧。 post 实际上包含 SDF 着色器,因为它非常简单。

关于你问题的第二部分:最好事先为字体准备SDF纹理,并且有工具可以做到这一点。 This one,例如