TheaterJS:模仿人類打字效果的 JavaScript 動畫特效

TheaterJS是一個用于模擬人輸入行為的JS庫宪卿。
下面是一個簡單完整的Demo畜埋,模擬了兩個角色(Vader缆瓣、luke)的對話翻伺,可以打開看一下運行效果和代碼材泄,然后復(fù)制代碼到自己的項目中,試一試吨岭。
https://codepen.io/Zhouzi/pen/JoRazP

首先進(jìn)行準(zhǔn)備工作:

1拉宗、安裝依賴npm install theaterjs
2、在你要寫代碼的頁面引入theaterjs插件import theaterJS from 'theaterjs'

接下來開始看一下代碼:

HTML:

<div class="body">
    <main class="scene">
      <!-- 此處有兩個角色辣辫,vader和luke -->
      <div class="actor">
        <div class="actor__prefix">-</div>
        <div id="vader" class="actor__content"></div>
      </div>
      <div class="actor">
        <div class="actor__prefix">-</div>
        <div id="luke" class="actor__content"></div>
      </div>
    </main>
  </div>

CSS:(只有一部分)

.dark {
  color: $color-white;
  background-color: $color-black;
}
.actor__content--typing::after {//添加打字和刪除時的光標(biāo)
  content: '|';
  animation: blink 500ms infinite;
}

JS:

mounted(){
    //1,初始化一個theaterJS對象
    var theater = theaterJS()    
    //2,將演員添加到選角中旦事。
    theater
      .addActor('vader', { speed: 0.8, accuracy: 0.6 })
      .addActor('luke')
    //3,將場景添加到場景中,options.autoplay為true急灭,則播放場景姐浮。
    theater
      .addScene('vader:Luke.', 600)
      .addScene('luke:What?', 400)
      .addScene('vader:I am your father.', 400)
      .addScene('luke:Nooo...', -3, '!!! ', 600, 'No! ', 600)
      .addScene('luke:That\'s not true!', 600)
      .addScene('luke:That\'s impossible!', 400)
      .addScene('vader:Search your feelings.', 1600)
      .addScene('vader:You know it to be true.', 1000)
      .addScene('luke:Noooooooo! ', 600, 'No!', 400)
      .addScene('vader:Luke.', 600)
      .addScene('vader:You can destroy the Emperor.', 1600)
      .addScene('vader:He has foreseen this. ', 800)
      .addScene('vader:It is your destiny.', 1600)
      .addScene('vader:Join me.', 800)
      .addScene('vader:Together we can rule the galaxy.', 800)
      .addScene('vader:As father and son.', 1600)
      .addScene('vader:Come with me. ', 800)
      .addScene('vader:It is the only way.', 2000)
      .addScene(theater.replay.bind(theater))
    //4,添加在發(fā)出事件時執(zhí)行的回調(diào)( ( 當(dāng)場景開始/結(jié)束時葬馋、) )卖鲤。
    //效果是當(dāng)打字(type)和刪除(erase)開始時肾扰,顯示光標(biāo)
    //當(dāng)打字(type)和刪除(erase)結(jié)束時,移除光標(biāo)蛋逾。
    //當(dāng)vader打字(type)時白对,
    theater
      .on('type:start, erase:start', function () {
        theater.getCurrentActor().$element.classList.add('actor__content--typing')
      })
      .on('type:end, erase:end', function () {
        theater.getCurrentActor().$element.classList.remove('actor__content--typing')
      })
      .on('type:start, erase:start', function () {
        if (theater.getCurrentActor().name === 'vader') {
          document.body.classList.add('dark')
        } else {
          document.body.classList.remove('dark')
        }
      })
  },
先來了解幾個單詞的意思:

theater:戲劇换怖;
type:打字甩恼;
erase:清除;

1沉颂、TheaterJS

需要提供一些選項來創(chuàng)建一個新的TheaterJS對象条摸。
var theater = theaterJS(<options>)
參數(shù)默認(rèn)描述{autoplay, locale, minSpeed, maxSpeed}

選項 默認(rèn) 描述
autoplay true 如果為true,則自動播放場景(調(diào)用addScene時)
locale detect 確定在鍵入隨機字符(錯誤)時使用哪個鍵盤铸屉。注意:"detect"是一種檢測用戶的語言環(huán)境并在受支持的情況下使用的選項钉蒲。
minSpeed {erase:80, type: 80 } 每個鍵入字符之間的最小延遲(越低,速度越快)彻坛。
maxSpeed {erase:450, type: 450 } 每個鍵入的字符之間的最大延遲(越大顷啼,越慢)。
注意:obj1等效于obj2昌屉。
let obj1 = {
  "minSpeed ":80钙蒙,
  "maxSpeed":450 
}
let obj2 = {
   "minSpeed ":{
     "erase":80,
     "type":80
  },
  
  "maxSpeed"::{
     "erase": 450间驮,
     "type": 450
  }
}
TheaterJS對象具有兩個公共(只讀)屬性:

theater.options:對象的選項躬厌。
theater.status:對象的狀態(tài)(“正在播放”,“正在停止”或“準(zhǔn)備就緒”)竞帽。

2扛施、addActor

將演員添加到演員表中。

theater.addActor(<name>, <options>, <callback>)

參數(shù)默認(rèn)描述

參數(shù) 默認(rèn) 描述
name 用于標(biāo)識角色的名稱
options 0.8 accuracy (0到1之間的數(shù)字):用來決定演員犯錯誤的頻率屹篓。speed (0到1之間的數(shù)字):用于確定actor打字的速度疙渣。
callback 角色的顯示值更改時調(diào)用的函數(shù)。

注意:actor回調(diào)是在設(shè)置其顯示值時調(diào)用的函數(shù)堆巧。它也可以是字符串妄荔,在這種情況下,TheaterJS將假定它是DOM選擇器并查找相應(yīng)的元素恳邀。然后懦冰,當(dāng)值更改時灶轰,將設(shè)置元素的innerHTML谣沸。如果為目標(biāo)元素指定了具有參與者名稱的id,則可以放心地忽略此參數(shù)笋颤。

theater.addActor('vader')
//在這種情況下乳附,TheaterJS將查找 #vader 元素的元素内地。 另外,當(dāng)使用選擇器字符串時赋除,actor將有一個引用DOM元素的附加 $element 屬性阱缓。

3、addScene

將場景添加到場景中举农,如果 options.autoplay 為 true荆针,則播放場景。

theater.addScene(<scene>)

<scene>有五種類型

theater
.addScene('vader:Luke...') //擦除演員顯示值的當(dāng)前值颁糟,然后鍵入新值航背。
.addScene(800) //在播放下一個場景之前,先中斷800毫秒棱貌。
.addScene('I am your father!') //將值追加到參與者值的當(dāng)前顯示玖媚。
.addScene(-7) //擦除7字符。
.addScene(fn) //調(diào)用fn婚脱,它接收完成的回調(diào)作為第一個參數(shù)( 調(diào)用 done() 將播放場景中的下一個場景)今魔。

注意,addScene實際上接受了無限數(shù)量的參數(shù)障贸,因此你可以執(zhí)行以下操作:

theater
. addScene('vader:Luke... ', 800, 'I am your father!')
. addScene(-7, 'mother!')
. addScene(fn)

4错森、監(jiān)聽事件

添加在發(fā)出事件時執(zhí)行的回調(diào)( ( 當(dāng)場景開始/結(jié)束時的比如 ) )。

theater.on(<eventName>, <callback>)

例子:

theater
      .on('type:start, erase:start', function () {
        theater.getCurrentActor().$element.classList.add('actor__content--typing')
      })
      .on('type:end, erase:end', function () {
        theater.getCurrentActor().$element.classList.remove('actor__content--typing')
      })
      .on('type:start, erase:start', function () {
        if (theater.getCurrentActor().name === 'vader') {
          document.body.classList.add('dark')
        } else {
          document.body.classList.remove('dark')
        }
      })

參數(shù)默認(rèn)描述

參數(shù) 描述
eventName 要偵聽的事件的NAME
Callback 事件發(fā)布時調(diào)用的函數(shù)篮洁,回調(diào)函數(shù)將事件的NAME 作為第一個參數(shù)接收 问词。

注意:
通過使用快捷方式來偵聽所有事件: theater.on('*', callback)。
事件在序列啟動( sequence:start ) 并結(jié)束( sequence:end )嘀粱。
比如 時發(fā)出 theater.addScene('vader:Luke.', 'vader:I am your father.') 是一個序列激挪。
當(dāng)方案開始和結(jié)束時,分別為 scenario:start 和 scenario:end 發(fā)出事件锋叨。
場景是 :end 事件偵聽器中的stoppable垄分。 表示在偵聽場景 :end的回調(diào)內(nèi)調(diào)用 theater.stop() 將停止場景。 這對于異步回調(diào)(娃磺。比如 動畫) 非常有用薄湿。

5、播放

theater.play()

例子:

var theater =theaterJS({ autoplay:false })
theater
. addActor('vader')
.addScene('vader:Luke...')
document.querySelector('button').addEventListener('click', function () {
 theater.play()
}, false)

6偷卧、重播

theater.replay()

例子:

var theater =theaterJS();
theater
. addActor('vader')
. addScene('vader:Luke...')
. addScene(theater.replay)

7豺瘤、停止

theater.stop()

例子:

var theater =theaterJS()
theater
. addActor('vader')
. addScene('vader:Luke... ', 'I am your father...')
document.querySelector('button').addEventListener('click', function () {
 theater.stop()}, false)

8、getCurrentActor

返回當(dāng)前正在播放的演員听诸。

var theater =theaterJS()
theater
. addActor('vader')
. addScene('vader:Luke...')
. addScene(function (done) {
 var vader = theater.getCurrentActor()
 vader.$element.classList.add('dying')
   done()
 })
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末坐求,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子晌梨,更是在濱河造成了極大的恐慌桥嗤,老刑警劉巖须妻,帶你破解...
    沈念sama閱讀 222,183評論 6 516
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異泛领,居然都是意外死亡荒吏,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,850評論 3 399
  • 文/潘曉璐 我一進(jìn)店門渊鞋,熙熙樓的掌柜王于貴愁眉苦臉地迎上來绰更,“玉大人,你說我怎么就攤上這事锡宋《” “怎么了?”我有些...
    開封第一講書人閱讀 168,766評論 0 361
  • 文/不壞的土叔 我叫張陵员辩,是天一觀的道長盒粮。 經(jīng)常有香客問我,道長奠滑,這世上最難降的妖魔是什么丹皱? 我笑而不...
    開封第一講書人閱讀 59,854評論 1 299
  • 正文 為了忘掉前任,我火速辦了婚禮宋税,結(jié)果婚禮上摊崭,老公的妹妹穿的比我還像新娘。我一直安慰自己杰赛,他們只是感情好呢簸,可當(dāng)我...
    茶點故事閱讀 68,871評論 6 398
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著乏屯,像睡著了一般根时。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上辰晕,一...
    開封第一講書人閱讀 52,457評論 1 311
  • 那天蛤迎,我揣著相機與錄音,去河邊找鬼含友。 笑死替裆,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的窘问。 我是一名探鬼主播辆童,決...
    沈念sama閱讀 40,999評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼惠赫!你這毒婦竟也來了把鉴?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,914評論 0 277
  • 序言:老撾萬榮一對情侶失蹤汉形,失蹤者是張志新(化名)和其女友劉穎纸镊,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體概疆,經(jīng)...
    沈念sama閱讀 46,465評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡逗威,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,543評論 3 342
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了岔冀。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片凯旭。...
    茶點故事閱讀 40,675評論 1 353
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖使套,靈堂內(nèi)的尸體忽然破棺而出罐呼,到底是詐尸還是另有隱情,我是刑警寧澤侦高,帶...
    沈念sama閱讀 36,354評論 5 351
  • 正文 年R本政府宣布嫉柴,位于F島的核電站,受9級特大地震影響奉呛,放射性物質(zhì)發(fā)生泄漏计螺。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 42,029評論 3 335
  • 文/蒙蒙 一瞧壮、第九天 我趴在偏房一處隱蔽的房頂上張望登馒。 院中可真熱鬧,春花似錦咆槽、人聲如沸陈轿。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,514評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽麦射。三九已至,卻和暖如春灯谣,著一層夾襖步出監(jiān)牢的瞬間法褥,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,616評論 1 274
  • 我被黑心中介騙來泰國打工酬屉, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留半等,地道東北人。 一個月前我還...
    沈念sama閱讀 49,091評論 3 378
  • 正文 我出身青樓呐萨,卻偏偏與公主長得像杀饵,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子谬擦,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,685評論 2 360

推薦閱讀更多精彩內(nèi)容

  • 一 Activity 1 Activity 生命周期 1.1 Activity 的四種狀態(tài) running 當(dāng)前...
    _執(zhí)_念__閱讀 10,411評論 0 91
  • ??JavaScript 與 HTML 之間的交互是通過事件實現(xiàn)的惨远。 ??事件谜悟,就是文檔或瀏覽器窗口中發(fā)生的一些特...
    霜天曉閱讀 3,502評論 1 11
  • iOS網(wǎng)絡(luò)架構(gòu)討論梳理整理中话肖。。葡幸。 其實如果沒有APIManager這一層是沒法使用delegate的最筒,畢竟多個單...
    yhtang閱讀 5,207評論 1 23
  • 【Android 動畫】 動畫分類補間動畫(Tween動畫)幀動畫(Frame 動畫)屬性動畫(Property ...
    Rtia閱讀 6,182評論 1 38
  • 點擊查看原文 Web SDK 開發(fā)手冊 SDK 概述 網(wǎng)易云信 SDK 為 Web 應(yīng)用提供一個完善的 IM 系統(tǒng)...
    layjoy閱讀 13,786評論 0 15