You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Three.js单纹理立方体侧/上下表面纹理差异的原因及解决方法

为什么立方体六个面的纹理表现不一致?

这个问题我之前也碰到过,核心原因是Three.js默认的BoxGeometry为每个面生成的UV坐标是基于面的自身朝向设计的,而非统一的映射逻辑:

  • 立方体的顶面/底面,UV坐标对应立方体的X-Z轴平面;
  • 四个侧面的UV坐标则对应X-Y轴平面;
    当你设置repeat.set(10,10)和offset.set(0.5,0.5)后,纹理的重复方向、偏移位置会因为每个面的UV轴对应关系不同,呈现出视觉上的差异。简单来说,就是同一个纹理参数,在不同朝向的面上,被“拉伸”或“偏移”的方向不一样。

怎么让六个面的纹理效果一致?

这里有两种实用的解决思路:

方法1:手动修正BoxGeometry的UV坐标

直接修改默认立方体的UV数据,让六个面的UV映射逻辑统一。你可以遍历几何体的UV数组,把每个面的UV都重置为标准的0-1范围,确保方向一致:

// 假设你已经创建了BoxGeometry
const cubeGeometry = new THREE.BoxGeometry(1, 1, 1);

// 遍历每个面的UV数据(BoxGeometry的每个面是四边形,对应4个UV顶点)
cubeGeometry.faceVertexUvs[0].forEach((uvs) => {
  // 统一设置每个面的UV为:左下角(0,0)、右下角(1,0)、右上角(1,1)、左上角(0,1)
  uvs[0].set(0, 0);
  uvs[1].set(1, 0);
  uvs[2].set(1, 1);
  uvs[3].set(0, 1);
});

// 告诉Three.js更新UV数据
cubeGeometry.uvsNeedUpdate = true;

// 再把修改后的几何体应用到网格上
const cubeMesh = new THREE.Mesh(cubeGeometry, corkMaterial);

方法2:用PlaneGeometry拼接立方体

这种方法更直观——用六个独立的PlaneGeometry分别作为立方体的六个面,每个平面的UV都是默认的统一逻辑,这样纹理参数在所有面上的表现自然一致:

const planeGeo = new THREE.PlaneGeometry(1, 1);
const corkMaterial = new THREE.MeshBasicMaterial({
  map: corkTexture,
  side: THREE.DoubleSide // 因为平面默认只渲染正面,需要开启双面渲染
});

// 创建六个面并定位、旋转到对应位置
const frontFace = new THREE.Mesh(planeGeo, corkMaterial);
frontFace.position.z = 0.5;

const backFace = new THREE.Mesh(planeGeo, corkMaterial);
backFace.position.z = -0.5;
backFace.rotation.y = Math.PI;

const leftFace = new THREE.Mesh(planeGeo, corkMaterial);
leftFace.position.x = -0.5;
leftFace.rotation.y = -Math.PI / 2;

const rightFace = new THREE.Mesh(planeGeo, corkMaterial);
rightFace.position.x = 0.5;
rightFace.rotation.y = Math.PI / 2;

const topFace = new THREE.Mesh(planeGeo, corkMaterial);
topFace.position.y = 0.5;
topFace.rotation.x = Math.PI / 2;

const bottomFace = new THREE.Mesh(planeGeo, corkMaterial);
bottomFace.position.y = -0.5;
bottomFace.rotation.x = -Math.PI / 2;

// 把六个面放到一个Group里,当作立方体使用
const cubeGroup = new THREE.Group();
cubeGroup.add(frontFace, backFace, leftFace, rightFace, topFace, bottomFace);

这两种方法都能解决你的问题,方法1适合不想改动原有几何体结构的场景,方法2更直观,容易理解和调试。

内容的提问来源于stack exchange,提问作者Nat Nite

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 12:30:21