WebGL - SPLessons
SPLessons 5 Steps, 3 Clicks
5 Steps - 3 Clicks

WebGL Lighting

WebGL Lighting

shape Introduction

This chapter demonstrates about the WebGL Lighting which makes scene as more effective when compared to the normal scenes. Using different types of lights gives different look following are the concepts covered in this chapter.
  • Types of Lights

Types of Lights

shape Description

Three.JS have different types of lights. Each and every light has its own priority these are used for the several purposes which makes scene more effective when compared to the normal scene. There are many available lights and following are some types. The figure below shows the different type of lights as shown.

AmbientLight

shape Description

AmbientLight Affects all objects equally on the scene which is similar to the fluorescent light with equal brightness every where. Generally Lights are used in conjuction with the other lighting types and provide a base color to a scene like grey colors. The snippet below demonstrates the basic example of the AmbientLight. [c] var light = new THREE.AmbientLight(color); var light = new THREE.AmbientLight(0xffffff) [/c] The AmbientLight accepts one parameter which is the color.

PointLight

shape Description

PointLight is a special type of light which shines in all directions and it will only affect MeshLambert or MeshPhongMaterials. Properties The snippet below demonstrates the PointLight example as shown. [c] var light = new THREE.PointLight(color, intensty, distance); var light = new THREE.PointLight(0xffffff, 1, 100) [/c] While creating PointLight user need give the intensity and distance other wise which takes the default values.

DirectionalLight

shape Description

DirectionalLight is a lighting source in which light appears to come from the same direction and does not fade over distance. Good example of the Direction Light is the sun. The snippet below demonstrates the basic example of the DirectionalLight. [c] var directionaLight = new THREE.DirectionaLight(color, intensty); var directionaLight = new THREE.DirectionaLight(0xffffff, 0.5); [/c]

SpotLight

shape Description

SpotLight is similar to the theater or concert spot light and which allows user to create a light with a kind of a cone effect which will caste shadows in one direction. The snippet below demonstrates the SpotLight Example as shown. [c] var spotLight = new THREE.SpotLight(color, intensty, distance, angle); var spotLight = new THREE.SpotLight(0xffffff, 1, 100); [/c] SpotLight has an additional property which is angle and is specified in radians.

shape Examples

The code below demonstrates the different types of light effects as shown below. app.js [c] var demo = (function() { "use strict"; var scene = new THREE.Scene(), light = new THREE.AmbientLight(0xffffff), ambientLight, camera, renderer = new THREE.WebGLRenderer(), cube, lightCube, plane, itemsToControl, rotateCube = true, showShadowCastSetting = false, ground; function initScene() { renderer.setSize(window.innerWidth, window.innerHeight); document.getElementById("webgl-container").appendChild(renderer.domElement); camera = new THREE.PerspectiveCamera( 35, window.innerWidth / window.innerHeight, 1, 1000 ); renderer.shadowMapEnabled = true; renderer.shadowMapSoft = true; camera.position.z = 170; camera.position.y = 20; scene.add(camera); plane = new THREE.Mesh(new THREE.PlaneGeometry(200, 200), new THREE.MeshPhongMaterial({ color: 0x0088aa, ambient: 0x0088aa, specular: 0x003344, shininess: 100, shading: THREE.FlatShading, side: THREE.DoubleSide })); plane.rotation.x = 90 * (Math.PI / 180); plane.position.y = -10; plane.name = "plane"; plane.receiveShadow = true; scene.add(plane); light.position.y = 50; setupGui(); changeLight('directional'); lightCube = new THREE.Mesh( new THREE.BoxGeometry(4, 4, 4), new THREE.MeshBasicMaterial({ color: itemsToControl.cubeColor })); lightCube.name = "lightCube"; light.add(lightCube); createCube(); render(); }; function setupGui() { itemsToControl = new function() { this.lightType = 'ambient'; this.cubeMaterial = 'lambert'; this.cubeRotate = 'Yes'; this.ambientLight = 'No'; this.showShadowCast = 'No'; this.lightColor = "#ffffff"; this.cubeColor = "#ffffff"; this.cubeColor = "#ffffff"; this.ambientColor = '#ffffff'; this.specularColor = '#ffffff'; this.emissiveColor = '#0b062f'; this.lightIntensity = 1; this.lightDistance = 100; this.lightAngle = Math.PI / 3; this.cameraXPos = camera.position.x, this.cameraYPos = camera.position.y, this.cameraZPos = camera.position.z; this.lightXPos = light.position.x, this.lightYPos = light.position.y, this.lightZPos = light.position.z }; var gui = new dat.GUI(); var lightType = gui.add(itemsToControl, 'lightType', ['directional', 'point', 'spot']); lightType.onChange(function(value) { changeLight(value) }); var cubeRotate = gui.add(itemsToControl, 'cubeRotate', ['Yes', 'No']); cubeRotate.onChange(function(value) { rotateCube = value == 'Yes'; }); var showShadowCast = gui.add(itemsToControl, 'showShadowCast', ['Yes', 'No']); showShadowCast.onChange(function(value) { light.shadowCameraVisible = value == 'Yes'; }); var ambientLight = gui.add(itemsToControl, 'ambientLight', ['Yes', 'No']); ambientLight.onChange(function(value) { if (value == 'No') { if (ambientLight) scene.remove(ambientLight); } else { ambientLight = new THREE.AmbientLight('#ffffff'); scene.add(ambientLight); } }); //light var lightColor = gui.addColor(itemsToControl, 'lightColor'); lightColor.onChange(function(value) { changeLightColor(value); }); var lightIntensity = gui.add(itemsToControl, 'lightIntensity', 0, 10); lightIntensity.onChange(function(value) { changeLightIntensity(value); }); var lightDistance = gui.add(itemsToControl, 'lightDistance', 0, 200); lightDistance.onChange(function(value) { changeLightDistance(value); }); var lightAngle = gui.add(itemsToControl, 'lightAngle', 0, 180); lightAngle.onChange(function(value) { changeLightAngle(value); }); //cube var cubeMaterial = gui.add(itemsToControl, 'cubeMaterial', ['phong', 'lambert']); cubeMaterial.onChange(function(value) { changeCubeMaterial(value); }); var cubeColor = gui.addColor(itemsToControl, 'cubeColor'); cubeColor.onChange(function(value) { changeCubeColor('color', value); }); var specularColor = gui.addColor(itemsToControl, 'specularColor'); specularColor.onChange(function(value) { changeCubeColor('specular', value); }); var ambientColor = gui.addColor(itemsToControl, 'ambientColor'); ambientColor.onChange(function(value) { changeCubeColor('ambient', value); }); var emissiveColor = gui.addColor(itemsToControl, 'emissiveColor'); emissiveColor.onChange(function(value) { changeCubeColor('emissive', value); }); //camera var cameraXPos = gui.add(itemsToControl, 'cameraXPos', -200, 200); var cameraYPos = gui.add(itemsToControl, 'cameraYPos', -200, 200); var cameraZPos = gui.add(itemsToControl, 'cameraZPos', -400, 400); cameraXPos.onChange(function(value) { move(camera, 'x', value) }); cameraYPos.onChange(function(value) { move(camera, 'y', value) }); cameraZPos.onChange(function(value) { move(camera, 'z', value) }); //light position var lightXPos = gui.add(itemsToControl, 'lightXPos', -200, 200); var lightYPos = gui.add(itemsToControl, 'lightYPos', -200, 200); var lightZPos = gui.add(itemsToControl, 'lightZPos', -200, 200); lightXPos.onChange(function(value) { move(light, 'x', value) }); lightYPos.onChange(function(value) { move(light, 'y', value) }); lightZPos.onChange(function(value) { move(light, 'z', value) }); } function changeCubeMaterial(materialType) { if (cube) scene.remove(cube); var material; if (materialType == 'phong') { material = new THREE.MeshPhongMaterial({ specular: itemsToControl.specularColor, color: itemsToControl.cubeColor, ambient: itemsToControl.ambientColor, emissive: itemsToControl.emissiveColor, shininess: 100 }); } else { material = new THREE.MeshLambertMaterial({ Color: '#ffffff' }); } createCube(material); } function createCube(material) { if (!material) material = new THREE.MeshLambertMaterial({ Color: '#ffffff' }); cube = new THREE.Mesh(new THREE.BoxGeometry(20, 20, 20), material); cube.position.y = 10; cube.name = "cube"; cube.castShadow = true; cube.material.needsUpdate = true; scene.add(cube); } function changeCubeColor(colorType, color) { cube.material[colorType] = new THREE.Color(color); cube.material.needsUpdate = true; } function changeLightColor(color) { light.color = new THREE.Color(color); cube.material.needsUpdate = true; } function changeLightIntensity(intensity) { light.intensity = intensity; cube.material.needsUpdate = true; } function changeLightDistance(value) { light.distance = value; cube.material.needsUpdate = true; } function changeLightAngle(value) { light.angle = value * (Math.PI / 180); cube.material.needsUpdate = true; } function changeLight(lightType) { scene.remove(light); if (lightType == "ambient") { light = new THREE.AmbientLight(new THREE.Color(itemsToControl.lightColor)) } else if (lightType == "directional") { light = new THREE.DirectionalLight(new THREE.Color(itemsToControl.lightColor)); light.position.set(itemsToControl.lightXPos, itemsToControl.lightYPos, itemsToControl.lightZPos); light.castShadow = true; } else if (lightType == "point") { light = new THREE.PointLight(new THREE.Color(itemsToControl.lightColor), itemsToControl.lightIntensity, itemsToControl.lightDistance); light.position.set(itemsToControl.lightXPos, itemsToControl.lightYPos, itemsToControl.lightZPos); } else if (lightType == "spot") { light = new THREE.SpotLight(new THREE.Color(itemsToControl.lightColor)); light.position.set(itemsToControl.lightXPos, itemsToControl.lightYPos, itemsToControl.lightZPos, itemsToControl.lightAngle); light.castShadow = true; } light.shadowCameraVisible = showShadowCastSetting; light.shadowMapWidth = 2048; light.shadowMapHeight = 2048; if (cube) cube.material.needsUpdate = true; if (plane) plane.material.needsUpdate = true; light.add(lightCube); scene.add(light); } function move(item, axis, value) { item.position[axis] = value; } function render() { if (rotateCube) { cube.rotation.x += 0.01; cube.rotation.y += 0.01; } renderer.render(scene, camera); requestAnimationFrame(render); }; window.onload = initScene; return { scene: scene } })(); [/c] index.html [c] <!DOCTYPE html> <html> <head> <title>Intro to WebGL with Three.js</title> <script type="text/javascript" src="scripts/dat.gui.min.js"></script> </head> <body> <div id="webgl-container"></div> <script src="scripts/three.js"></script> <script src="scripts/app.js"></script> </body> </html> [/c] Result By running the above code in a preferred browser, user will get the output as shown below.

Summary

shape Key Points

  • SpotLight is similar to the Theatre light.
  • Direction Light does not fade over distance.
  • Point Light shines in all directions.