javascript - 如何将两种材质添加到已经在画布上渲染的网格中
问题描述
我正在尝试将颜色和图像添加到已经在画布上的threejs Mesh。据我所知,如果我使用相同的材料添加颜色和地图,它们将混合并且没有办法阻止它。因此,如果我有一个白色图像和一个黄色颜色,颜色会将图像染成黄色:
let material = new THREE.MeshLambertMaterial({
map: canvasTexture,
color: 0xCECECE
});
为了解决这个问题,我尝试向网格中添加两种材质。一个有颜色,一个有图像
let material0 = new THREE.MeshLambertMaterial({
color: 0xCECECE
});
let material1 = new THREE.MeshLambertMaterial({
map: canvasTexture
});
var materials = [material0, material1];
mesh.material = materials;
当我尝试将网格材质设置为材质数组时,它会变为空白,就好像它不接受该数组作为参数一样。尽管threejs文档说它接受一系列材料 https://threejs.org/docs/#api/en/objects/Mesh.material
我看到的另一个问题可能会发生,如果我让它使用只有图像的材料将默认为白色,因此不会显示下面材料的颜色。
那么如何在不混合的情况下设置网格材质的图像和颜色。添加两种材料对我来说似乎过于复杂,从长远来看可能更难管理?
更新 所以我的问题最终是我使用的纹理,它是画布纹理。我需要将画布纹理中使用的画布的填充样式设置为不透明。就像是:
ctx.fillStyle = "rgba(255, 255, 255, 0)";
然后我可以继续在一个数组中添加多个材质到网格中。使用画布纹理作为贴图的材质也必须设置为透明。我还必须将 map.minfilter 设置为 THREE.LinearFilter。不知道为什么,但至少它现在可以工作了:)
let material0 = new THREE.MeshLambertMaterial({
color: 0xf2f2f2
});
let material1 = new THREE.MeshLambertMaterial({
map: canvasTexture,
transparent: true
});
material1.map.minFilter = THREE.LinearFilter;
var materials = [material1, material0];
mesh.geometry.clearGroups();
mesh.geometry.addGroup( 0, 48, 0 );
mesh.geometry.addGroup( 0, 48, 1 );
mesh.material = materials;
希望这可以帮助某人。
解决方案
当我尝试将网格材质设置为材质数组时,它会变为空白,就好像它不接受该数组作为参数一样。
这可能会发生,因为您的几何没有定义任何组数据。这是使用多种材料的要求。
所以如果我有一个白色的图像和一个黄色的颜色,颜色会将图像染成黄色
这是预期的行为。材质的颜色与从漫反射纹理中采样的颜色值相乘。TBH,不同的默认行为没有意义。
那么如何在不混合的情况下设置网格材质的图像和颜色。
如果要使用不同的材质渲染网格的不同部分,请为相应的几何体定义组数据并使用多种材质。否则考虑复制网格并将一种材料分配给原始材料,将第二种材料分配给副本。通过将副本添加到原件 ( mesh.add( copy )
),您可以将两者保存在同一位置。
推荐阅读
- rabbitmq - 如何使用 MassTransit 和 RabbitMQ 设置消费者优先级
- javascript - 为什么使用 mongoose 删除 mongodb 集合中的数据后集合模式的长度没有改变?
- haskell - Haskell Attoparsec 无限循环
- toolkit - 使用 Holotoolkit 滑块的值
- android - Android ImageView程序,如何根据随机函数设置imageview
- c - 我的最终功能不会返回
- xcode - 没有故事板的编码
- excel - 代码似乎永远运行并且错误:未设置块变量(VBA)
- jersey-2.0 - 带有 Guice 的 Jersey 2.27 - 没有 HK2-guice 桥是否支持
- android - Android Place.getLocale() 返回 null