three.js - 如何用三个js将多个纹理剪辑为多边形

标签 three.js webgl rendering clipping

我有一堆飞机,每个飞机在网格中都有自己的纹理。目前,我将它们渲染为单独的平面,每个平面都有自己的纹理,尽管我可以使用具有多个面的单个平面。

textures

每种颜色都是一种纹理。

我有一个任意形状的多边形网格,与这些平面平行:

polygon

该形状可以完全包含在一个平面或更大的平面内。

我想用平面的重叠纹理来对多边形进行纹理处理:

overlap

如何在三个 js 中完成纹理的裁剪?

我也对任何其他 WebGL 解决方案持开放态度。

我的一些想法:

  1. 将多边形分割为与重叠平面相对应的面。然后使用 UV 坐标对这些面进行纹理化。我知道我可以让它发挥作用,但这似乎是一个太复杂的解决方案。
  2. 将多个纹理应用到多边形并使用 UV 坐标来分布它们。 -- 我不确定这是否可以在不分割的情况下实现?

还有其他想法吗?这可以通过混合模式来完成吗?

最佳答案

一些想法:


将小纹理烘焙到texture atlas中因此,您可以在单个平面上使用一组 uv 进行图 block (如果需要多于一张图集,您可以在一个 WebGL 程序中使用多个纹理采样器)。

计算与形状顶点的世界坐标相对应的平面的 uv,并使用这些 uv 采样纹理图集。为此,您可能需要传递给形状 Material 平面的模型矩阵(或者如果您知道其大小,则只需传递比例/偏移量)方向,或者如果平面固定则什么也不做)。

请记住,您不需要在小图 block 上使用高分辨率纹理。另外, map 集可以通过将图 block 渲染为纹理来替换(从顶部使用正交投影) 或通过在单独的采样器中传递纹理。关于最后一种情况:要确定要传递哪些纹理,您可以测试形状与 map 图 block 的边界框。


使用简单 Material 将形状渲染为纹理,并在绘制平面的主 channel 中使用该纹理作为 mask 。

详细说明:

将要遮盖的形状放在单独的容器中,然后 render it to a fixed size texture使用非常简单的 Material (到处写白色)和普通相机。在渲染过程之后,您应该会看到一个带有黑色和白色形状的纹理,就像您在屏幕上看到的那样(但缩放为方形纹理)。

之后渲染场景的其余部分并传递给瓷砖 Material 蒙版纹理。在片段着色器中,使用 screenPos 作为 uv 采样蒙版纹理,并且仅在获得白色时才绘制片段(否则丢弃)。可能不是最好的主意(丢弃的代价很高)。


深度掩模方法的更好版本:在掩模传递中禁用颜色写入(renderer.context.colorMask(false, false, false, false);)。之后,您应该拥有深度缓冲区中的形状。然后将颜色 mask 重置为全部 true,设置 renderer.autoClearDepth = false,设置 tileMaterial.depthFunc = THREE.GreaterDepth ( more about depthFunc ) 。然后渲染你的瓷砖。这应该可以完成工作。

也可以通过将掩码深度写入 depthTexture 来完成并在主 channel 中将其用作纹理。


使用模板缓冲区进行 mask :我还没有尝试过,但它应该适合您的情况。示例:1 , 2 。想法类似于上面描述的屏​​蔽。

关于three.js - 如何用三个js将多个纹理剪辑为多边形,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39860677/

相关文章:

javascript - 如何将 Three.js 中的网格仅在 X 和 Y 上居中

webgl - Three.js 行在 Canvas 渲染器中不起作用,但在 WebGL 渲染器中起作用

javascript - 我从 blender 导出到 three.js 的模型无法正确呈现

c++ - SDL2 主游戏循环

java - LWJGL 可以与 Graphics2D 一起使用吗?

javascript - 你如何检测 three.js 中粒子系统中的粒子悬停?

android - 移动智能手机查看球形全景的不同部分?

three.js - 如何在 Three.js 中自定义指针锁定控件?

opengl-es - WebGL - 如何传递无符号字节顶点属性颜色值?

macos - Ubuntu/OSX 上 PhantomJS 的字体渲染差异