Three.js如何在AR应用程序上触摸按钮时更改一个对象的两种材质
Posted
技术标签:
【中文标题】Three.js如何在AR应用程序上触摸按钮时更改一个对象的两种材质【英文标题】:Three.js How to change two materials of the one object when touching a button on a AR application 【发布时间】:2021-07-18 01:34:27 【问题描述】:我最近第一次接触 Three.js,我需要一些帮助来做一些测试。
目前我正在尝试创建一个 AR 应用程序,其中使用手机的摄像头将对象插入到真实环境中。最初该对象以蓝色显示在屏幕上,但是在顶部我想放置三个具有三种不同颜色的按钮,例如蓝色、红色和绿色,当触摸其中一个按钮时,对象只是改变它的颜色。
我在 Blender 上创建了对象及其材质。对象的一个面具有带有 UV 纹理的材质,而对象的其余部分具有第二种材质,没有纹理,只是具有初始节点的材质(在 Blender 循环中创建)。所以我创建了 6 种材质,3 种用于纹理,每种一种,3 种用于颜色,也每种一种。在 Blender 上,我将此对象导出为带有材质和纹理的 .glb。
现在我在 Three.js 上导入这个对象,我已经知道如何将这个对象添加到场景中并渲染它,以便它出现在手机屏幕上。包括对象附带的第一个材质正常工作(来自 .glb),我没有在 Three.js 中创建任何关于材质的内容,到目前为止,场景中显示的所有内容都来自我在搅拌机中导出的 .glb并刚刚加载到三个.js。
现在我需要创建应用程序的第二部分,即:当我触摸一种颜色的按钮时,对象必须改变颜色,以及“纹理”。正是在这里,我需要帮助。
我该怎么做? 我需要三个不同的对象吗?还是只有一个对象包含所有 6 种材料?如何在three.js 上实现此功能?我需要有关 Blender 和 Three.js 的帮助。
有人可以指点一下吗?或视频链接或有关此主题的精彩对话。
提前致谢。
【问题讨论】:
【参考方案1】:基本上您需要做的是更改 .glb 文件中相关网格的材质。
当您使用 GLTFLoader 加载 .glb 文件时,您会给它一个“onLoad”函数参数,您可以在其中首先访问文件的内容(文件本身就是它自己的迷你场景) - 这就是您可以遍历场景,找到网格并将其保存为变量,以便以后对其进行操作。
现在,假设文件中有多个网格,你怎么知道哪一个是正确的?最好的方法是通过名称。由于您从 Blender 创建了对象,因此您可以为每个网格指定一个唯一的名称,以便以后在 three.js 中识别。
因此,现在您可以在 onLoad 函数中插入一些逻辑来确认正确的网格是您作为变量存储的网格,请考虑以下代码:
let meshFromGLTF;
const meshName = "MESH_0" // assuming this is the name you gave it on blender
...
loader = new GLTFLoader();
loader.load( "path/to/gltf", ( gltf ) =>
const scene = gltf.scene;
scene.traverse( ( child ) =>
if ( child.isMesh && child.name === meshName ) // to confirm it is a mesh
meshFromGLTF = child;
// this may also be a good point to store the original material as a variable
)
现在,由于您将网格存储为变量,因此可以很容易地使用按钮更改它的材质和纹理。只需在单击按钮时提供一个 onClick 函数,在该函数中您可以执行以下操作:
const texture = textureLoader.load( 'path/to/texture.png' );
const materialBlue = new MeshBasicMaterial ( map: texture, color: 'blue' );
function onClickBlue ()
meshFromGLTF.material = materialBlue;
在为网格创建材质方面,这是一个相当广泛的话题,您可以查看documentation 并查看您可能需要什么样的材质,您在材质本身上应用的纹理参数包括单词'地图'。
我创建了一个小示例 here 来实现这种方法。
【讨论】:
以上是关于Three.js如何在AR应用程序上触摸按钮时更改一个对象的两种材质的主要内容,如果未能解决你的问题,请参考以下文章
我想在 AR 渲染对象上运行浏览器。 three.js 能做到吗? [关闭]