Hello…everyone in this forum…
I have a problem with perspective camera in my three.js app. Below is my explanation.
I have a 3d mesh and two skyboxes inside. Everytime I move into a skybox using tween, it goes nicely looking at the target and at the end the camera turns to -Z direction with controls.update(). If I don’t put controls.update(), the camera stays the direction until I click mouse and move the mouse. So, after I move the mouse the camera turns to -Z direction. I guess in animate function controls get reset maybe. I have been trying to solve this problem at least a couple of days and I have no clue why it happens. Here is the code snippet. Thanks in advance.
//-> init function
function init() {
//container = document.getElementById( 'container' );
container = document.createElement( 'div' );
container.style.width="100%";
container.style.height="calc( 100% - 70px)";
document.body.appendChild( container );
// SCENE
scene = new THREE.Scene(); // for model
scene.background = new THREE.Color( 0x000000 );
scene2 = new THREE.Scene(); // for other stuffs such as sprites // RENDERER
renderer = new THREE.WebGLRenderer();
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
renderer.gammaOutput = true;
//document.body.appendChild( renderer.domElement );
container.appendChild( renderer.domElement );
// possibly vr button will show up at the bottom
document.body.appendChild( WEBVR.createButton( renderer ) );
renderer.vr.enabled = false;
// CAMERA
camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 1, 2000 );
camera.zoom = 0.8;
camera.fov = 70;
camera.near = 1;
camera.far = 2000;
camera.updateProjectionMatrix();
var position = new THREE.Vector3( 0, 150, 500 );
moveCameraOut( position );
// CONTROL
controls = new OrbitControls( camera, renderer.domElement );
controls.update();
// LIGHT
var ambientLight = new THREE.AmbientLight( 0xffffff, 5 );
scene.add( ambientLight );
var pointLight = new THREE.PointLight( 0xffffff, 0.2 );
camera.add( pointLight );
scene.add( camera );
// axes
var axes = new THREE.AxesHelper();
axes.scale.set( 1000, 1000, 1000 );
scene.add( axes );
// MODEL LOADING
blah...blah...blah...
// to load panorama boxes with hot points at the bottom of them
for ( var i = 0 ; i < json_navi.length ; i++ ) {
var background = json_navi[i].background;
var textures = getTextures( background, 6 );
var materials = [];
for ( var j = 0 ; j < 6 ; j++ ) {
materials.push( new THREE.MeshBasicMaterial( { map: textures[ j ], transparent: false, opacity: 0.5 } ) );
}
var position = json_navi[ i ].position;
var skyBox = new THREE.Mesh( new THREE.BoxBufferGeometry( 10, 10, 10 ), materials );
skyBox.geometry.scale( 1, 1, -1 );
skyBox.position.copy( position );
skyBox.rotation.y = Math.PI * json_navi[i].rotation / 180;
skyBox.name = panoBox_name + '_' + json_navi[ i ].id;
scene.add( skyBox );
var naviGeometry = new THREE.RingBufferGeometry( 0.2, 0.5, 30, 30 );
var naviMaterial = new THREE.MeshBasicMaterial( { color: 0xFF0000, transparent: true, opacity: 0.5, side: THREE.DoubleSide } );
naviMaterial.depthTest = false;
naviMesh = new THREE.Mesh( naviGeometry, naviMaterial );
naviMesh.lookAt( new THREE.Vector3( 0, 1, 0 ) );
naviMesh.position.set( position.x, position.y-5, position.z );
naviMesh.name = panoBox_hp_name + '_' + json_navi[i].id;
scene.add( naviMesh );
}
// event listeners
window.addEventListener( 'resize', onWindowResize, false );
container.addEventListener( 'mousemove', function(event) {
if (floorplanMode != 'floorplan') {
onDocumentMouseMove( event );
}
}, false );
var singleClickTimer;
var clickCount = 0;
container.addEventListener( 'click', function(event) {
if (floorplanMode != 'floorplan') {
clickCount++;
if ( clickCount === 1 ) {
singleClickTimer = setTimeout( function() {
clickCount = 0;
onDocumentMouseDown( event );
}, 400 );
} else if ( clickCount === 2 ) {
clearTimeout( singleClickTimer );
clickCount = 0;
onDocumentMouseDblClick( event );
}
}
}, false );
}
//<- end of init function
function animate() {
requestAnimationFrame( animate );
renderer.render( scene, camera );
TWEEN.update();
}
function onWindowResize() {
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize( window.innerWidth, window.innerHeight );
}
function onDocumentMouseDown( event ) {
event.preventDefault();
var mouse = new THREE.Vector2();
mouse.x = ( event.clientX / renderer.domElement.clientWidth ) * 2 - 1;
mouse.y = - ( event.clientY / renderer.domElement.clientHeight ) * 2 + 1;
var vector = new THREE.Vector3( mouse.x, mouse.y, 0.5 );
vector = vector.unproject( camera );
var raycaster = new THREE.Raycaster( camera.position, vector.sub( camera.position ).normalize() );
raycaster.setFromCamera( mouse, camera );
var intersects = raycaster.intersectObjects( scene.children, true );
if ( intersects.length > 0 ) {
var panoramaObject = null;
var hotpointObject = null;
for ( var i = 0; i < intersects.length; i++ ){
var currentObject = intersects[i];
if (currentObject.object.name.startsWith(panoBox_name)) { panoramaObject = currentObject; }
if (hotpointObject == null && currentObject.object.name.startsWith(panoBox_hp_name)) { hotpointObject = currentObject; }
}
if (panoramaObject != null && hotpointObject != null) {
moveCameraToHotPoint( panoramaObject );
}
}
}
function moveCameraToHotPoint( panoramaObject ) {
var controlTo = panoramaObject.object.position.clone();
var cameraTo = panoramaObject.object.position.clone();
cameraTo.setZ( cameraTo.z + 0.01);
var tween = new TWEEN.Tween( camera.position );
tween.to( cameraTo, 1000 );
tween.easing( TWEEN.Easing.Linear.None );
tween.start();
tween.onUpdate( function() { /*camera.lookAt( cameraTo ); */controls.target.copy( controlTo ); } );
tween.onComplete( function() { /*camera.lookAt( cameraTo ); */controls.target.copy( controlTo ); controls.update();} );
}