如何在 three.js 中制作带网格的立方体

how can i make a cube with a grid in three.js

Cube

我想做一些完全像这样的东西,但我可以用一个变量改变网格中立方体的数量。(我不知道如何开始)

您需要将立方体添加到 Group,然后将 Group 添加到场景,然后将 Group

居中

这是执行此操作的一种方法:

const grid = new THREE.Group();

const cubeSize = 0.25;
const rows = 4;
const cols = 4;
const gap = 0.01;

for (let row = 0; row < rows; row++) {
    for (let col = 0; col < cols; col++) {
        for (let z = 0; z < rows; z++) {
            const cube = createCube(cubeSize);
            const pos = ((cubeSize / 2) * rows) / 2 + gap;
            const x = pos * row;
            const y = pos * col;
            cube.position.set(x, y, pos * z);
            grid.add(cube);
        }
    }
}

scene.add(grid);

请注意,添加的多维数据集越多,扩展效果就越差。由于对象总数将是(rows + cols) ^ 3,这将产生大量对象。鉴于此,您可以使用 InstancedMesh 网格,我在下面展示了它的演示。

演示:

* {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
}

canvas {
  display: block;
}
<script type="module">
  import * as THREE from "https://cdn.jsdelivr.net/npm/three@0.121.1/build/three.module.js";
  import { OrbitControls } from "https://cdn.jsdelivr.net/npm/three@0.121.1/examples/jsm/controls/OrbitControls.js";

  const renderer = new THREE.WebGLRenderer();
  renderer.setSize(window.innerWidth, window.innerHeight);
  document.body.appendChild(renderer.domElement);

  const scene = new THREE.Scene();
  const camera = new THREE.PerspectiveCamera(
    75,
    window.innerWidth / window.innerHeight,
    0.1,
    1000
  );
  const controls = new OrbitControls(camera, renderer.domElement);

  const grid = new THREE.Group();

  const cubeSize = 0.25;
  const size = 20;
  const gap = 0.01;

  const geometry = new THREE.BoxBufferGeometry(
    cubeSize,
    cubeSize,
    cubeSize
  );
  const material = new THREE.MeshNormalMaterial();
  const cubes = new THREE.InstancedMesh(
    geometry,
    material,
    Math.pow(size, 3)
  );
  cubes.instanceMatrix.setUsage(THREE.DynamicDrawUsage);

  grid.add(cubes);
  scene.add(grid);

  const cube = new THREE.Object3D();
  const center = (size + gap * (size - 1)) * -0.5;

  grid.position.set(center, center, center);

  camera.position.z = size * 1.5;

  (function animate() {
    requestAnimationFrame(animate);

    let i = 0;
    for (let x = 0; x < size; x++) {
      for (let y = 0; y < size; y++) {
        for (let z = 0; z < size; z++) {
          cube.position.set(x, y, z);
          cube.updateMatrix();
          cubes.setMatrixAt(i, cube.matrix);
          i++;
        }
      }
    }

    cubes.instanceMatrix.needsUpdate = true;

    controls.update();
    renderer.render(scene, camera);
  })();
</script>