【问题标题】:Texture not showing on ThreeJS PointsMaterial mapThreeJS PointsMaterial 贴图上未显示纹理
【发布时间】:2022-01-08 15:43:18
【问题描述】:

我正在尝试将此image 加载为PointsMaterialTextureLoader 的地图,但没有成功,它不会引发错误,但由于某种原因纹理不会显示。是我做错了什么还是什么?

代码:

const scene = new THREE.Scene();

const camera = new THREE.PerspectiveCamera(
  75,
  window.innerWidth / window.innerHeight,
  1,
  1000
);

const particleBufferGeometry = new THREE.BufferGeometry();
const positionArray = [];

for (let i = 0; i < 10000; i++) {
  positionArray.push((Math.random() * 2 - 1) * 200);
  positionArray.push((Math.random() * 2 - 1) * 200);
  positionArray.push((Math.random() * 2 - 1) * 200);
}

particleBufferGeometry.setAttribute("position", new THREE.Float32BufferAttribute(positionArray, 3));

const particlePointsMaterial = new THREE.PointsMaterial({
  size: 0.3,
  map: new THREE.TextureLoader().load("./sparkle.png"),
  transparent: true,
});

const particlePoints = new THREE.Points(particleBufferGeometry, particlePointsMaterial);

const renderer = new THREE.WebGLRenderer({
  antialias: true,
  alpha: true,
  canvas: document.getElementById("three")
});

renderer.setClearColor(0x000000, 0);
renderer.setSize(
  window.innerWidth,
  window.innerHeight
);

scene.add(particlePoints);

renderer.render(scene, camera);

【问题讨论】:

  • 看起来你的纹理正在加载,但是你的点太小了以至于你看不到细节。试着让你的分数更大。
  • 无助于他们仍然是隐形的。

标签: javascript html css three.js


【解决方案1】:

另一种选择是使用动画循环:

body{
  overflow: hidden;
  margin: 0;
}
<canvas id="three"></canvas>
<script type="module">
import * as THREE from "https://cdn.skypack.dev/three@0.135.0";

const scene = new THREE.Scene();

const camera = new THREE.PerspectiveCamera(
  75,
  window.innerWidth / window.innerHeight,
  1,
  1000
);


const positionArray = [];
for (let i = 0; i < 10000; i++) {
  positionArray.push(new THREE.Vector3().random().subScalar(0.5).multiplyScalar(400));
}
const particleBufferGeometry = new THREE.BufferGeometry().setFromPoints(positionArray);

const particlePointsMaterial = new THREE.PointsMaterial({
  size: 3,
  map: new THREE.TextureLoader().load("https://threejs.org/examples/textures/sprites/spark1.png"),
  transparent: true,
});

const particlePoints = new THREE.Points(particleBufferGeometry, particlePointsMaterial);

const renderer = new THREE.WebGLRenderer({
  antialias: true,
  alpha: true,
  canvas: document.getElementById("three")
});

renderer.setClearColor(0x000000, 1);
renderer.setSize(
  window.innerWidth,
  window.innerHeight
);

scene.add(particlePoints);

renderer.setAnimationLoop(() => { // animation loop
  renderer.render(scene, camera);
});
</script>

【讨论】:

    【解决方案2】:

    我找到了为什么会这样。我在加载之前将纹理作为贴图传递。

    这是错误的。

    const particlePointsMaterial = new THREE.PointsMaterial({
      size: 0.3,
      map: new THREE.TextureLoader().load("./sparkle.png"),
      transparent: true,
    });
    

    TextureLoaderload() 函数有第二个参数 onLoad,它在纹理加载时执行。所以解决方案是:

    new THREE.TextureLoader().load("./sparkle.png", (texture) => {
      const particlePointsMaterial = new THREE.PointsMaterial({
        transparent: true,
        map: texture
      });
    
      const particlePoints = new THREE.Points(particleBufferGeometry, particlePointsMaterial);
    
      scene.add(particlePoints);
    
      renderer.render(scene, camera);
    });
    

    【讨论】:

    • “这是错误的。” 不是,只是这种情况下作者需要有动画循环。
    猜你喜欢
    • 2019-08-12
    • 2019-03-16
    • 2021-06-11
    • 2014-09-26
    • 1970-01-01
    • 1970-01-01
    • 2017-09-18
    • 1970-01-01
    • 2019-10-21
    相关资源
    最近更新 更多