前端生僻字显示

异名在一个游戏项目中遇到一个比较有意思的问题,在游戏的玩法设定中,当怪物在消失的时候会爆出一个中文字,这个效果在部分机型上会出现乱码符号css

显示乱码的缘由

一开始还觉得是字符太多了,char的纹理不够用了,还尝试过手动调用游戏引擎的cc.Label.clearCharCache去清除;后来才认识到是生僻字的问题,这得从字符编码提及,Unicode为每种语言中的每一个字符设定了统一而且惟一的二进制编码,以知足跨语言、跨平台进行文本转换、处理的要求,其中:前端

3400~4dffh:是中日韩认同表意文字扩充a区,总计收容6,582个中日韩汉字
4e00~9fffh:是中日韩认同表意文字区,总计收容20,902个中日韩汉字web

一般状况下,咱们平常所用到的中日韩非符号字符都会落在3400-9fff这个编码区间,所以当咱们须要判断某一个字符是不是属于汉字的时候,就能够经过查看它的的Unicode编码是否落在这个区间,咱们写一个正则去检查一下上面两个字符👇:浏览器

能够看到第二个字它并不处于经常使用汉字的编码区间,它是生僻字,生僻字的使用频率很低,咱们平常高频用的的汉字其实也就是几千个而已。字体公司设计汉字字体的成本比较高,由于若是要设计一款英文字体,那就只要设计26个字母就能够组合出全部的单词了,而每个汉字则几乎都须要人工去作造型,生僻字的造字性价比可见有多低,能够说每一款汉字字体都是收录残缺,缺多缺乏而已。因此这就解析了为啥在华为的手机上为啥看到的是乱码而在苹果手机上却能正常显示该字符,由于他们的系统字体库不一样,华为的字体库没有录用这个生僻字性能优化

解决方法

在前端要解决生僻字的显示问题能够利用css的font-family 的字体备选机制,能够把这个生僻字单独作成一个字体文件,而后经过@font-face 嵌入,而后在须要的地方引用,浏览器在解析文字的时候会逐字匹配,当字体上没有这个字符的时候就会在备用的字体上选择,从而可以让咱们的生僻字被显示出来,通常生成单字体文件有这几种方式:微信

字体切割

若是你缺失的还不算太生僻,可能在某些字体库中收录了这个字,那就能够经过字蛛或者fontmin这些字体提取方案把这个字单独提取出来,做为单字体文件引用app

icon font

让设计师单独针对这个生僻字作设计而后生成icon font,能够直接上传阿里的iconfont,而后再下载代码,默认会给到UnicodeFont classSymbol三种引用方式async

专用的字体信息网站

有一个日本的字体信息网站glyphwiki.org,支持检索,甚至能够经过偏旁部首拼凑生僻字,也很是方便编辑器

位图字体

固然在游戏中,更常见的方式是使用位图字体,位图字体由 fnt 格式的字体文件和一张png图片组成,fnt文件提供了对每个字符小图的索引,这种格式的字体能够由专门的软件生成,异名用的是shoebox。由于位图字体是一个符号和图片的索引文件,因此咱们能够把某个场景下具备特点的字体都单独作设计,固然也能够应用在生僻字的显示中:性能

这个也是异名最终使用的方案,你永远不知道你的下一个游戏背景设定是什么,万一是山海经里面的远古神兽或者是像异名这种学科游戏里面的奇葩新造字,或者可以给你们带来一点参考。

不可靠的String.length

以上就把需求解决完了,可是异名在踩坑的过程当中还发现一个有趣的事情:

字符串的length属性是多么的不可靠!并且更有意思的是,String.length的长度不是2吗,可是若是你用不一样的方式去遍历,你还会发现一些更神奇的事情:

异名看到这个执行结果的时候是挺惊讶,并且这个怪异表现可能还会和咱们的平常工做产生交集。相对于汉字,咱们更常常遇到的问题多是emoji,好比某天产品经理有个需求,用户的姓名输入框要作一个长度限制,长度不能超过十,你说简单啊,利用length作一下校验,长度超过十的就拦截了。而后测试同窗,啪啪啪输入五个💩...

这个需求相信大部分前端都有遇到过,用length去判断是不可靠的,为何呢?由于在字符编码上,有好几种方式能够用来表达字符:

💩能够是一个字符,可是也能够用两个字符来表达,因此你就不能奢望String.length能给到你一个可靠的结果了。这个时候咱们回头看一眼MDN上对String.length的描述,你就会发现人家一开始就说了,我不可靠...

那有没有一种可靠的方法可以准确统计字符串的长度呢,我上面举了Array.from的例子,它正确返回了字符的长度,可是它也只是一个有缺陷的方案,它对某些字符有效

有兴趣的同窗能够点击原文跳转,在原文那里,异名贴了两篇参考文章,他们进行了更深刻的研究



 

融球效果(shader)    颜色滤镜    水波扩散效果(shader)

镜面光泽效果    圆形头像(shader)    追光效果

shader 溶解效果    富文本打字机效果    放大镜效果

子弹跟踪效果    移动残影效果    刮刮卡实现

微信小游戏首包超出4M以后       遥控杆实现

金币落袋效果    使用cocos进行2D和3D混合开发

Cocos游戏开发入门最佳实践    背景无限滚动

马赛克效果(shader)

渐变过渡的相册(shader)

游戏性能优化

本文分享自微信公众号 - 异名(async-code)。
若有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一块儿分享。

相关文章
相关标签/搜索