在實際開發中,3D美術提供的三維模型可能包含幀動畫數據需要你解析渲染,比如一個機械的裝配過程,一個車門開關的動作,一個物體的移動動畫。這時候你首先要對建立幀動畫的概念,然后對Threejs幀動畫相關的API使用規則進行熟悉,這樣才能很好的解析加載的外部模型包含的幀動畫。
效果圖:
Threejs提供了一系列用戶編輯和播放關鍵幀動畫的API,使用關鍵幀KeyframeTrack
和剪輯AnimationClip
編寫一個關鍵幀動畫,然后調用操作AnimationAction
、混合器AnimationMixer
播放編寫好的關鍵幀動畫。
主要代碼:
<button onclick="pause()" type="button" style="position: absolute;padding: 10px;">暫停/繼續</button> <button onclick="pos()" type="button" style="position: absolute;padding: 10px;left:90px">時間遞增</button>
/** * 創建兩個網格模型並設置一個父對象group */ var group = new THREE.Group(); mesh1.name = "Box"; //網格模型1命名 mesh2.name = "Sphere"; //網格模型2命名 group.add(mesh1); //網格模型添加到組中 group.add(mesh2); //網格模型添加到組中 /** * 編輯group子對象網格模型mesh1和mesh2的幀動畫數據 */ // 創建名為Box對象的關鍵幀數據 var times = [0, 100]; //關鍵幀時間數組,離散的時間點序列 var values = [0, 0, 0, 150, 0, 0]; //與時間點對應的值組成的數組 // 創建位置關鍵幀對象:0時刻對應位置0, 0, 0 10時刻對應位置150, 0, 0 var posTrack = new THREE.KeyframeTrack('Box.position', times, values); // 創建顏色關鍵幀對象:10時刻對應顏色1, 0, 0 20時刻對應顏色0, 0, 1 var colorKF = new THREE.KeyframeTrack('Box.material.color', [50, 100], [1, 0, 0, 0, 0, 1]); // 創建名為Sphere對象的關鍵幀數據 從0~20時間段,尺寸scale縮放3倍 var scaleTrack = new THREE.KeyframeTrack('Sphere.scale', [30, 100], [1, 1, 1, 5, 5, 5]); // duration決定了默認的播放時間,一般取所有幀動畫的最大時間 // duration偏小,幀動畫數據無法播放完,偏大,播放完幀動畫會繼續空播放 var duration = 100; // 多個幀動畫作為元素創建一個剪輯clip對象,命名"default",持續時間20 var clip = new THREE.AnimationClip("default", duration, [posTrack, colorKF, scaleTrack]) scene.add(group); // 暫停繼續播放函數 function pause() { if (AnimationAction.paused) { // 如果是播放狀態,設置為暫停狀態 AnimationAction.paused = false; } else { // 如果是暫停狀態,設置為播放狀態 AnimationAction.paused = true; } } // 時間點設置函數 function pos() { // 開始結束時間設置為一樣,相當於播放時間為0,直接跳轉到時間點對應的狀態 AnimationAction.time += 2; //操作對象設置開始播放時間 clip.duration = AnimationAction.time; //剪輯對象設置播放結束時間 AnimationAction.play(); //開始播放 } /** * 播放編輯好的關鍵幀數據 */ // group作為混合器的參數,可以播放group中所有子對象的幀動畫 var mixer = new THREE.AnimationMixer(group); // 剪輯clip作為參數,通過混合器clipAction方法返回一個操作對象AnimationAction var AnimationAction = mixer.clipAction(clip); //通過操作Action設置播放方式 AnimationAction.timeScale = 20; //默認1,可以調節播放速度 // AnimationAction.loop = THREE.LoopOnce; //不循環播放 AnimationAction.play(); //開始播放