早年間在遊戲機硬件機能十分有限的時候,當時的製作者們就已經發現。在介紹背景劇情、或表現人物對話時,直接顯示一段文字,與逐漸顯示出一段文字的體驗是完全不同的。根據人物語速逐個顯示出一個一個文字,代入感和演出效果會改善很多。
而且,如果在蹦出文字時,配上打字機的音效,任務的代入感會更強。雖然早期的遊戲一般沒有語音,但是根據人物說話的語速顯示文字,再配上“嘟嘟嘟”的音效,結合玩家強大的腦補,就能做出很強的代入感。
比如大名鼎鼎的魂鬥羅一代日版,地球被隕石撞擊的動畫,配合打字機一樣的任務簡報,代入感頓時加滿。
雖然如今的遊戲可以用真人配音等方式製作出真正的語音,但就像8bit像素風格逐漸變成一種流行的風格一樣,“嘟嘟嘟”的配音也變成了一種無可取代的風格。給遊戲平添了一種風味。
比如《蔚藍》就是一個優秀案例,主角麥德玲的說話帶有“嘰嘰哇哇”的音效,與精美的像素風格相得益彰。這種語音有一個專有名詞“Gibberish”,英文原意為“嘟嘟囔囔”,你也可以理解為一種語言。
而相比其它遊戲中“嘰嘰咕咕”的簡單電子音效,《動物之森》裏的合成音效則成熟得多!
《動物之森》裏的音效不再是單調的“嘰裏咕嚕”,而是真的能識別出語音中的“音素”和“音節”,用極少的音頻資源就能做出類似“朗讀”的效果。雖然這種“朗讀”似是而非,玩家很難直接聽懂。但是隻要配合文字觀看,就好像是動物們在說話一樣。
更有趣的是,這種語音係統,可以適配各種不同的語言,中文、英文、俄語等等,隻要能夠拆分出“音素”,就能讓狸貓說各種外語。
這種神奇的算法是如何實現的呢?
簡單來說,合成嘰裏咕嚕語的主要技術分為三步:一是聲母韻母錄音,二是漢字轉拚音,三是語音合成。
我為了製作這個“嘰裏咕嚕語”,特地找來了小學一年級的“聲母韻母表”。不知道誰還記得b p m f d t n l, a o e i u v, 還有an en yin un vn,小學一年級的知識恍如隔世,但語音語素的秘密其實就藏在聲母韻母表中。
我們需要自己錄製一份原始素材,朗讀整個聲母韻母表並錄音,然後將這些聲音切分出來,保存在單獨的文件裏。文件名與拚音名稱對應。
把錄音切分成幾十個文件是一件麻煩事,這裏我用了python的pydub庫對聲音進行處理。pydub這個庫可以識別音頻中沒有聲音的部分做切分。很快就處理好了所有的原始音頻文件。
錄音時注意,中文“魚”、“暈”的發音不是“u”而是“v”。其中v是變通寫法,正確寫法是“u上麵帶兩點”,注意不要弄混。
實現語音合成的第二大難點在於漢字如何轉為拚音。
細說的話,轉拚音的關鍵在於——我們的漢字編碼順序是有規律的。一般是按照讀音的字母順序進行排列,比如“啊”就在“好”的前麵,像“張”這種z開頭的漢字就排在靠後的位置。這樣一來,我們可以用一張編碼表給漢字和拚音做一個簡單的對應關係。
說起來容易做起來難,實際上還是要借鑒前人已做過的成果。經過耐心搜索,我在網上找到了某個大神寫的一個庫,庫名Sunrise.Spell,這個庫的基本原理就是用一個大的對應表將漢字轉為拚音,但中間也有很多特殊情況需要處理。
而且由於我們的需求比較特殊,不得不對源碼做出大幅度修改。
最終實現了將文字轉換為拚音序列的功能,而且加入了標點符號的識別,逗號、句號等常用標點符號會被識別為空白停頓,用下劃線表示。
剩下的問題就是單純的Unity技術問題了。整理一下思路,現在的問題是:
給出一段用空格分割的音節字符串,找到每個音節對應的音頻文件,並依次播放出來。
這個問題比較繁瑣,在這裏咱們用Unity做了一個簡單的實現。Unity工程晚些時候會放在評論區。
在播放時,需要控製音頻的音調(Pitch),音調高一些比較卡通。為了效果好,還需要適當“吞音”,就是每個音節不要說全,掐頭去尾,隻播放中間一段,感覺反而更好。
核心的音頻控製腳本是Pronounce Core,其中Trim Begin是掐掉音節的開頭,Trim End是去掉音節尾部,取值都是0~1的百分比。上圖中的設置表示,去掉了音節的11.2%之前的部分,與79.6%之後的部分。All Clips為音頻列表。