內容目錄
前言
GreenSock 動畫平台 (GSAP)是一個可以使用JS來控制CSS、SVG、React、canvas來製作動畫,解決瀏覽器不一致的問題,甚至比JQuery快20倍(他們官網這樣寫的)
GSAP是一個屬性操控器,讓動畫每秒更改多次屬性值,看起來就像是在移動、變色、旋轉…等,他會抓一個起始跟終點值,每秒更改60次,從技術上講,我們可以將 GSAP 命名為“GreenSock Property Manipulator”(GSPM)
安裝
NPM
npm install gsap
CDN
<script src = "https://cdnjs.cloudflare.com/ajax/libs/gsap/3.10.4/gsap.min.js" ></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.10.4/gsap.min.js"></script>
測試執行
同樣先簡單進行套件安裝的測試(CDN安裝),直接使用官網的範例,先設定三個正方形,分別為橘色、灰色、綠色,所有正方形會被右移300(x:300),標題變淡、綠色旋轉縮小
執行成功表示套件安裝成功
HTML
<head>
<link rel="stylesheet" href="https://codepen.io/GreenSock/pen/JGaKdQ.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.10.4/gsap.min.js"></script>
</head>
<body>
<h2 class="title">gsap.to() Basic Usage</h2>
<div class="box orange"></div>
<div class="box grey"></div>
<div class="box green"></div>
</body>
CSS
body {
margin: 10px;
}
.box {
display: block;
}
JS
gsap.to("h2.title", {duration: 1, opacity: 0.3});
gsap.to(".box", {duration: 2, x: 300});
gsap.to(".green", {duration: 3, rotation: 360, scale: 0.5});
認識gsap.to()
使用gsao.to來控制動畫有兩個參數
- 參數1:要控制的目標,直接使用選擇器選擇目標”.class”、”#id”
- 參數2:加入CSS動畫,以物件的方式表示。{duration: 1, x: 100}
※CSS的部分,有一些特殊屬性要注意
例:要讓id為logo的目標,在一秒內向右移動100
gsap.to("#logo", {duration: 1, x: 100});
特殊屬性
主要是一些動畫的屬性值的設置,以及一些可選的屬性,可以參照官網的介紹,這邊先列舉一些簡單的
官網:GreenSock | Docs | GSAP | Tween | vars
duration | 動畫的持續時間 |
delay | 動畫幾秒後開始 |
ease | 動畫期間的變化,有點像是速率不同的概念,至於需要什麼速度,可以直接使用官網的設定GreenSock | Docs | Eases |
id | 分配一個ID給你設定的目標,於後面tween 中,可以使用gsap.getById()捕捉到他 |
repeat | 動畫重複次數,預設0,當設定1會跑兩次 |
repeatDelay | 每次動畫間隔的”秒數”,預設0 |
keyframes | 關鍵偵動畫,可以將目標設定為不同狀態的動畫,例如keyframes: [{x:100, duration:1}, {y:100, duration:0.5}] |
上面例子改編:
我們把box改成,需要重複11次,一開始為一秒後跑一秒右100,在接3秒後跑0.5秒下100
gsap.to(".box", {repeat:10 ,keyframes: [{x:100, duration:1,delay : 1}, {y:100, duration:0.5 ,delay : 3}]});
callbacks
其實也是一種特殊屬性,只是他可以塞入一些方法在特殊時間點,像是生命週期一般
onComplete | 動畫完成時調用。 |
onStart | 動畫開始時調用 |
onUpdate | 每次動畫更新時調用(在動畫處於活動狀態時的每一幀)。 |
onRepeat | 每次動畫重複時調用。 |
onReverseComplete | 當動畫在反轉時再次到達其開始時調用。 |
以開始跟結束這兩個callback來做範例,就是在結束跟開始時顯示console,那兩種寫法都可以,看自己程式習慣
gsap.to(".box", {duration: 2, x: 300 ,onComplete:()=>{console.log('動畫完成')} ,onStart: boxStart() });
function boxStart(){
console.log('動畫開始')
}
gsap.from()
基本上就是跟gsap.to()完全相反,gsap.to()從原本你設定的HTML出發,到你動畫最終跑的位置。而gsap.from()從動畫開始位置出發,到你原本設置HTML的位置
以上面例子為例把gsap.to改為gsap.from(),就會從原本的由左至右,改為由右至左
gsap.from("h2.title", {duration: 1, opacity: 0.3});
gsap.from(".box", {duration: 2, x: 300});
gsap.from(".green", {duration: 3, rotation: 360, scale: 0.5});
gsap.fromTo()
知道前面兩個,就知道fromTo()是設定起始跟終點動畫,方便用於完全控制
有三個參數,基本跟from還有To差不多:
- 參數1:要控制的目標,直接使用選擇器選擇目標”.class”、”#id”
- 參數2:加入CSS動畫設置”起點”動畫
- 參數3:加入CSS動畫設置”終點”動畫
範例
把box改為,開始為透明,Y100,X0,動畫結束是,五秒後,不透明,往右300:往上100
gsap.fromTo(".box", {autoAlpha: 0,y: 100,x: 0}, {autoAlpha: 1, duration: 5,x: 300,y:0});
gsap.set()
立即修改CSS屬性,在動畫開始前就會改變
參數1:要控制的目標,直接使用選擇器選擇目標”.class”、”#id”
參數2:加入CSS設置
控制動畫
前面都是讓動畫單純的跑完,現在加入一些簡單控制的方法,先把動畫實例給儲存,接下來就可以控制了
var tween = gsap.to("#logo", {duration: 1, x: 100});
tween.pause()
pause() | 暫停 |
resume() | 恢復 |
restart() | 重新,並撥放 |
seek(0.5) | 跳到 0.5 秒 |
progress(0.25) | 跳轉進度的 1/4 |
timeScale(0.5) | 變為半速 |
timeScale(2) | 變為雙倍速度 |
kill() | 刪除動畫 |
play() | 正常走 |
reverse(); | 反轉走 |
timeline時間線
開始進入相對複雜的階段,以上範例都是一個動畫一次撥完,如果要同時控制多個動畫為一組
使用時機為
- 一組動畫做為一整個整體控制
- 建構一個序列,(前面動畫時間可以接續後續動畫)
- 模組化動畫程式碼
- 可以做很複雜的排程
直接看範例,將上面的範例修改為由時間線控制,重複30次,相隔一秒,並由綠色>橘色>灰色相繼產生動畫,做完一個才會進行下一個
var tl = gsap.timeline({repeat: 30, repeatDelay: 1});
//add 3 tweens that will play in direct succession.
tl.to(".green", {duration: 1, x: 200});
tl.to(".orange", {duration: 1, x: 200, scale: 0.2});
tl.to(".grey", {duration: 1, x: 200, scale: 2, y: 20});
timeline設定
先創造一個 gsap.timeline()實例後,並儲存起來,參數可以設定一些初始的特殊屬性
var tl = gsap.timeline();
也可以調用.to、.from()跟fromTo()的方法,只要使用add就好。
範例中,可以看到to的寫法有沒有加add都是一樣的m。如果要使用到from或是fromTo就要使用add
var tl = gsap.timeline();
//下面兩種寫法相同
tl.add( gsap.to("#id", {duration: 2, x: 100}) );
tl.to("#id", {duration: 2, x: 100});
//from跟fromTo就要使用add
tl.add( gsap.from("#id", {duration: 2, x: 100}) );
方法鏈
根據上面範例,就看你要寫成一條,還是分行都可以
var tl = gsap.timeline({repeat: 30, repeatDelay: 1});
//一條
tl.to(".green", {duration: 1, x: 200}).to(".green", {duration: 1, x: 200}).to(".orange", {duration: 1, x: 200, scale: 0.2})
//多行
tl.to(".green", {duration: 1, x: 200});
tl.to(".orange", {duration: 1, x: 200, scale: 0.2});
tl.to(".grey", {duration: 1, x: 200, scale: 2, y: 20});
Timeline Defaults(默認值)
如果你接下來動畫有相同屬性的東西,可以直接用defaults來讓所有的時間線內的動畫都有這個屬性,比如,動畫時序時間都要一秒
這樣默認時間線內的三個動畫都為一秒,如果要覆蓋掉,直接在該行的屬性內修改即可覆蓋,比如就orange自己是三秒
var tl = gsap.timeline({defaults: {duration: 1}});
tl.to(".green", {x: 200})
.to(".orange", {x: 200, scale: 0.2,duration: 3})
.to(".grey", {x: 200, scale: 2, y: 20});
時間線特殊屬性
可以控制一整組動畫的屬性,像是次數、相隔時間…等
repeat | 動畫重複次數 |
repeatDelay | (一整組)動畫之間的相隔時間 |
yoyo | 向前向後交替 |
delay | 在開始之前的時間 |
onComplete | 撥完之後調用的函數 |
var tl = gsap.timeline({defaults: {duration: 5},repeat:10 ,yoyo:true });
時間線的方法
有點像是電視遙控器的概念,控制整組動畫的快慢、撥放進度,播放位置
restart() | 從頭播放 |
time() | 到指定時間(以秒為單位) |
progress() | 把整組動畫分為0~1,0.5代表動畫一半,0開頭,1結束 |
duration() | 修改整組動畫的持續時間 |
delay() | 在開始之前的時間 |
var tl = gsap.timeline({defaults: {duration: 5},repeat:10 });
tl.duration(1)
結論
在學習GreenSock的過程中,發現他是一個很用心的套件,內容一直都有在翻新,所以會看到很多版本的用法,越新的版本就越簡單操控,但我也沒有時間將全部都學習完,最主要的目標是要將動畫加上移動路徑,並且由下拉scroll來控制,下一部份將透過scroll magic跟GreenSock來達成這個功能(但實際後續發現GreenSock就能做到了)