簡體   English   中英

鼠標單擊時對象的動畫(旋轉,移動)

[英]Animation (rotation, movement) of an object on mouse click

考慮這個three.js示例

https://threejs.org/examples/?q=glt#webgl_loader_gltf

我正在嘗試在鼠標單擊事件上實現對象的動畫(對象當前所在位置的旋轉/移動),但沒有動畫。

這是我添加的代碼。 我會過度渲染嗎?

        document.addEventListener( 'mousedown', clickMe, false );
        render();

        function clickMe() {
            rotation();
            render();   
        }


        var gltfModel;


        function rotation() {
            var rotationAnimation = 5 * (Math.PI / 180);
            gltfModel.rotation.x += rotationAnimation;
            render();       
        }

        function render() {
            renderer.render( scene, camera );
        }

如果我添加功能rotation(); requestAnimationFrame(rotation);

            function rotation() {
            requestAnimationFrame( rotation );
            var rotationAnimation = 5 * (Math.PI / 180);
            gltfModel.rotation.x += rotationAnimation;
            render();       
        }

gltfModel保持循環旋轉,每次單擊速度都會翻倍

這是完整的代碼:

        <script>

        if ( WEBGL.isWebGLAvailable() === false ) {

            document.body.appendChild( WEBGL.getWebGLErrorMessage() );

        }

        var container, stats, controls;
        var camera, scene, renderer, light;




        init();
        animate();

        function init() {

            container = document.createElement( 'div' );
            document.body.appendChild( container );

            camera = new THREE.PerspectiveCamera( 45, window.innerWidth / window.innerHeight, 0.25, 20 );
            camera.position.set( - 1.8, 0.9, 2.7 );

            controls = new THREE.OrbitControls( camera );
            controls.target.set( 0, - 0.2, - 0.2 );
            controls.update();

            var urls = [ 'posx.jpg', 'negx.jpg', 'posy.jpg', 'negy.jpg', 'posz.jpg', 'negz.jpg' ];
            var loader = new THREE.CubeTextureLoader().setPath( 'textures/cube/Bridge2/' );
            var background = loader.load( urls );

            scene = new THREE.Scene();
            scene.background = background;

            light = new THREE.HemisphereLight( 0xbbbbff, 0x444422 );
            light.position.set( 0, 1, 0 );
            scene.add( light );

            // model
            var loader = new THREE.GLTFLoader().setPath( 'models/gltf/DamagedHelmet/glTF/' );
            loader.load( 'DamagedHelmet.gltf', function ( gltf ) {

                gltf.scene.traverse( function ( child ) {

                    if ( child.isMesh ) {

                        child.material.envMap = background;

                        gltfModel = child;

                    }

                } );

                scene.add( gltf.scene );

            }, undefined, function ( e ) {

                console.error( e );

            } );

            renderer = new THREE.WebGLRenderer( { antialias: true } );
            renderer.setPixelRatio( window.devicePixelRatio );
            renderer.setSize( window.innerWidth, window.innerHeight );
            renderer.gammaOutput = true;
            container.appendChild( renderer.domElement );

            window.addEventListener( 'resize', onWindowResize, false );

            //MY LINE OF CODE
            document.addEventListener( 'mousedown', clickMe, false );
            render();


            // stats
            stats = new Stats();
            container.appendChild( stats.dom );

        }

        function onWindowResize() {

            camera.aspect = window.innerWidth / window.innerHeight;
            camera.updateProjectionMatrix();

            renderer.setSize( window.innerWidth, window.innerHeight );

        }

        //MY LINE OF CODE
        ///////////////////////////////////////

        function clickMe() {

            rotation();

            render();



        }


        var gltfModel;


        function rotation() {

            var rotationAnimation = 5 * (Math.PI / 180);

            gltfModel.rotation.x += rotationAnimation;

            render();

        }




        ///////////////////////////////////////



        function animate() {

            requestAnimationFrame( animate );


            render();

            stats.update();


        }


        function render() {
            renderer.render( scene, camera );
        }

    </script>

可以用EventDispatcher完成嗎? 如果是這樣,怎么辦? https://threejs.org/docs/#api/en/core/EventDispatcher

但我寧願選擇第一種方法?

是的,您只需要調用一次render ,這樣您就可以從rotation()clickMe()以及在document.addEventListener( 'mousedown', clickMe, false );之后取出這三個調用document.addEventListener( 'mousedown', clickMe, false );

但是,每次單擊僅旋轉對象一次。 我假設您要實現的是按住鼠標的同時旋轉對象。

如果要執行此操作,可以在mousedown上設置一個布爾值。

因此,在clickMe內,您可以執行以下操作:

function clickMe() {
  rotating = true; // declare this as a global variable
}

然后在渲染功能中,您可以執行以下操作:

function render() {
  if (rotating) {
    var rotationAnimation = 5 * (Math.PI / 180);
    gltfModel.rotation.x += rotationAnimation;
  }
  renderer.render( scene, camera );
}

完成所有這些操作后,請確保添加一個mouseup偵聽器,以在放開鼠標時停止旋轉。

function handleMouseUp() {
  rotating = false;
}

document.addEventListener('mouseup', handleMouseUp);

一個盒子的簡單代碼示例,它將鼠標向下滾動以幫助您入門。 您可以輕松地將其應用於gltf模型。 至於render方法,是的,您無緣無故地在函數中使用它。 您應該看一下基本的場景示例。

https://threejs.org/docs/#manual/en/introduction/Creating-a-scene

 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> </body> <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/101/three.min.js"></script> <script> var box; var isMouseDown = false; var rotateSpeed = 0; init(); animate(); function init() { container = document.createElement('div'); document.body.appendChild(container); camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.25, 20); camera.position.set(5,5,5); camera.lookAt(new THREE.Vector3(0,0,0)); scene = new THREE.Scene(); light = new THREE.HemisphereLight(0xbbbbff, 0x444422); light.position.set(0, 1, 0); scene.add(light); var geometry = new THREE.BoxBufferGeometry( 1, 1, 1 ); var material = new THREE.MeshBasicMaterial( {color: 0x00ff00} ); box = new THREE.Mesh( geometry, material ); scene.add( box ); renderer = new THREE.WebGLRenderer({ antialias: true }); renderer.setPixelRatio(window.devicePixelRatio); renderer.setSize(window.innerWidth, window.innerHeight); container.appendChild(renderer.domElement); window.addEventListener('mousedown', () => isMouseDown = true,false); window.addEventListener('mouseup', () => isMouseDown = false,false); animate(); } function animate() { requestAnimationFrame(animate); if(isMouseDown) rotateSpeed += 0.001; else rotateSpeed /= 1.01; box.rotation.y += rotateSpeed; render(); } function render() { renderer.render(scene, camera); } </script> </html> 

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM