用 JavaScript 玩轉 Emoji 表情圖示原來這麼簡單
栏目: JavaScript · 发布时间: 6年前
内容简介:這陣子花了一些時間研究 Unicode 萬國碼,看著看著就研究起 Emoji 表情圖示來了。過程中還跑去看了首先,先來講怎樣在文件中使用 Emoji 表情圖示。這過程說簡單很簡單,要說複雜其實也有點複雜。基本上,你有 4 種方式可以在文件中輸出 Emoji 表情圖示:其實每一個 Emoji 就是一個 Unicode 字元,就跟一般文字一樣,所以你大可將 Emoji 字元放在任意字串中,完全沒有問題!
這陣子花了一些時間研究 Unicode 萬國碼,看著看著就研究起 Emoji 表情圖示來了。過程中還跑去看了 Unicode® Emoji 官方規格,要是沒有先建立對 Unicode 的理解,要完全看懂 Emoji 的來龍去脈是不太容易的。研究的過程中,還發現了一些有趣的冷知識,欲知詳情請繼續看下去! :wink:
首先,先來講怎樣在文件中使用 Emoji 表情圖示。這過程說簡單很簡單,要說複雜其實也有點複雜。基本上,你有 4 種方式可以在文件中輸出 Emoji 表情圖示:
- 直接輸入 Emoji 字元
- 將 12 個按鍵符號轉換為 Emoji 圖示
- 在現有的 Emoji 字元後方加入菲茨派屈克修飾符 (膚色深度)
- 透過 零寬連字(ZWJ) 將多個 Emoji 連接在一起
直接輸出 Emoji 字元
其實每一個 Emoji 就是一個 Unicode 字元,就跟一般文字一樣,所以你大可將 Emoji 字元放在任意字串中,完全沒有問題!
任何支援 Unicode (UTF-8, UTF-16, UTF-32) 的文件,都可以完全合法的放入 Emoji 字元,使用者的作業系統 (包含行動裝置) 只要有安裝含有 Emoji 的字型 (大多已內建),就可以正確顯示 Emoji 表情圖示。
-
直接上網搜尋並複製貼上
大部分 Emoji 字元都可以上網找到,直接透過複製/貼上就可以立即使用,相當便利:
-
使用 Windows 10 的 Emoji 輸入法視窗
從 Windows 10 周年更新內建了一個
Win+.
快速鍵,可以叫出 Emoji 鍵盤來用,非常方便! -
透過 HTML Entities 語法輸出到 HTML 文件中
&what: Discover Unicode & HTML Character Entities
-
透過 JavaScript 的 Unicode escape sequences 寫在字串中
在寫 JavaScript 字串的時候,直接將 Emoji 字元寫入字串是可以的,例如:
var a = ':information_desk_person::ok_hand::bamboo::heart_eyes:';
JavaScript 有個 Unicode escape sequences 表示法,可以用在字串中,假設 Unicode 的字碼為
U+1F197
( :ok: ),那麼 JavaScript 有兩種表示法:-
ES6 (ES2015) 可以使用 UTF-32 編碼
var st = '\u{01F197}';
-
ES5 僅支援 UTF-16 編碼,而大部分 Emoji 字元被定義在 UTF-16 以外的字碼區域 (UTF-32),你必須把一個 UTF-32 字碼 (Code point) 轉換成兩個 UTF-16 字碼才行,透過 surrogate pair 的方式來表達一個 UTF-32 字元,所以
U+1F197
只能用以下語法來寫:'\uD83C\uDD97'
你可以透過 ES6 (ES2015) 提供的 API 來計算出 ES5 可以使用的兩個 UTF-16 字碼:
var hb = '\u{01F197}'[0].codePointAt(0).toString(16); // \ud83c var lb = '\u{01F197}'[1].codePointAt(0).toString(16); // \udd97
也可以透過 以下函式 將 UTF-32 字碼轉換為兩個 UTF-16 的表示法:
function toUTF16(codePoint) { var TEN_BITS = parseInt('1111111111', 2); function u(codeUnit) { return '\\u'+codeUnit.toString(16).toUpperCase(); } if (codePoint <= 0xFFFF) { return u(codePoint); } codePoint -= 0x10000; // Shift right to get to most significant 10 bits var leadingSurrogate = 0xD800 | (codePoint >> 10); // Mask to get least significant 10 bits var trailingSurrogate = 0xDC00 | (codePoint & TEN_BITS); return u(leadingSurrogate) + u(trailingSurrogate); }
使用範例如下:
toUTF16(0x1F197)
-
將 12 個按鍵符號轉換為 Emoji 圖示
Emoji 定義了 12 個按鍵符號 ( 0123456789#*
),只要加入一組 2 個字元的 Emoji Keycap Sequence ( '\uFE0F\u20E3'
) 就可以把文字自動轉成 Emoji 圖示。
var keycap = '\uFE0F\u20E3'; console.assert(':zero:' === '0' + keycap); console.assert(':one:' === '1' + keycap); console.assert(':two:' === '2' + keycap); console.assert(':three:' === '3' + keycap); console.assert(':four:' === '4' + keycap); console.assert(':five:' === '5' + keycap); console.assert(':six:' === '6' + keycap); console.assert(':seven:' === '7' + keycap); console.assert(':eight:' === '8' + keycap); console.assert(':nine:' === '9' + keycap); console.assert(':hash:' === '#' + keycap); console.assert('*️⃣' === '*' + keycap);
在現有的 Emoji 字元後方加入菲茨派屈克修飾符 (膚色深度)
在 Emoji 表情圖示的 Unicode 規格中,有個特別的 EMOJI MODIFIER FITZPATRICK (菲茨派屈克修飾符) 可用,這個 修飾符 (Modifier) 也是一個合法的 Unicode 字元,必須緊接著在 Emoji 字元後面出現。
目前全世界人類的 膚色分級 ( Fitzpatrick scale ) 是 1975 年由一位叫做 Thomas B. Fitzpatrick 的人訂定出來的,他當初定義了 6 種膚色等級。(Type 1 ~ Type 6)。研究 Emoji 竟然還能學習到這種冷知識,哈!
在 Emoji 表情符號中,總共定義了 5 個字元,用來代表 Emoji 的顏色深度。為什麼不是 6 個呢?因為 Type 1 與 Type 2 顏色太相近了,在電腦螢幕上不容易區分,索性就合併了。這五個字元分別是:
字元名稱 | Code point | 字元 | UTF-16 (使用 JavaScript 字串) | UTF-8 |
---|---|---|---|---|
FITZ-1-2 | U+1F3FB | 0xD83C 0xDFFB ( '\uD83C\uDFFB' ) |
0xF0 0x9F 0x8F 0xBB | |
FITZ-3 | U+1F3FC | 0xD83C 0xDFFC ( '\uD83C\uDFFC' ) |
0xF0 0x9F 0x8F 0xBC | |
FITZ-4 | U+1F3FD | 0xD83C 0xDFFD ( '\uD83C\uDFFD' ) |
0xF0 0x9F 0x8F 0xBD | |
FITZ-5 | U+1F3FE | 0xD83C 0xDFFE ( '\uD83C\uDFFE' ) |
0xF0 0x9F 0x8F 0xBE | |
FITZ-6 | U+1F3FF | 0xD83C 0xDFFF ( '\uD83C\uDFFF' ) |
0xF0 0x9F 0x8F 0xBF |
以下是不同的 Emoji 在加上菲茨派屈克修飾符之後的比較表:
Code point | Default | FITZ-1-2 | FITZ-3 | FITZ-4 | FITZ-5 | FITZ-6 |
---|---|---|---|---|---|---|
U+1F9D2: 小孩 | ||||||
U+1F466: 男孩 | :boy: | :boy|type_1_2: | :boy|type_3: | :boy|type_4: | :boy|type_5: | :boy|type_6: |
U+1F467: 女孩 | :girl: | :girl|type_1_2: | :girl|type_3: | :girl|type_4: | :girl|type_5: | :girl|type_6: |
U+1F9D1: 大人 | ||||||
U+1F468: 男人 | :man: | :man|type_1_2: | :man|type_3: | :man|type_4: | :man|type_5: | :man|type_6: |
U+1F469: 女人 | :woman: | :woman|type_1_2: | :woman|type_3: | :woman|type_4: | :woman|type_5: | :woman|type_6: |
我簡單透過 JavaScript 示範將 (大人) 膚色改成 (黑人) 的程式寫法:
var adult = ' '; var fitz6 = '\uD83C\uDFFF'; var black = adult + fitz6; // 只要透過簡單的字串相加就可以完成! console.log(black);
請注意:不是所有 Emoji 都能加上膚色,只有跟「人類」有關的 Emoji 才能這樣用,例如 Emoji 中有出現臉、手、腳、身體的,都可以這樣用。目前 Unicode v11.0 定義了 106 個 Emoji 圖示是可以加上 EMOJI MODIFIER FITZPATRICK 字元的,完整清單可以參考 這裡 。
透過零寬連字(ZWJ)將多個 Emoji 連接在一起
這個就真的很酷了,我以前一直很納悶有些 Emoji 到底是怎樣產生的,深入研究後才發現,原來 Emoji 這麼好玩,除了有幾千種不同的 Emoji 之外,還可以將其組合成各種千變萬化的玩法。
Unicode 中有個特殊的 零寬連字(ZWJ) 符號 ( U+200D
),這基本上是一個合法的 Unicode 文字,只是他預設是看不見的 零寬 (Zero Width) 字元。這個字元通常用在排版用途,不過卻被 Emoji 拿來用了。你可以透過這個字元,任意串接兩個不同的 Emoji 字元,然後就可以創造出新的、不存在 Emoji 清單中的全新 Emoji 字元。
這邊我做個非常簡單的示範,我直接把 :man: (男人) 與 :woman: (女人) 串加起來,但中間卡一個 ZWJ 字元,這個 Emoji 就會自動變成 :man::woman: (一男一女):
var man = ':man:'; var women = ':woman:'; var zwj = '\u200D'; console.log(man + zwj + women);
如果希望顯示一家三口全家福的 Emoji 圖示,可以直接把 :man: (男人) 、 :woman: (女人) 與 (男孩) 串加起來,但不同的字元中間都要卡一個 ZWJ 字元,此時 Emoji 就會自動變成 :man::woman::boy: (一男一女外加一個男孩):
var man = ':man:'; var women = ':woman:'; var child = ':boy:'; var zwj = '\u200D'; console.log(man + zwj + women + zwj + child);
相同的邏輯,如果你想顯示一家三口全家福,但小孩是個女兒的話,的 Emoji 圖示,可以直接把 :man: (男人) 、 :woman: (女人) 與 :girl: (女孩) 串加起來,不同的字元中間依然要卡一個 ZWJ 字元,此時 Emoji 就會自動變成 :man::woman::girl: (一男一女外加一個女孩):
var man = ':man:'; var women = ':woman:'; var child = ':girl:'; var zwj = '\u200D'; console.log(man + zwj + women + zwj + child);
如果有兩個小孩呢?沒問題! :man: + :woman: + :boy: + :girl: = :man::woman::boy::girl:
var all = [':man:', ':woman:', ':boy:', ':girl:']; var zwj = '\u200D'; console.log(all.join(zwj));
基本上,你要加幾個人都可以!而且在這兩性平權的時代,兩個爸爸、兩個媽媽也不奇怪,想親手試試 Emoji 怎樣設定嗎?
:man::man::boy::girl:
var all = [':man:', ':man:', ':boy:', ':girl:']; var zwj = '\u200D'; console.log(all.join(zwj));
:woman::woman::boy::girl:
var all = [':woman:', ':woman:', ':boy:', ':girl:']; var zwj = '\u200D'; console.log(all.join(zwj));
喔!爸爸是巴西人、媽媽是黑人?沒問題!I got you back! :man|type_1_2::woman|type_6::boy::girl:
var fitz1 = '\uD83C\uDFFB'; var fitz6 = '\uD83C\uDFFF'; var all = [':man:'+fitz1, ':woman:'+fitz6, ':boy:', ':girl:']; var zwj = '\u200D'; console.log(all.join(zwj));
你是一個白人、女性、而且是一位學生?:woman|type_1_2::mortar_board:
var fitz1 = '\uD83C\uDFFB'; var all = [':woman:'+fitz1, ':mortar_board:']; // 加上學士帽 Emoji 即可! var zwj = '\u200D'; console.log(all.join(zwj));
套用 ZWJ 字元的 Emoji 完整清單可以參考 這裡 。
注意事項
雖然 Unicode 明確定義了許多 Emoji 的字碼,但還是有很多平台會自己定義額外的 Emoji 圖示,因此不是所有的 Emoji 大家都看的到,這點必須特別注意。
有些沒有被定義在 Emoji 的 Unicode 符號,在特定作業系統平台也會特別做成 彩色版 的 Emoji 圖示,這部分各位就不用過於擔心,就算在其他平台看不到這個圖示,還是會顯示「文字版」的符號樣式,但也就沒有顏色了。
Unicode 標準定義的 Emoji 清單,可以從 Full Emoji List, Unicode v11.0 取得!
相關連結
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
猜你喜欢:- Vue 表情包输入组件
- mysql 存储emoji表情
- Swift自定义表情键盘+录音
- 让 MySQL 支持存储 emoji 表情
- 深度卷积网络迁移学习的脸部表情识别
- Mysql存储微信Emoji表情问题
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
嵌入式系统开发之道
2011-12 / 69.00元
《嵌入式系统开发之道:菜鸟成长日志与项目经理的私房菜》用平易朴实的语言,以一个完整的嵌入式系统的开发流程为架构,通过一位“菜鸟”工程师与项目经理的诙谐对话,故事性地带出嵌入式系统概念及开发要素,并点出要成为一名称职的嵌入式系统工程师,在实际工作中所必须具备的各项知识及技能。 《嵌入式系统开发之道:菜鸟成长日志与项目经理的私房菜》可以分为三大部分:第1、3、4、17、18、19章和附录D为嵌入......一起来看看 《嵌入式系统开发之道》 这本书的介绍吧!