threejs下載位置:http://www.threejs.org
我在Facebook上看到Facebook實現了3D全景圖,而後,一直很好奇,最後,我發現threejs裏面有一個庫居然能夠實現,一下我貼出代碼:css
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0"> <title>three.js css3d - panorama</title> <style> body { background-color: #000000; margin: 0; cursor: move; overflow: hidden; } a { color: #ffffff; } #info { position: absolute; width: 100%; color: #ffffff; padding: 5px; font-family: Monospace; font-size: 13px; font-weight: bold; text-align: center; z-index: 1; } </style> </head> <body> <script src="../build/three.min.js"></script> <!-- 此處引入threejs基礎類 --> <script src="js/renderers/CSS3DRenderer.js"></script> <!-- 此處引入CSS3Drenderer.js類 --> <!-- 以上兩個文件,在下載threejs的時候就有的,引入就好 --> <script> var camera, scene, renderer; var geometry, material, mesh; var target = new THREE.Vector3(); var lon = 90, lat = 0; var phi = 0, theta = 0; var touchX, touchY; init(); animate(); function init() { camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 1, 1000 ); scene = new THREE.Scene(); /** 次數是重點說明的 * 這個sides對應的是六張圖位於立體座標軸內的位置,裏面的position又包含x,y,三個軸 * 而後ratation是三個軸上的變換 */ var sides = [ { position: [ 512, 0, 0 ], // 1 rotation: [ 0, -Math.PI / 2, 0 ] }, { position: [ -512, 0, 0 ], // 2 rotation: [ 0, Math.PI / 2, 0 ] }, { position: [ 0, 512, 0 ], // 3 rotation: [ Math.PI / 2, 0, Math.PI ] }, { position: [ 0, -512, 0 ], // 4 rotation: [ - Math.PI / 2, 0, Math.PI ] }, { position: [ 0, 0, 512 ], // 5 rotation: [ 0, Math.PI, 0 ] }, { position: [ 0, 0, -512 ], // 6 rotation: [ 0, 0, 0 ] } ]; var canvas = document.createElement('canvas'); var image = document.createElement('img'); image.src = 'picture/360photos.jpg'; // 畫圖,這裏引入的這張圖片,是一張圖上集合了6張圖片 image.height = 6144; image.width = 1024; canvas.width = 1024; canvas.height = 1024; // 這裏有判斷image.onload,這裏是判斷建立的image節點是否把引入的圖片加載進來 image.onload = function() { for ( var i = 0; i < sides.length; i ++ ) { // 因爲是六張圖放在一張圖片上,而後這裏分割六張圖片 var cxt = canvas.getContext("2d"); cxt.drawImage(image, 0, -1024*i); var side = sides[ i ]; var element = document.createElement( 'img' ); element.width = 1026; // 2 pixels extra to close the gap. document.getElementsByTagName('body')[0].appendChild(canvas); var _img_url = canvas.toDataURL("image/png"); // 獲取圖片位置 element.src = _img_url; var object = new THREE.CSS3DObject( element ); // 這裏根據sides把圖片放在座標軸上進行渲染 object.position.fromArray( side.position ); object.rotation.fromArray( side.rotation ); scene.add( object ); } } renderer = new THREE.CSS3DRenderer(); renderer.setSize( window.innerWidth, window.innerHeight ); document.body.appendChild( renderer.domElement ); // document.addEventListener( 'mousedown', onDocumentMouseDown, false ); document.addEventListener( 'mousewheel', onDocumentMouseWheel, false ); document.addEventListener( 'touchstart', onDocumentTouchStart, false ); document.addEventListener( 'touchmove', onDocumentTouchMove, false ); window.addEventListener( 'resize', onWindowResize, false ); } function onWindowResize() { camera.aspect = window.innerWidth / window.innerHeight; camera.updateProjectionMatrix(); renderer.setSize( window.innerWidth, window.innerHeight ); } function onDocumentMouseDown( event ) { event.preventDefault(); document.addEventListener( 'mousemove', onDocumentMouseMove, false ); document.addEventListener( 'mouseup', onDocumentMouseUp, false ); } function onDocumentMouseMove( event ) { var movementX = event.movementX || event.mozMovementX || event.webkitMovementX || 0; var movementY = event.movementY || event.mozMovementY || event.webkitMovementY || 0; lon -= movementX * 0.1; lat += movementY * 0.1; } function onDocumentMouseUp( event ) { document.removeEventListener( 'mousemove', onDocumentMouseMove ); document.removeEventListener( 'mouseup', onDocumentMouseUp ); } function onDocumentMouseWheel( event ) { camera.fov -= event.wheelDeltaY * 0.05; camera.updateProjectionMatrix(); } function onDocumentTouchStart( event ) { event.preventDefault(); var touch = event.touches[ 0 ]; touchX = touch.screenX; touchY = touch.screenY; } function onDocumentTouchMove( event ) { event.preventDefault(); var touch = event.touches[ 0 ]; lon -= ( touch.screenX - touchX ) * 0.1; lat += ( touch.screenY - touchY ) * 0.1; touchX = touch.screenX; touchY = touch.screenY; } function animate() { requestAnimationFrame( animate ); lon += 0.1; lat = Math.max( - 85, Math.min( 85, lat ) ); phi = THREE.Math.degToRad( 90 - lat ); theta = THREE.Math.degToRad( lon ); target.x = Math.sin( phi ) * Math.cos( theta ); target.y = Math.cos( phi ); target.z = Math.sin( phi ) * Math.sin( theta ); camera.lookAt( target ); renderer.render( scene, camera ); } </script> </body> </html>
以上,我把重要的說明點都寫上了註釋,而後,注意,我這裏的圖片是去facebook上下載下來的,我把Facebook上的圖片手動進行了左右翻轉實現的程序,若是不須要手動翻轉,若是是渲染Facebook上的圖片的話,須要把Facebook的圖片用程序進行翻轉再分割才能渲染出正常的圖片,不然渲染出來的全景是不正常的。
我下面附上的圖很大,寬度是1024像素的,而後高度是1024像素*6;原圖是這張圖的左右翻轉。
下面,我附上圖,此圖來自簡書上傳的,可能會有盜鏈致使加載不出來:html