国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

前端每日實(shí)戰(zhàn) 168# 視頻演示如何利用 Web Animation API 制作一個(gè)切換英語單詞的

appetizerio / 2418人閱讀

摘要:眨眼動(dòng)畫和字符切換動(dòng)畫都是用實(shí)現(xiàn)的。三獲得下一個(gè)單詞接下來寫一點(diǎn)業(yè)務(wù)邏輯,用于隨機(jī)取出一個(gè)單詞。在點(diǎn)擊事件中調(diào)用上面的函數(shù),把結(jié)果存入一個(gè)名為的變量中第步獲得下一個(gè)單詞第步字符切換動(dòng)畫四字符切換動(dòng)畫該制作字符切換動(dòng)畫了。

效果預(yù)覽

按下右側(cè)的“點(diǎn)擊預(yù)覽”按鈕可以在當(dāng)前頁面預(yù)覽,點(diǎn)擊鏈接可以全屏預(yù)覽。

https://codepen.io/comehope/pen/byabeG

可交互視頻

此視頻是可以交互的,你可以隨時(shí)暫停視頻,編輯視頻中的代碼。

請(qǐng)用 chrome, safari, edge 打開觀看。

https://scrimba.com/p/pEgDAM/cevPbkfB

(因?yàn)?scrimba 不支持 web animation api,所以動(dòng)畫效果在視頻播放過程中看不到,不過你可以隨時(shí)暫停視頻,手工刷新預(yù)覽窗口查看動(dòng)畫效果)

源代碼下載

每日前端實(shí)戰(zhàn)系列的全部源代碼請(qǐng)從 github 下載:

https://github.com/comehope/front-end-daily-challenges

代碼解讀

本作品用于展示若干包含字母組合 OO 的單詞,每點(diǎn)擊一下,OO 就眨眨眼,同時(shí)更換一個(gè)單詞。

整體開發(fā)過程分成 4 步,第 1 步用 CSS 實(shí)現(xiàn)頁面的靜態(tài)布局,后面 3 步用 JS 實(shí)現(xiàn)動(dòng)畫和業(yè)務(wù)邏輯。第 2 步實(shí)現(xiàn)單詞中間字母 OO 的眨眼效果,第 3 步實(shí)現(xiàn)隨機(jī)取單詞的邏輯,第 4 步實(shí)現(xiàn)字符的切換動(dòng)畫。

眨眼動(dòng)畫和字符切換動(dòng)畫都是用 Web Animation API 實(shí)現(xiàn)的。雖然用 JS 寫動(dòng)畫比用 CSS 要麻煩一些,但 API 提供了一些事件 handler,在字符切換動(dòng)畫中就是利用事件機(jī)制來精確控制動(dòng)畫和在動(dòng)畫過程中加入業(yè)務(wù)邏輯的。

下面開始編碼。

一、靜態(tài)布局:dom,css

dom 結(jié)構(gòu)很簡單,一個(gè)名為 .word

元素中包含了 4 個(gè) 子元素,每個(gè)子元素容納一個(gè)字符:

b o o k

令頁面中的元素居中,設(shè)置頁面背景色為青藍(lán)色:

body {
    margin: 0;
    height: 100vh;
    display: flex;
    align-items: center;
    justify-content: center;
    background-color: steelblue;
}

設(shè)置單詞的樣式,麻布色,大字號(hào),大寫:

.word {
    font-size: 100px;
    color: linen;
    font-family: monospace;
    font-weight: bold;
    display: flex;
    text-transform: uppercase;
    cursor: pointer;
    user-select: none;
}

讓單詞兩端的 2 個(gè)字符變?yōu)榉凵?/p>

.word span:first-child,
.word span:last-child {
    color: pink;
}

用徑向漸變給單詞中間的 OO 加上眼珠:

.word span:not(:first-child):not(:last-child) {
    background-image: radial-gradient(
        circle at center,
        linen 0.05em,
        transparent 0.05em
    );
}

至此,靜態(tài)布局完成。

二、眨眼動(dòng)畫

.word 元素創(chuàng)建一個(gè)單擊事件函數(shù),每當(dāng)點(diǎn)擊發(fā)生時(shí),就先讓中間的 OO 眨眼,然后獲得下一個(gè)要顯示的單詞,再把當(dāng)前的單詞換成新的單詞:

document.querySelector(".word").onclick = function() {
    //第1步:眨眼動(dòng)畫
    //第2步:獲得下一個(gè)單詞
    //第3步:字符切換動(dòng)畫
}

先來實(shí)現(xiàn)第1步-眨眼動(dòng)畫。在此之前了解一下 Web Animation API 的語法,下面是一個(gè)簡單的示例:

let keyframes = [
    {transform: "scaleY(1)"},
    {transform: "scaleY(0.1)"},
]
let options = {
    duration: 200,
    iterations: 2,
}
element.animate(keyframes, options)

animate() 方法接收 2 個(gè)參數(shù),第 1 個(gè)參數(shù)是一個(gè)數(shù)組,用于定義關(guān)鍵幀;第 2 個(gè)參數(shù)是一個(gè)對(duì)象,用于定義動(dòng)畫屬性,它們分別對(duì)應(yīng)著 CSS 中的 @keyframes 語句和 animation 屬性。上面的 JS 代碼等價(jià)于以下 CSS 代碼:

@keyframes anim {
    from {
        transform: scaleY(1);
    }

    to {
        transform: scaleY(0);
    }
}

.element {
    animation-name: anim;
    animation-duration: 200ms;
    animation-iteration-count: 2;
}

好了,我們來正式寫眨眼動(dòng)畫:

function blinkEyes() {
    let eyes = document.querySelectorAll(".word span:not(:first-child):not(:last-child)")
    let keyframes = [
        {transform: "scaleY(1)", offset: 0},
        {transform: "scaleY(0.1)", offset: 0.25},
        {transform: "scaleY(1)", offset: 0.5},
        {transform: "scaleY(1)", offset: 1},
    ]
    let options = {
        duration: 200,
        iterations: 2,
    }
    eyes.forEach(eye => eye.animate(keyframes, options))
}

上面代碼中的 offset@keyframes 中為每一幀指定的百分比值。這段動(dòng)畫的意思是每次動(dòng)畫眨眼 2 次,每次眨眼用時(shí) 200ms,這 200ms 的前 50% 時(shí)間(即前 100ms)做眨眼動(dòng)作,后 50% 時(shí)間等待,這樣設(shè)計(jì)的目的是在 2 次眨眼之間插入 100ms 的間隔。

然后,在點(diǎn)擊事件里調(diào)用上面的方法:

document.querySelector(".word").onclick = function() {
    //第1步:眨眼動(dòng)畫
    blinkEyes()

    //第2步:獲得下一個(gè)單詞
    //第3步:字符切換動(dòng)畫
}

至此,當(dāng)用鼠標(biāo)點(diǎn)擊文字時(shí),OO 就會(huì)眨動(dòng)。

三、獲得下一個(gè)單詞

接下來寫一點(diǎn)業(yè)務(wù)邏輯,用于隨機(jī)取出一個(gè)單詞。

引入 lodash 庫:

定義一個(gè)名為 Word 的類:

function Word() {
    const WORDS = ["book", "boot", "cook", "cool", "door", "food", "fool", "foot", "good", "look", "loop", "moon", "noon", "pool", "poor", "room", "roof","root", "soon", "tool", "wood", "zoom",]
    let current = "book"
    this.getNext = () => {return current = _(WORDS).without(current).sample()}
}

Word 類有一個(gè)名為 getNext() 的方法,用于從預(yù)設(shè)的數(shù)組中隨機(jī)取出一個(gè)單詞,可以用下面的代碼測(cè)試一下效果,會(huì)輸出類似 food 這樣的單詞:

let word = new Word()
console.log(word.getNext())

因?yàn)榻酉聛淼膭?dòng)畫只涉及單詞左右兩側(cè)的字母,所以在 getNext() 方法中再把兩端的字符拆出來,返回一個(gè)對(duì)象:

function Word() {
    const WORDS = ["book", "boot", "cook", "cool", "door", "food", "fool", "foot", "good", "look", "loop", "moon", "noon", "pool", "poor", "room", "roof","root", "soon", "tool", "wood", "zoom",]
    let current = "book"
    this.getNext = () => {
        current = _(WORDS).without(current).sample()
        return {
            first: current.slice(0, 1),
            last: current.slice(-1)
        }
    }
}

再測(cè)試一下效果,輸出結(jié)果會(huì)變?yōu)轭愃?{first: "f", last: "d"} 的對(duì)象。

在點(diǎn)擊事件中調(diào)用上面的函數(shù),把結(jié)果存入一個(gè)名為 chars 的變量中:

let word = new Word()

document.querySelector(".word").onclick = function() {
    //step 1: eyes blink animation
    blinkEyes()

    //第2步:獲得下一個(gè)單詞
    let chars = word.getNext()

    //第3步:字符切換動(dòng)畫
}
四、字符切換動(dòng)畫

該制作字符切換動(dòng)畫了。

函數(shù)的聲明如下,函數(shù)名為 switchChar,它接收 2 個(gè)參數(shù),第 1 個(gè)參數(shù)表示對(duì)哪個(gè)字符執(zhí)行動(dòng)畫,值為 firstlast,第 2 個(gè)參數(shù)是將被替換成的新字符:

function switchChar(which, char) {}

這樣來調(diào)用:

switchChar("first", "f")

先實(shí)現(xiàn)更換邏輯,不包含動(dòng)畫效果:

function switchChar(which, char) {
    let letter = {
        first: {
            dom: document.querySelector(".word span:first-child"),
        },
        last: {
            dom: document.querySelector(".word span:last-child"),
        }
    }[which]

    letter.dom.textContent = char
}

在點(diǎn)擊事件中調(diào)用 switchChar 函數(shù):

document.querySelector(".word").onclick = function() {
    //step 1: eyes blink animation
    blinkEyes()

    //第2步:獲得下一個(gè)單詞
    let chars = word.getNext()

    //第3步:字符切換動(dòng)畫
    Object.keys(chars).forEach(key => switchChar(key, chars[key]))
}

現(xiàn)在運(yùn)行程序的話,在每次點(diǎn)擊之后,單詞兩側(cè)的字符都會(huì)更新。

接下來寫動(dòng)畫效果,方法和寫眨眼動(dòng)畫類似。這里有兩點(diǎn)要說明,一是因?yàn)橛?firstlast 2 個(gè)字符、又有入場(chǎng)、出場(chǎng) 2 個(gè)動(dòng)畫,所以實(shí)際上一共實(shí)現(xiàn)了 4 個(gè)動(dòng)畫效果;二是動(dòng)畫的流程是先讓舊字符出場(chǎng),再讓新字符入場(chǎng),而更換字符的操作放置在這 2 個(gè)動(dòng)畫中間,這是用動(dòng)畫 API 的 onfinish 事件實(shí)現(xiàn)的:

function switchChar(which, char) {
    let letter = {
        first: {
            dom: document.querySelector(".word span:first-child"),
            to: "-0.5em",
            from: "0.8em",
        },
        last: {
            dom: document.querySelector(".word span:last-child"),
            to: "0.5em",
            from: "-0.8em",
        }
    }[which]

    let keyframes = {
        out: [
            {transform: `translateX(0)`, filter: "opacity(1)"},
            {transform: `translateX(${letter.to})`, filter: "opacity(0)"},
        ],
        in: [
            {transform: `translateX(${letter.from})`, filter: "opacity(0)"},
            {transform: `translateX(0)`, filter: "opacity(1)"},
        ]
    }

    let options = {
        duration: 500,
        fill: "forwards",
        easing: "cubic-bezier(0.5, 1.5, 0.5, 1.5)"
    }

    letter.dom
        .animate(keyframes.out, options)
        .onfinish = function() {
            letter.dom.animate(keyframes.in, options)
            letter.dom.textContent = char
        }
}

至此,全部編碼完成。解讀 JS 代碼和解讀 CSS 代碼不一樣,因?yàn)椴皇敲恳恍写a都有視覺效果,很難用語言描述。如果你有不理解的地方,一定是我沒有講清楚,那么請(qǐng)你多看幾遍視頻,仔細(xì)體會(huì)。

在前端每日實(shí)戰(zhàn)的第 162 號(hào)作品中也曾使用過 Web Animation API,但那個(gè)作品的業(yè)務(wù)邏輯比這個(gè)要復(fù)雜,你在理解了這個(gè)作品之后若還想再挑戰(zhàn)一下,可以再去參考它。

大功告成!

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/109767.html

相關(guān)文章

  • 前端每日實(shí)戰(zhàn) 168# 視頻演示如何利用 Web Animation API 制作一個(gè)切換英語單詞

    摘要:眨眼動(dòng)畫和字符切換動(dòng)畫都是用實(shí)現(xiàn)的。三獲得下一個(gè)單詞接下來寫一點(diǎn)業(yè)務(wù)邏輯,用于隨機(jī)取出一個(gè)單詞。在點(diǎn)擊事件中調(diào)用上面的函數(shù),把結(jié)果存入一個(gè)名為的變量中第步獲得下一個(gè)單詞第步字符切換動(dòng)畫四字符切換動(dòng)畫該制作字符切換動(dòng)畫了。 showImg(https://segmentfault.com/img/bVbs2j1?w=400&h=401); 效果預(yù)覽 按下右側(cè)的點(diǎn)擊預(yù)覽按鈕可以在當(dāng)前頁面預(yù)...

    Sike 評(píng)論0 收藏0
  • 前端每日實(shí)戰(zhàn) 2018年10月至2019年6月項(xiàng)目匯總(共 20 個(gè)項(xiàng)目)

    摘要:過往項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月份項(xiàng)目匯總共個(gè)項(xiàng)目年月至年月發(fā)布的項(xiàng)目前端每日實(shí)戰(zhàn)專欄每天分解一個(gè)前端項(xiàng)目,用視頻記錄編碼過程,再配合詳細(xì)的代碼解讀, 過往項(xiàng)目 2018 年 9 月份項(xiàng)目匯總(共 26 個(gè)項(xiàng)目) 2018 年 8 月份項(xiàng)目匯總(共 29 個(gè)項(xiàng)目) 2018 年 7 月份項(xiàng)目匯總(...

    muddyway 評(píng)論0 收藏0
  • 前端每日實(shí)戰(zhàn) 169# 視頻演示如何制作“數(shù)略詞”交互動(dòng)畫(內(nèi)含2個(gè)視頻

    摘要:本項(xiàng)目將制作一個(gè)交互動(dòng)畫效果,令其在單詞原詞和數(shù)略詞之間切換。二擴(kuò)展應(yīng)用到多個(gè)單詞數(shù)略詞有很多,為了能夠一次展示多個(gè)單詞,我們將對(duì)現(xiàn)有的程序進(jìn)行擴(kuò)展。 showImg(https://segmentfault.com/img/bVbtPjm?w=400&h=401); 效果預(yù)覽 按下右側(cè)的點(diǎn)擊預(yù)覽按鈕可以在當(dāng)前頁面預(yù)覽,點(diǎn)擊鏈接可以全屏預(yù)覽。 https://codepen.io/co...

    roland_reed 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

appetizerio

|高級(jí)講師

TA的文章

閱讀更多
最新活動(dòng)
閱讀需要支付1元查看
<