上一篇博客記錄了animation的介紹,這次記錄一下具體的使用。
1.再次觸發(fā)動畫
可以通過給元素添加類名來觸發(fā)animation動畫改抡,但是需要注意的是再次觸發(fā)的情況述召。
比如俘枫,如果想每次點擊鼠標都能重新觸發(fā)動畫,CSS和JS并沒有提供這種功能萧恕。我們能做的就是要先除去動畫的效果,然后讓文檔重新計算樣式肠阱,最后將動畫效果再次添加到元素上票唆。
假定有下面的頁面
// HTML:
<div class="box">
</div>
<div id="runButton">Click me to run the animation</div>
//CSS
.box {
width: 100px;
height: 100px;
border: 1px solid black;
}
@keyframes colorchange {
0% { background: yellow }
100% { background: blue }
}
.changing {
animation: colorchange 2s;
}
下面的代碼是無效的。
// JS
document.querySelector('#runButton').addEventListener('click',function(){
document.querySelector('.box').className = 'box';
document.querySelector('.box').className = 'box changing';
});
因為沒有實現(xiàn)<cite>先除去動畫的效果屹徘,然后讓文檔重新計算樣式走趋,最后將動畫再次添加到元素上的效果。
1.1 解決方法一
來自MDN
// JS
function play() {
document.querySelector(".box").className = "box";
window.requestAnimationFrame(function(time) {
window.requestAnimationFrame(function(time) {
document.querySelector(".box").className = "box changing";
});
});
}
document.querySelector("#runButton").addEventListener("click", play, false);
window.requestAniationFrame(callback)
方法告訴瀏覽器你要執(zhí)行一個動畫噪伊,并請求瀏覽器在重新繪繪制頁面之前執(zhí)行一個函數(shù)簿煌。
上面的代碼中,
-
document.querySelector(".box").className = "box";
是除去動畫的效果鉴吹。 - 第一個
window.requestAniationFrame
告訴瀏覽器我要執(zhí)行一個動畫姨伟,請求瀏覽器執(zhí)行該方法的參數(shù)所指定的函數(shù)。 - 瀏覽器執(zhí)行了這個參數(shù)所指定的方法豆励,告訴瀏覽器我又要執(zhí)行一個方法夺荒,希望瀏覽器在重新繪制頁面之前執(zhí)行另一個函數(shù),即
document.querySelector(".box").className = "box changing";
,
然后瀏覽器重新繪制了頁面。 - 最后執(zhí)行了
document.querySelector(".box").className = "box changing";
,
給.box
添加changing
類名技扼,將動畫效果再次添加到元素上伍玖。
綜上,就實現(xiàn)了再次觸發(fā)動畫的效果剿吻。
1.2 解決方法二
來自實踐所得窍箍。
// JS
function play() {
document.querySelector(".box").className = "box";
setTimeout(() => {
document.querySelector(".box").className = "box changing";
},0);
}
document.querySelector("#runButton").addEventListener("click", play, false);
原理還不清楚,可能跟異步代碼和瀏覽器的渲染規(guī)則有關(guān)系吧和橙,日后查清楚再來更新仔燕。
2.防止多次重復(fù)觸發(fā)動畫
有時候不希望每次點擊都讓動畫從頭開始,而是等動畫結(jié)束之后才能再次觸發(fā)魔招。
2.1 方法一
當(dāng)希望再次觸發(fā)動畫時晰搀,判斷有沒有應(yīng)用動畫的類名,沒有的話办斑,才再次觸發(fā)外恕。
// JS
function play() {
if($(".box").hasClass('changing')){return;}
setTimeout(() => {
$(".box").addClass = "changing";
},0);
}
document.querySelector("#runButton").addEventListener("click", play, false);
2.2 方法二
前面的方法是先除去含有動畫效果的類名,然后再添加類名以觸發(fā)動畫乡翅。
還可以先添加類名觸發(fā)動畫鳞疲,等動畫結(jié)束后再除去帶有動畫效果類名。
// JS
function play() {
if($(".box").hasClass('changing')){return;}
$(".box").addClass = "changing";
setTimeout(() => {
$(".box").removeClass = "changing";
},1000);
}
document.querySelector("#runButton").addEventListener("click", play, false);
缺點是需要確定動畫的時間蠕蚜,而且添加了異步代碼尚洽,好像這樣是不好的。