javascript - 立体几何背后的光
问题描述
我正在创建一个集成 ThreeJs 的 HTML 文件,基本上我创建了 4 个球体,其中 1 个投射光,其他 3 个球体在墙上转动。当球体在墙后面时,它们不应该反射光线,我应该怎么做才能解决这个问题?
我已经尝试将围绕墙壁转动的球体的材质更改为 Lambert 和 Phong,将 castShadow 设置为 true,并将 recieveShadow 设置为 False
(function onLoad() {
var camera, scene, renderer, orbitControls;
init();
animate();
function init() {
camera = new THREE.PerspectiveCamera(70, window.innerWidth / window.innerHeight, 1, 1000);
camera.position.set(0, 30, -100);
scene = new THREE.Scene();
scene.background = new THREE.Color(0xffffff);
scene.add(camera);
orbitControls = new THREE.OrbitControls(camera);
escena = scene;
esferaLuz = new THREE.SphereBufferGeometry(0.5, 16, 16);
luzUno = new THREE.SpotLight(0xFFFFFF, 1);
luzUno.angle = Math.PI / 12;
luzUno.penumbra = 0.05;
luzUno.decay = 2;
luzUno.position.set(-30, 40, -5);
mtLuzUno = new THREE.MeshBasicMaterial({color: 0xFFFFFF});
mallaLuzUno = new THREE.Mesh(esferaLuz, mtLuzUno);
luzUno.add(mallaLuzUno);
escena.add(luzUno);
luzUno.castShadow = true;
luzUno.shadow.mapSize.width = 1024;
luzUno.shadow.mapSize.height = 1024;
luzUno.shadow.camera.near = 10;
luzUno.shadow.camera.far = 200;
luzMap = new THREE.SpotLightHelper(luzUno);
escena.add(luzMap);
sombraMap = new THREE.CameraHelper(luzUno.shadow.camera);
escena.add(sombraMap);
var luzAmbiente = new THREE.AmbientLight( 0xffffff, 0.1 );
escena.add(luzAmbiente);
geometriaPlana = new THREE.CubeGeometry(100, 100, 2, 2);
mtPlano = new THREE.MeshLambertMaterial({color: 0x000000});
mtPlano.transparent = false;
mtPlano.depthWrite = true;
mallaPlano = new THREE.Mesh(geometriaPlana, mtPlano);
mallaPlano.rotation.x = -0.5*Math.PI;
mallaPlano.position.x = 15;
mallaPlano.position.y = 0;
mallaPlano.position.z = 0;
mallaPlano.receiveShadow = true;
escena.add(mallaPlano);
objEsfera = new THREE.SphereGeometry(5, 100, 100);
mtObjEsfera = new THREE.MeshPhongMaterial({color: 0xFFFFFF, specular:0xFFFFFF, shininess: 1024});
mallaObjEsfera3 = new THREE.Mesh(objEsfera, mtObjEsfera);
mallaObjEsfera3.position.set(20, 0, 0);
mallaObjEsfera3.castShadow = true;
mallaObjEsfera3.receiveShadow = false;
escena.add(mallaObjEsfera3);
objEsfera = new THREE.SphereGeometry(5, 100, 100);
mtObjEsfera = new THREE.MeshPhongMaterial({color: 0xF90E0E, specular:0xF90E0E, shininess: 512});
mallaObjEsfera2 = new THREE.Mesh(objEsfera, mtObjEsfera);
mallaObjEsfera2.position.set(5, 0, 0);
mallaObjEsfera2.castShadow = true;
mallaObjEsfera2.receiveShadow = false;
escena.add(mallaObjEsfera2);
objEsfera = new THREE.SphereGeometry(5, 100, 100);
mtObjEsfera = new THREE.MeshLambertMaterial({color: 0xF2E406});
mallaObjEsfera = new THREE.Mesh(objEsfera, mtObjEsfera);
mallaObjEsfera.position.set(-10, 0, 0);
mallaObjEsfera.castShadow = true;
mallaObjEsfera.receiveShadow = false;
escena.add(mallaObjEsfera);
renderer = new THREE.WebGLRenderer({antialias: true});
renderer.setPixelRatio( window.devicePixelRatio);
renderer.setClearColor(0xEEEEEE);
renderer.shadowMap.enabled = true;
renderer.shadowMap.renderReverseSided = false;
renderer.sortObjects = false
renderer.shadowMap.type = THREE.PCFSoftShadowMap;
renderer.setSize( window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);
renderer.gammaInput = true;
renderer.gammaOutput = true;
window.onresize = function() {
renderer.setSize(window.innerWidth, window.innerHeight);
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
}
}
function animate() {
requestAnimationFrame(animate);
orbitControls.update();
render();
}
function render() {
renderer.render(scene, camera);
}
})();
<script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/103/three.min.js"></script>
<script src="https://threejs.org/examples/js/controls/OrbitControls.js"></script>
我希望当球体在墙后面时,不要显示任何类型的光反射,但是当球体在前面时会反射光。
解决方案
实现预期结果的一种方法是使用阴影。所以你必须为你的球体和你的地面设置和Object3D.castShadow
设置,就像下面的例子一样:Object3D.receiveShadow
true
https://jsfiddle.net/85q3sfeg/
另请记住,three.js
目前不支持选择性照明。这个问题已经在 github 上讨论过:https ://github.com/mrdoob/three.js/issues/5180
假设场景中的所有对象都应用了光照材质,您无法定义哪些光源应该影响哪些对象。
three.js R103
推荐阅读
- reactjs - 通过 onClick 改变 Component 属性
- bash - Scala 2.12.12 的 Shell 脚本损坏了吗?
- splunk - 如何一次计算和绘制多个搜索?
- javascript - 如何更改高图上未悬停的列的不透明度?
- ruby - ruby cmd在文件夹rbenv中不起作用:ruby:找不到命令
- reactjs - 传递给 withAuthenticator HOC 封闭组件的 Props 为空
- c# - 如何在 xamarin 中实现 httpclientfactory?
- r - 如何在 ggplot 中添加来自 GauPro 的曲线?
- vba - 如何在 VBA 中为重复键使用字典?
- ios - ITMS-90809:不推荐使用的 API 使用 - 不再接受使用 UIWebView 的新应用程序