slingers
 
slingers
 
 
 
 
 
 
amsterdam
 
Amsterdam
 
 
 
 
 
 
 
 
fractals
 
fractals
 
 
 
 
 
 
 
 
 
wolken
 
 boven de wolken
 
 
 
 
 
amsterdam
 
 Amsterdam
 
 
 
wolken
 
boven de wolken

Spiegelbal.                           terug naar de inleiding             ga naar de animatie in fullscreen

Spiegelbal is een animatie met equirectangulaire afbeeldingen en een bal waarin deze afbeeldingen worden gespiegeld.
Dit spiegelen wordt gerealiseerd in de functie createEquirectShader (line 59) met de classes ShaderMaterial en ShaderLib

Shaders zijn best moeilijk te begrijpen ze zijn geschreven in GLSL  Hier nog een link naar "the book of shaders".

De overige functies zijn, met wat aanpassingen, hetzelfde als die in de schets "wereldbeeld".
De schets maakt gebruik van twee camera's, een voor de achtergrond en een voor de bol, daarom is in de renderer autoclear (line 43) uitgeschakeld.

Door deze truc  werkte createExport niet goed.

De achtergrond beweegd mee met de bol, dit door het telkens copieeren van de camera positie van de bol afbeelding

naar de camerapositie van de achtergrond afbeelding (line 155).

In alle 3d animaties is een storende streepjeslijn te zien, dit komt door de equirectangulaire afbeelding, dit probleem ontstaat niet bij cube afbeeldingen.

 
 

let container, scene, sceneBol, camera, cameraBol, ambient, renderer, controls; 
let textureLoader, textureEquirec, equirectShader, uniforms, gui, params; 
let bolG, bolMat, bolM, equirectG, equirectMat, equirectM, dataURL, exporteren; 
 
  init(); 
  play(); 
 
  function init() { 
    createScenecontainer(); 
    createCamera(); 
    createLight();  //deze uitschakelen dan in de bol zwart 
    createRenderer();//createRenderen moet altijd boven createControls staan 
    createControls(); 
    createEquirect(); //Laden van de Equirectangular afbeelding 
    createEquirectShader(); //uitschakelen --> witte bol met zwarte achtergrond 
    createSpiegelbol(); // uitschakelen dan zie je alleen de omgeving 
    createGUI(); 
    onWindowResize(); 
    window.addEventListener( 'resize', onWindowResize ); 
} 
 
function createScenecontainer(){ 
  container = document.querySelector( '#scene-container' ); 
  scene = new THREE.Scene(); 
  sceneBol = new THREE.Scene(); 
} 
 
function createCamera(){ 
  cameraBol = new THREE.PerspectiveCamera( 70, container.clientWidth / container.clientHeight, 1, 100000 ); 
  cameraBol.position.set( 0, 0, 800 ); 
  camera = new THREE.PerspectiveCamera( 70, container.clientWidth / container.clientHeight, 1, 100000 ); 
  camera.position.set( 0, 0, 200 ); 
} 
 
 function createLight(){ 
   ambient = new THREE.AmbientLight( 0xffffff ); 
   sceneBol.add( ambient ); 
 } 
 
 function createRenderer(){ 
   renderer = new THREE.WebGLRenderer(); 
   renderer.autoClear = false; 
   renderer.setPixelRatio( window.devicePixelRatio ); 
   renderer.setSize( container.clientWidth, container.clientHeight ); 
   document.body.appendChild( renderer.domElement ); 
   renderer.outputEncoding = THREE.sRGBEncoding; 
 } 
 
function createEquirect(){ 
  textureLoader = new THREE.TextureLoader(); 
  textureEquirec = textureLoader.load( 'textures/equirectangular/escher.jpg' ); 
  textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
  textureEquirec.encoding = THREE.sRGBEncoding; 
} 
 
//In deze functie wordt de geladen afbeelding textureEquirec omgezet in eqiurectmaterial 
//equirectMaterial wordt op een SphereBufferGeometry geplakt 
 function createEquirectShader(){ 
   equirectShader = THREE.ShaderLib[ 'equirect' ]; 
   equirectMat = new THREE.ShaderMaterial( { 
   uniforms: THREE.UniformsUtils.clone( equirectShader.uniforms ), 
   fragmentShader: equirectShader.fragmentShader, 
   vertexShader: equirectShader.vertexShader, 
   depthWrite: false, 
   side: THREE.BackSide 
} ); 
 
   equirectMat.uniforms[ 'tEquirect' ].value = textureEquirec; 
   Object.defineProperty( equirectMat, 'map', { 
   get: function () {return this.uniforms.tEquirect.value;}} ); 
 
   equirectG = new THREE.SphereBufferGeometry( 1000, 200, 200 ); 
   equirectM = new THREE.Mesh( equirectG, equirectMat ); 
   scene.add( equirectM ); 
} 
 
function createSpiegelbol(){ 
   bolG = new THREE.SphereBufferGeometry( 400.0, 48, 24 ); 
   //de ommgeving wordt met envMap op de bol gemapt 
   bolMat= new THREE.MeshLambertMaterial( { envMap: textureEquirec} ); 
   bolM = new THREE.Mesh( bolG, bolMat ); 
   sceneBol.add( bolM ); 
 } 
 
 function onWindowResize() { 
   cameraBol.aspect = container.clientWidth / container.clientHeight; 
   cameraBol.updateProjectionMatrix(); 
   camera.aspect = container.clientWidth / container.clientHeight; 
   camera.updateProjectionMatrix(); 
   renderer.setSize( container.clientWidth, container.clientHeight ); 
 } 
 
function createGUI() { 
  params = { 
    escher: function () { 
      textureEquirec = textureLoader.load( 'textures/equirectangular/escher.jpg' ); 
      textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
      textureEquirec.encoding = THREE.sRGBEncoding; 
      createEquirectShader(); 
      bolMat.envMap = textureEquirec; 
      bolMat.needsUpdate = true; 
    }, 
    slingers: function () { 
      textureEquirec = textureLoader.load( 'textures/equirectangular/texture2.jpg' ); 
      textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
      textureEquirec.encoding = THREE.sRGBEncoding; 
      createEquirectShader(); 
      bolMat.envMap = textureEquirec; 
      bolMat.needsUpdate = true; 
    }, 
    Amsterdam: function () { 
      textureEquirec = textureLoader.load( 'textures/equirectangular/brug.jpg' ); 
      textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
      textureEquirec.encoding = THREE.sRGBEncoding; 
      createEquirectShader(); 
      bolMat.envMap = textureEquirec; 
      bolMat.needsUpdate = true; 
    }, 
    fractals_3d: function () { 
      textureEquirec = textureLoader.load( 'textures/equirectangular/stenen3.jpg' ); 
      textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
      textureEquirec.encoding = THREE.sRGBEncoding; 
      createEquirectShader(); 
      bolMat.envMap = textureEquirec; 
      bolMat.needsUpdate = true; 
    }, 
    boven_de_wolken: function () { 
      textureEquirec = textureLoader.load( 'textures/equirectangular/lucht.jpg' ); 
      textureEquirec.mapping = THREE.EquirectangularReflectionMapping; 
      textureEquirec.encoding = THREE.sRGBEncoding; 
      createEquirectShader(); 
      bolMat.envMap = textureEquirec; 
      bolMat.needsUpdate = true; 
    }, 
    bol_in_uitschakelen: true 
}; 
 
  var gui = new dat.GUI({width:280}); 
  gui.add( params, 'escher' ); 
  gui.add( params, 'slingers' ); 
  gui.add( params, 'Amsterdam' ); 
  gui.add( params, 'fractals_3d' ); 
  gui.add( params, 'boven_de_wolken' ); 
  gui.add( params, 'bol_in_uitschakelen' ); 
  gui.close(); 
} 
 
 function createControls() { 
  controls = new THREE.OrbitControls( cameraBol , container); 
  controls.minDistance = 500; 
  controls.maxDistance = 3000; 
  controls.addEventListener('change', render); 
} 
 
 
 function render() { 
   cameraBol.lookAt( sceneBol.position ); 
   camera.rotation.copy( cameraBol.rotation ); 
   renderer.render( scene, camera ); 
   renderer.render( sceneBol, cameraBol ); 
 } 
 
 function animate() { 
 
    if (params.bol_in_uitschakelen) { 
      sceneBol.visible = true; 
    } 
      else 
      { 
        sceneBol.visible = false; 
      } 
 } 
 
 function play() { 
   renderer.setAnimationLoop( () => {animate();render();} ); 
 }