從 0到1,開發一個動畫庫(1)
作者: jshao
https://segmentfault.com/a/1190000012923589
如今市面上關於動畫的開源庫多得數不勝數,有關於CSS、js甚至是canvas渲染的,百花齊放,效果炫酷。但你是否曾想過,自己親手去實現(封裝)一個簡單的動畫庫?
本文將從零開始,講授如何搭建一個簡單的動畫庫,它將具備以下幾個特徵:
從實際動畫中抽象出來,根據給定的動畫速度曲線,完成「由幀到值」的計算過程,而實際渲染則交給開發者決定,更具拓展性
支持基本的事件監聽,如 、 、 、 ,及相應的回調函數
支持手動式觸發動畫的各種狀態,如 、 、 、
支持自定義路徑動畫
支持多組動畫的鏈式觸發
完整的項目在這裡:點贊行為高尚!,歡迎各種吐槽和指正^_^
OK,話不多說,現在正式開始。
作為開篇,本節將介紹的是最基本、最核心的步驟——構建「幀-值」對應的函數關係,完成「由幀到值」的計算過程。
目錄結構
首先介紹下我們的項目目錄結構:
是本項目的根目錄,各文件的作用分別如下:
index.js 項目入口文件
core.js 動畫核心文件
easing.js 存放基本緩動函數
引入緩動函數
所謂動畫,簡單來說,就是在一段時間內不斷改變目標某些狀態的結果。這些狀態值在運動過程中,隨著時間不斷發生變化,狀態值與時間存在一一對應的關係,這就是所謂的「幀-值」對應關係,常說的動畫緩動函數也是相同的道理。
有了這種函數關係,給定任意一個時間點,我們都能計算出對應的狀態值。OK,那如何在動畫中引入緩動函數呢?不說廢話,直接上代碼。
首先我們在core.js中創建了一個 類:
我們在構造函數中對實例調用 函數,對其初始化:將傳入的參數保存在實例屬性中。
當你看到 的時候可能不大明白:外界傳入的 到底是啥?其實 是一個數組,它的每一個元素都保存著獨立動畫的起始與結束兩種狀態。這樣說好像有點亂,舉個栗子好了:假設我們要創建一個動畫,讓頁面上的div同時往右、左分別平移300px、500px,此外還同時把自己放大1.5倍。在這個看似複雜的動畫過程中,其實可以拆解成三個獨立的動畫,每一動畫都有自己的起始與終止值:
對於往右平移,就是把css屬性的 的0px變成了300px
同理,往下平移,就是把 的0px變成500px
放大1.5倍,也就是把 從1變成1.5
因此傳入的value應該長成這樣: 。我們將數組的每一個元素依次保存在實例的value屬性中。
此外, 是由外界提供的渲染函數,即 ,它的作用是:動畫運動的每一幀,都會調用一次該函數,並把計算好的當前狀態值以參數形式傳入,有了當前狀態值,我們就可以自由地選擇渲染動畫的方式啦。
接下來我們給Core類添加一個循環函數:
的作用是:倘若當前時間進度 還未到終點,則根據當前時間進度計算出目標現在的狀態值,並以參數的形式傳給即將調用的渲染函數,即 ,並繼續循環。如果大於 ,則將目標的運動終止值傳給 ,運動結束,將狀態設為 。
代碼中的 是從tween.js文件引入的緩動函數,tween.js的代碼如下(網上搜搜基本都差不多= =):
最後,給 類增加 方法:
core.js的完整代碼如下:
在html中引入它後就可以愉快地調用啦^ _ ^
看到這裡,本文就差不多結束了,下節將介紹如何在項目中加入各類事件監聽及觸發方式。
本系列文章將會繼續不定期更新,歡迎各位大大指正^_^
回復「面試題」「ajax」等詞,可看文章;
其它功能正在完善,不定期更新....
覺得本文對你有幫助?請分享給更多人
關注「前端大學」,提升前端技能
TAG:IT程序員 |