three.js:thetaLength为负的圆柱体

时间:2018-07-31 05:00:44

标签: three.js

我想使用thetaLength设置为-6.3的“倒置”圆柱体,以便将内部分类为FrontSide,以便该圆柱体可以进入另一个普通圆柱体,顶部和底部带有环,以形成一个管。

我想做所有这些事情的原因是这样,整个对象可以用一种材料组合成一个网格。如果您没有将thetaLength设置为负数,则必须将材质设置为BackSide,并将侧面设置为BackSide。

在下面的示例中,我已经完成了我要说的(您可以使用鼠标进行缩放和移动)。负theta柱面在左侧,而正常的θ柱面在右侧。

我遇到的问题是,您可以看到左边的那个圆柱体(内部)比右边的圆柱体暗得多。合适的人看起来更现实。

我在想也许是因为它认为光是从不同的方向发出的,而不是实际发出的方向。

有什么方法可以解决这个问题,并使倒立的圆柱体看起来像BackSide一样,这样我就可以将一个这样的管子当作一个网格?

width = window.innerWidth
height = window.innerHeight

renderer = new THREE.WebGLRenderer({antialias: true})
renderer.setClearColor(0x8e8ed7)
renderer.setPixelRatio(window.devicePixelRatio)
renderer.setSize(width, height)
document.body.appendChild(renderer.domElement)

scene = new THREE.Scene()
camera = new THREE.PerspectiveCamera(35, width / height, 0.1, 3000)
camera.position.set(0, 50, 100)

controls = new THREE.OrbitControls(camera)
controls.minDistance = 40
controls.maxDistance = 1300

scene.add(camera, new THREE.AmbientLight(0xffffff, 0.48))
light = new THREE.PointLight(0xffffff, 0.55)

light.position.copy( camera.position );
light.position.y -= 80
light.position.x += 100
camera.add(light)

requestAnimationFrame(function animate(){
  requestAnimationFrame(animate)
  renderer.render(scene, camera)
})

material = new THREE.MeshPhongMaterial({color: 0xFF7E14, specular: 0x111111, shininess: 75})
material2= new THREE.MeshPhongMaterial({color: 0xFF7E14, specular: 0x111111, shininess: 75, side: THREE.BackSide})

tube_a = new THREE.Mesh(new THREE.CylinderGeometry(6,6,20,32,1,true,0,-6.3), material)
tube_aa = new THREE.Mesh(new THREE.CylinderGeometry(6,6,20,32,1,true,0,6.3), material2)
tube_b = new THREE.Mesh(new THREE.CylinderGeometry(8.1375,8.1375,20,32,1,true), material)
ring = new THREE.Mesh(new THREE.RingGeometry(6,8.1375,32), material)

group1 = new THREE.Group()

ta1 = tube_a.clone()
group1.add(ta1)
tb1 = tube_b.clone()
group1.add(tb1)
r = ring.clone()
r.position.y -= 10
r.rotateX((9*Math.PI)/18)
group1.add(r)
r = ring.clone()
r.position.y += 10
r.rotateX((27*Math.PI)/18)
group1.add(r)
group1.position.x -= 15
scene.add(group1)

group2 = new THREE.Group()

ta2 = tube_aa.clone()
group2.add(ta2)
tb2 = tube_b.clone()
group2.add(tb2)
r = ring.clone()
r.position.y -= 10
r.rotateX((9*Math.PI)/18)
group2.add(r)
r = ring.clone()
r.position.y += 10
r.rotateX((27*Math.PI)/18)
group2.add(r)
group2.position.x += 15
scene.add(group2)
<script src="http://threejs.org/build/three.min.js"></script>
<script src="http://threejs.org/examples/js/controls/OrbitControls.js"></script>

1 个答案:

答案 0 :(得分:1)

  

我遇到的问题是,您可以看到左边的那个圆柱体(内部)比右边的圆柱体暗得多。合适的人看起来更现实。

生成网格后,必须通过Geometry.computeVertexNormals()更新顶点法线向量,以解决此问题:

tube_a = new THREE.Mesh(new THREE.CylinderGeometry(6,6,20,32,1,true,0,-6.3), material)
tube_a.geometry.computeVertexNormals();

width = window.innerWidth
height = window.innerHeight

renderer = new THREE.WebGLRenderer({antialias: true})
renderer.setClearColor(0x8e8ed7)
renderer.setPixelRatio(window.devicePixelRatio)
renderer.setSize(width, height)
document.body.appendChild(renderer.domElement)

scene = new THREE.Scene()
camera = new THREE.PerspectiveCamera(35, width / height, 0.1, 3000)
camera.position.set(0, 50, 100)

controls = new THREE.OrbitControls(camera)
controls.minDistance = 40
controls.maxDistance = 1300

scene.add(camera, new THREE.AmbientLight(0xffffff, 0.48))
light = new THREE.PointLight(0xffffff, 0.55)

light.position.copy( camera.position );
light.position.y -= 80
light.position.x += 100
camera.add(light)

requestAnimationFrame(function animate(){
  requestAnimationFrame(animate)
  renderer.render(scene, camera)
})

material = new THREE.MeshPhongMaterial({color: 0xFF7E14, specular: 0x111111, shininess: 75})
material2= new THREE.MeshPhongMaterial({color: 0xFF7E14, specular: 0x111111, shininess: 75, side: THREE.BackSide})

tube_a = new THREE.Mesh(new THREE.CylinderGeometry(6,6,20,32,1,true,0,-6.3), material)
tube_a.geometry.computeVertexNormals();

tube_aa = new THREE.Mesh(new THREE.CylinderGeometry(6,6,20,32,1,true,0,6.3), material2)
tube_b = new THREE.Mesh(new THREE.CylinderGeometry(8.1375,8.1375,20,32,1,true), material)
ring = new THREE.Mesh(new THREE.RingGeometry(6,8.1375,32), material)




group1 = new THREE.Group()

ta1 = tube_a.clone()
group1.add(ta1)
tb1 = tube_b.clone()
group1.add(tb1)
r = ring.clone()
r.position.y -= 10
r.rotateX((9*Math.PI)/18)
group1.add(r)
r = ring.clone()
r.position.y += 10
r.rotateX((27*Math.PI)/18)
group1.add(r)
group1.position.x -= 15
scene.add(group1)

group2 = new THREE.Group()

ta2 = tube_aa.clone()
group2.add(ta2)
tb2 = tube_b.clone()
group2.add(tb2)
r = ring.clone()
r.position.y -= 10
r.rotateX((9*Math.PI)/18)
group2.add(r)
r = ring.clone()
r.position.y += 10
r.rotateX((27*Math.PI)/18)
group2.add(r)
group2.position.x += 15
scene.add(group2)

function resize() {
    
    var aspect = window.innerWidth / window.innerHeight;
    renderer.setSize(window.innerWidth, window.innerHeight);
    camera.aspect = aspect;
    camera.updateProjectionMatrix();
    //controls.handleResize();
  }

window.onresize = resize;
<script src="http://threejs.org/build/three.min.js"></script>
<script src="http://threejs.org/examples/js/controls/OrbitControls.js"></script>