【问题标题】:Generate particles for spiral galaxy in THREE.js在 THREE.js 中为螺旋星系生成粒子
【发布时间】:2019-07-27 06:55:27
【问题描述】:

我想在 THEE.js 中使用 THREE.Points 创建一个简单的螺旋星系。
我不知道如何生成螺旋臂。有没有(不太难)的方法来做到这一点?

我在这里创建了这个fiddle。有一个扁平的球体,但没有旋臂。

const scene = new THREE.Scene()
const camera = new THREE.PerspectiveCamera(50, window.innerWidth / window.innerHeight)
camera.position.z = 1500
scene.add(camera)
const renderer = new THREE.WebGLRenderer({ clearColor: 0x000000 })
renderer.setSize(window.innerWidth, window.innerHeight)
document.body.appendChild(renderer.domElement)

// Random function with normal dustribution.
const normalRandom = (mean, std) => {
    let n = 0
    
    for (let i = 1; i <= 12; i++) {
      n += Math.random()
    }

    return (n - 6) * std + mean
}

const geometry = new THREE.Geometry()
const galaxySize = 1000

// Generate particles for spiral galaxy:
for (let i = 0; i < 10000; i++) {
  var theta = THREE.Math.randFloatSpread(360) 
  var phi = THREE.Math.randFloatSpread(360)
  const distance = THREE.Math.randFloatSpread(galaxySize)

  // Here I need to generate spiral arms instead of a sphere.
  geometry.vertices.push(new THREE.Vector3(
  	 distance * Math.sin(theta) * Math.cos(phi),
     distance * Math.sin(theta) * Math.sin(phi),
     distance * Math.cos(theta) / 10
  ))
}

const spiralGalaxy = new THREE.Points(geometry, new THREE.PointsMaterial({ color: 0xffffff }))
scene.add(spiralGalaxy)

function render() {
    requestAnimationFrame(render)
    renderer.render(scene, camera)
    spiralGalaxy.rotation.x += 0.01;
    spiralGalaxy.rotation.y += 0.01;
}

render()
&lt;script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/102/three.min.js"&gt;&lt;/script&gt;

【问题讨论】:

    标签: javascript math random three.js spiral


    【解决方案1】:

    看起来您自己已经用极坐标系完成了很多繁重的工作。但是请记住,角度是弧度,而不是度数,所以不要使用360,而应该使用PI * 2。现在您所要做的就是同时增加 distancetheta 以创建螺旋,而 phi 保持接近 0 以创建银河系的黄道平面。

    • distance 将从 0 增长到 galaxySize
    • theta 将从 0 增长到 Math.PI(或 PI * 2,如果你想要更紧密的螺旋)
    • phi 接近于 0
    // Temp variables to assign new values inside loop
    var norm, theta, phi, thetaVar, distance;
    
    // Generate particles for spiral galaxy:
    for (let i = 0; i < 1000; i++) {
        // Norm increments from 0 to 1
        norm = i / 1000;
    
        // Random variation to theta [-0.5, 0.5]
        thetaVar = THREE.Math.randFloatSpread(0.5);
    
        // Theta grows from 0 to Math.PI (+ random variation)
        theta = norm * Math.PI + thetaVar;
    
        // Phi stays close to 0 to create galaxy ecliptic plane
        phi = THREE.Math.randFloatSpread(0.1);
    
        // Distance grows from 0 to galaxySize
        distance = norm * galaxySize;
    
        // Here I need generate spiral arms instead of sphere.
        geometry.vertices.push(new THREE.Vector3(
            distance * Math.sin(theta) * Math.cos(phi),
            distance * Math.sin(theta) * Math.sin(phi),
            distance * Math.cos(theta)
        ));
    }
    

    您可以为每只手臂创建一个循环。请注意,我没有像您在示例中那样在最后除以 10,而是将 phi 的范围限制为 [-0.1, 0.1]。你可以看到它在行动in this fiddle

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-02-09
      • 2016-09-27
      • 1970-01-01
      • 2012-06-28
      • 2013-07-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多