• 浅析emoji与零宽连接符的应用及Emoji在JavaScript中的应用


    一、emoji与零宽连接符的应用

    1、Emoji ZWJ Sequences

      一般的 emoji 的字符是 3 个字节或 4 个字节, 像 ‍❤️‍ 这种看起来只有单个字符的 emoji 之所以它的 size 远超过 4 字节,是因为它是由若干个 emoji 按顺序连接组成的,这种顺序叫做 emoji zwj sequences 。

    2、零宽连接符

      实际上,并不是把 ❤️ 这三个 emoji 并排在一起就能够自动组成一个 ‍❤️‍ 。这三个 emoji 之间是需要通过一个 zwj 字符来连接的,也就是 “ zwj ❤️ zwj ”。

      那么什么是 zwj 呢?zwj 全称 zero width joiner,也就是 “零宽连接符”。因为这个字符是零宽度的,所以我们是看不见这个字符的。根据名字我们就可以知道,zwj 的作用就是用于字符与字符之间的连接。

      zwj 的 unicode point 是 U+200D

      同样,在 emoji 中还有非常多类似的组合式 emoji,比如:

    二、Emoji在JavaScript中的应用

    1、在写 JavaScript 字串的時候,直接将 Emoji 字元写入字符串是可以的,例如

    var a = '';

    2、JavaScript 有个 Unicode escape sequences 表示法,可以用在字串中,假设 Unicode 的字码为 U+1F197 ( ),那么 JavaScript 有2种表示法:

    (1)ES6 (ES2015) 可以使用 Unicode 的 Code point (码点) 表示一个 Unicode 文字 

    var emoji1 = '\u{01F354}';
    var emoji2 = String.fromCodePoint(0x1F354);

      注意:即便 ES6 可以用 Unicode 的 Code point  來表示一个 Unicode 文字,但事实上內部的文字码点主要还是以 UTF-16 为主。

    (2)ES5 仅支持 \uhhhh 表示法,大部分 Emoji 字元被定义在 BMP 以外的字码区域,你必須把一个 Unicode 字碼码(Code point) 转换成2个 UTF-16 码元 (code unit) 才行,通过 surrogate pair 的方式来表达一个 Unicode 字元。所以 U+1F197 只能用以下语法来写: 

    '\uD83C\uDD97'

      你可以通过 ES6 (ES2015) 提供的 API 来计算出 ES5 可以使用的2个 UTF-16 码元 (code unit):

    var hb = '\u{01F197}'[0].codePointAt(0).toString(16); // \ud83c
    var lb = '\u{01F197}'[1].codePointAt(0).toString(16); // \udd97

      也可以通过以下函数将 UTF-32 字码转换为2个 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);
    }

    3、将 12 个按键符号转换为 Emoji

      Emoji 定义了 12 个按键符号(0123456789#*),只要加入一组 2 个字元的 Emoji Keycap Sequence ('\uFE0F\u20E3') 就可以把文字自动转成 Emoji。

    4、在现有的 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 颜色太相近了,在电脑屏幕上不容易区分,索性就合并了。这5个字元分別是:

      以下是不同的 Emoji 在加上菲茨派屈克修飾符之后的比较

    var adult = '';
    var fitz6 = '\uD83C\uDFFF';
    var black = adult + fitz6; // 只要透過簡單的字串相加就可以完成!
    console.log(black);

      这样就会出现一个黑人。

      注意:不是所有 Emoji 都能加上虚色,只有跟「人类」有关的 Emoji 才能用,例如 Emoji 中有出現脸、手、脚、身体的,都可以这样用。目前 Unicode v11.0 定义了 106 个 Emoji 是可以加上 EMOJI MODIFIER FITZPATRICK 字元的,完整清单可以参考这里

    5、通过零宽连字符(ZWJ) 将多个Emoji 连接在一起

      我以前一直很纳闷有些 Emoji 到底是怎样产生的,深入研究后才发现,原谅 Emoji 这么好玩,除了有几千种不同的 Emoji 之外,还可以将其组合成各种千变万化的玩法。

      Unicode 中有个特殊的 零寬連字(ZWJ) 符號 (‍U+200D),这基本上是一个合法的 Unicode 文字,只是他预设是看不见的零宽(Zero Width) 字元。这个字元通常用在排版用途,不过却被 Emoji 拿来用了。你可以通过这个字元,任意串接2个不同的 Emoji 字元,然后就可以创造出新的、不存在 Emoji 清单中的全新 Emoji 字元。

      我直接把 (男人) 与 (女人) 串加起來,但中间卡一个 ZWJ 字元,这个 Emoji 就会自动变成 ‍ (一男一女):

      如果希望显示一家三口全家福的 Emoji ,可以直接把 (男人) 、 (女人) 与 (男孩) 串加起來,但不同的字元中间都要加一个 ZWJ 字元,Emoji 就会自动变成 ‍‍ (一男一女外加一个男孩)

      基本上,你要加几个人都可以,是不是很好玩。

  • 相关阅读:
    微软面试题_中文字符串转换为数字
    微软面试题_3个字母的组合
    LeetCode Notes_#1031_两个非重叠子数组的最大和
    剑指Offer_#57-II_和为 s 的连续正数序列
    LeetCode Notes_#560 和为k的子数组
    LeetCode Notes_#84 柱状图中最大的矩形
    LeetCode Notes_#221 最大正方形
    LeetCode Notes_#146 LRU缓存机制
    码云团队开发项目拉取与推送
    vue父子组件的双向绑定
  • 原文地址:https://www.cnblogs.com/goloving/p/16023118.html
Copyright © 2020-2023  润新知