做煤的網(wǎng)站app網(wǎng)站需要怎么優(yōu)化比較好
前端動畫
一、css動畫
transition
過渡
transition:transiton-property,transition-duration,transition-timing-function,transition-delay
相關(guān)屬性說明
屬性 | 默認(rèn)值 | 其他說明 |
---|---|---|
property過渡的屬性 | all | 不是所有css屬性都支持過渡 |
duration動畫完成時間 | 0s | 單位是秒 |
timing-function | ease | linear ease ease-in ease-out step-start step-end |
delay動畫開始時間 | 0s | 出發(fā)過渡后多久開始實現(xiàn)過渡 |
.transition-box {width: 100px;height: 200px;background-color: pink;transition: all 1s ease 1s;
}.transition-box:hover {width: 150px;background-color: skyblue;
}
transition的優(yōu)點在于簡單易用,但是它有幾個很大的局限。
(1)transition需要事件觸發(fā),所以沒法在網(wǎng)頁加載時自動發(fā)生。
(2)transition是一次性的,不能重復(fù)發(fā)生,除非一再觸發(fā)。
(3)transition只能定義開始狀態(tài)和結(jié)束狀態(tài),不能定義中間狀態(tài),也就是說只有兩個狀態(tài)。
(4)一條transition規(guī)則,只能定義一個屬性的變化,不能涉及多個屬性。
transition需要明確知道,開始狀態(tài)和結(jié)束狀態(tài)的具體數(shù)值,才能計算出中間狀態(tài)。transition沒法算出0px到auto的中間狀態(tài),也就是說,如果開始或結(jié)束的設(shè)置是height: auto,max-height等,那么就不會產(chǎn)生動畫效果。類似的情況還有,display: none到block
animation
屬性 | 說明 | 其他 |
---|---|---|
animation-name | 動畫名 | |
animation-duration | 動畫執(zhí)行一次的時長 | 可以時秒也可以毫秒,但是必須帶單位 |
animation-timing-function | 動畫執(zhí)行在不同階段的快慢 | linear/ease…… |
animation-delay | 延遲多久開始 | |
animation-iteration-count | 動畫執(zhí)行的次數(shù) | 可以是小數(shù) |
animatioin-derection | 動畫播放方向 | normal循環(huán)播放時每次都是正向/reverse正到反再到正/alternat正反交替e/alternate-reverse |
animation-fill-mode | 動畫在執(zhí)行之前和之后如何將樣式應(yīng)用于其目標(biāo) | |
animation-play-state | paused/running 動畫是暫停還是播放 | 恢復(fù)暫停的動畫將從暫停時停止的位置開始播放,而不是從動畫序列的開頭重新開始播放 |
transform
只能轉(zhuǎn)換由和模型定位的元素
屬性 | 說明 | |
---|---|---|
translate(10,20) | 往x軸(右)平移10px,往y軸(下)平移20px | |
scale(1.5) | 放大1.5倍 | |
rotate(90deg) | 旋轉(zhuǎn)90度 | |
skew | 傾斜 | |
translate3d | ||
scale3d | ||
rotate3d | ||
perspective | 設(shè)置視角 |
transform-origin:元素變形的起點
默認(rèn)值是元素的中心
它的值的類型可以值百分比、px、center/left/right/top/bottom這些
二、js動畫
setTimeout()、setInterval()
可以通過setTimeout、setInterval修改元素的css位置信息,修改canvas畫出來的東西等
js配合canvas實現(xiàn)動畫:
<canvas id="canvas" width="300" height="300"></canvas>
地球公轉(zhuǎn)動畫:
const sun = new Image();const earth = new Image();function init() {sun.src = "./img/sun.jpg";earth.src = "./img/eartH.jpg";}function draw() {const ctx = document.getElementById("canvas").getContext("2d");ctx.globalCompositeOperation = "destination-over";ctx.clearRect(0, 0, 300, 300); // 清除畫布ctx.save();ctx.translate(150, 150);// 地球const time = new Date();ctx.rotate(((2 * Math.PI) / 60) * time.getSeconds() +((2 * Math.PI) / 60000) * time.getMilliseconds());ctx.translate(105, 0);ctx.fillRect(0, -12, 40, 24); // 陰影ctx.drawImage(earth, -12, -12);ctx.restore();ctx.beginPath();ctx.arc(150, 150, 105, 0, Math.PI * 2, false); // 地球軌道ctx.stroke();ctx.drawImage(sun, 0, 0, 300, 300);}init();setInterval(() => {draw();}, 300);
requestAnimationFrame()
**作用:**告訴瀏覽器你要執(zhí)行動畫,瀏覽器在下一次重繪之前調(diào)用你傳入的回調(diào)函數(shù)來更新動畫
回調(diào)函數(shù)執(zhí)行次數(shù)通常是每秒 60 次,但在大多數(shù)遵循 W3C 建議的瀏覽器中,回調(diào)函數(shù)執(zhí)行次數(shù)通常與瀏覽器屏幕刷新次數(shù)相匹配
調(diào)用一次requestAnimationFrame()只會執(zhí)行一次回調(diào),若你想在瀏覽器下次重繪之前繼續(xù)更新下一幀動畫,那么回調(diào)函數(shù)自身必須再次調(diào)requestAnimationFrame()
語法:
requestAnimationFrame(callback)
參數(shù)callback:
當(dāng)你的動畫需要更新時,為下一次重繪所調(diào)用的函數(shù);該函數(shù)會傳入一個參數(shù),參數(shù)代表該函數(shù)開始執(zhí)行的時刻
返回值:
一個 long
整數(shù),請求 ID ,是回調(diào)列表中唯一的標(biāo)識。是個非零值,沒別的意義;每執(zhí)行一次就加1
window.cancelAnimationFrame()
終止動畫,終止執(zhí)行
requestAnimationFrame(callback)
動畫應(yīng)用
實現(xiàn)假進度條
loadFakeProgress() {// let preTime = 0;let timer = 0;const vm = this;function timerFun(timestamp) {if (vm.percentage === 100) {cancelAnimationFrame(timerFun);return;}// if (timestamp - preTime < 2000) {// requestAnimationFrame(timerFun);// return;// }// preTime = timestamp;timer = Math.round((timer + 0.01) * 100) / 100;let per = vm.percentage + Math.ceil(Math.random() * 10);requestAnimationFrame(timerFun);// 1》進度條達到了百分之90,不會更新進度條// 2》減慢進度條變化速度;每次調(diào)用timer都會增加0.01,就是調(diào)用了一百次動畫回調(diào)才會更新一次// timestamp - preTime和timer都可以控制進度條變化一次的時間;if (per >= 90 || timer % 1 !== 0) {return;}// if (per >= 90) {// return;// }vm.percentage = per < 85 ? per : 99;}requestAnimationFrame(timerFun);}
requestAnimationFrame做動畫相比比定時器的優(yōu)勢
定時器動畫可能會出現(xiàn)卡頓,而requestAnimationFrame比較穩(wěn)定、順暢
定時器為什么卡頓:普通顯示器刷新頻率是60Hz,一秒鐘刷新60次,也就是十多毫秒刷新一次,也就是如果動畫能動卡在約17毫秒執(zhí)行一次,就不會卡頓;但是定時器是一個異步任務(wù),它受到其他宏任務(wù)和微任務(wù)的影響,比如某次執(zhí)行時中間前面有大量微任務(wù)導(dǎo)致到了17秒后并沒有執(zhí)行,到了刷新,整個動畫沒變,經(jīng)過很多次刷新,整個過程動畫可能出現(xiàn)一會變,一會不變,就會出現(xiàn)抖動
而requestAnimationFrame的回調(diào)函數(shù)能夠在瀏覽器下一次重回之前執(zhí)行,所以不會出現(xiàn)卡頓,更順暢
svg動畫
元素
attributeName:變量屬性的屬性名
from:變動的初始值
to:結(jié)束值
dur:動畫持續(xù)的時間
<svg width="300" height="100"><title>Attribute Animation with SMIL</title><rect x="0" y="0" width="300" height="100" stroke="black" stroke-width="1" /><circle cx="0" cy="50" r="15" fill="blue" stroke="black" stroke-width="1"><animateattributeName="cx"from="0"to="500"dur="5s"repeatCount="indefinite" /></circle>
</svg>
元素
用于變動 transform 屬性
<svg width="300" height="100"><title>SVG SMIL Animate with transform</title><rect x="0" y="0" width="300" height="100" stroke="black" stroke-width="1" /><rectx="0"y="50"width="15"height="34"fill="blue"stroke="black"stroke-width="1"><animateTransformattributeName="transform"begin="0s"dur="20s"type="rotate"from="0 60 60"to="360 100 60"repeatCount="indefinite" /></rect>
</svg>