V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
iOS 开发实用技术导航
NSHipster 中文版
http://nshipster.cn/
cocos2d 开源 2D 游戏引擎
http://www.cocos2d-iphone.org/
CocoaPods
http://cocoapods.org/
Google Analytics for Mobile 统计解决方案
http://code.google.com/mobile/analytics/
WWDC
https://developer.apple.com/wwdc/
Design Guides and Resources
https://developer.apple.com/design/
Transcripts of WWDC sessions
http://asciiwwdc.com
Cocoa with Love
http://cocoawithlove.com/
Cocoa Dev Central
http://cocoadevcentral.com/
NSHipster
http://nshipster.com/
Style Guides
Google Objective-C Style Guide
NYTimes Objective-C Style Guide
Useful Tools and Services
Charles Web Debugging Proxy
Smore
jox
V2EX  ›  iDev

微信用来输入 gif 表情的那个键盘是怎么实现的?有人了解么?

  •  
  •   jox · 2014-12-26 20:24:58 +08:00 · 8434 次点击
    这是一个创建于 3656 天前的主题,其中的信息可能已经有所发展或是发生改变。
    我从github上下载了weico用的表情键盘,他们的做法是采用了collection view,显示键盘的时候读取每个图片,说实话我不太想用这种方法来实现,觉得有点麻烦,而且性能上也不太行,总感觉collection view比table view性能上要差一些,不太想用。百度贴吧和微信是怎么实现的不清楚,感觉微信的表情键盘用起来更顺畅,而且用户还可以定制,做得挺好的。

    我现在能想到的办法是将默认的表情分组排列到几张图片里,弄成一个矩阵,在滚动的时候不是一个表情一个表情地读取,而是整张整张地读取优化过的图片,这样CPU主要负责从硬盘读取图片就可以了,如果内存够的话可以直接使用解码过的图片,性能上肯定是比使用collection view一个一个地读取然后再贴上去快一些,实现起来也很容易,使用scroll view分页就能搞定,通过用户touch的位置在矩阵的哪个部分来判断是哪个表情被用户选中,但是要花时间在图片编辑上,我用的还是GIMP 😱

    不知道大家还有没有更好的想法?
    39 条回复    2014-12-27 01:27:50 +08:00
    jox
        1
    jox  
    OP
       2014-12-26 20:26:35 +08:00
    百度贴吧的输入表情键盘在滚动的时候会有比较明显的卡顿,貌似是在主线程做的渲染,晕,还是微信的做得好。
    chmlai
        2
    chmlai  
       2014-12-26 20:33:35 +08:00
    collection view 没啥问题, 有性能问题应该做Profile.
    jox
        3
    jox  
    OP
       2014-12-26 20:40:26 +08:00
    @chmlai 我下载了weico,性能上感觉还行,与微信的表情键盘比起来差不多一样顺畅,我很好奇微信是怎么实现的,这位朋友了解吗?
    Elethom
        4
    Elethom  
       2014-12-26 20:44:30 +08:00 via iPhone
    越獄之後上工具分析一下就知道了.
    jox
        5
    jox  
    OP
       2014-12-26 20:52:20 +08:00
    @Elethom 什么工具?我开始做iOS上的开发没多久,目前工具只会用xcode和instruments,什么工具能满足我的需要?
    OctWu
        6
    OctWu  
       2014-12-26 21:32:25 +08:00 via iPhone
    @jox reveal?好像是这么拼。可以看图层结构的
    jox
        7
    jox  
    OP
       2014-12-26 21:39:23 +08:00
    @OctWu 就是这个!我在网上检索了一下,非常感谢!
    yellowV2ex
        8
    yellowV2ex  
       2014-12-26 22:06:04 +08:00
    你collection view的cell你也可以自己写度缓存啊,并且collection view的cell会自动重用,最省事官方最推荐的一大堆格子scroll的方式就是collection了,ios6之后都支持。

    再说,collection view只是读个静态小图,ios的性能轻松应付没问题的,你想的太多了。
    jox
        9
    jox  
    OP
       2014-12-26 22:19:03 +08:00
    @yellowV2ex 刚刚研究了一下微信,微信似乎也是用的collection view,额,我之前用过一段时间collection view,因为觉得不如table view流畅又换回了table view,所以对collection view的印象不太好。


    你觉得使用几张固定尺寸的扁平的图片来排列表情这个方法怎么样呢?比如微信的兔斯基表情,微信是每个表情有一个gif文件,同时还有一个对应静态的png文件,里面是gif的第一帧,用户在输入兔斯基表情之前展示的表情列表是使用png文件组合出来的,表情发出去之后是用gif文件渲染的,列表的尺寸是固定的,所以这个也可以使用一张静态图片来实现,使用collection view就是用多个小图片来组合列表,然后通过collection view的delegate方法来捕获点击事件,使用静态图片的话就要使用gesture recognizer然后在捕获touch事件之后通过判断touch的位置来确定选择哪个表情。这样就不用写代码来一张一张地读取小图片然后组合列表了,但是需要使用图片剪辑软件来生成静态的列表。
    yellowV2ex
        10
    yellowV2ex  
       2014-12-26 22:38:30 +08:00
    @jox 你是不是想错了

    选表情的那个列表,肯定是静态图啊,并且还是很小的静态图,对应的并不是一个真的gif文件,只是一行网址的字符串,发过去给对方的也是一条特殊信息比如 gif|http://xxx.com/xxx.gif 而已。
    至于显示gif部分,是收到这条信息,上面消息列表的tableview的cell干的事情。
    yellowV2ex
        11
    yellowV2ex  
       2014-12-26 22:39:54 +08:00
    @jox 真不知道你在纠结什么,一共就几十个小图,你考虑这个资源占用不如花时间想想消息储存和显示的结构啊
    dcty
        12
    dcty  
       2014-12-26 22:46:00 +08:00 via iPad
    直接用单例的淡定路过。因为表情少,只有四页。
    性能瓶颈不在这里,把优化留给cell的富文本展示去吧。
    yellowV2ex
        13
    yellowV2ex  
       2014-12-26 22:47:56 +08:00
    另外,微信不一定是collection view,因为支持ios5,ios5是不支持collection view的,也可能是判断了ios6使用了collection view
    jox
        14
    jox  
    OP
       2014-12-26 22:50:17 +08:00
    @yellowV2ex 不止几十个啊。而且我也没说列表是用动态图组成的啊,只是说发出去之后渲染用的是gif,发出去之后发送者和接受者两边不都得显示动画啊?你从哪看出来我的意思是用gif来组合列表的?

    我在考虑该用什么样的方式来实现,性能是一方面,实现方式的难易也是一方面,我没实现过类似的东西,考虑一下不行吗?
    jox
        15
    jox  
    OP
       2014-12-26 22:51:44 +08:00
    @yellowV2ex 如果不用collection view,还可以用什么方法来实现呢?直接使用scroll view来模拟collection view吗?
    yellowV2ex
        16
    yellowV2ex  
       2014-12-26 22:53:26 +08:00
    @jox 你一屏不最多就几十个小图么?用collection view你放几万个都没问题啊,你到底在纠结个什么鬼啊。

    collection view最简单,写几个delegate 方法和一个cell就搞定,占用资源也是最小的,也是自带系统优化的,cell也是重用的。
    另外你说的那个方法不现实,后台如果修改一下顺序或者增加减少一个你全部页都要重新生成图片,并且得到的好处也不多,做起来也比collection view麻烦好几倍。
    yellowV2ex
        17
    yellowV2ex  
       2014-12-26 22:54:33 +08:00
    @jox collection view出现之前,一直是scroll view来模拟cell的,有些人也会用tableview,一个cell里横着放几个图这样,但前提都是有重用机制,不然滑来滑去容易闪退
    xummer
        18
    xummer  
       2014-12-26 22:57:05 +08:00   ❤️ 1
    微信自定义的MMUIScrollView继承的UIScrollView https://farm9.staticflickr.com/8681/16085385516_02b82fd1ae_o.png
    xummer
        19
    xummer  
       2014-12-26 23:00:25 +08:00   ❤️ 1
    ainopara
        20
    ainopara  
       2014-12-26 23:05:53 +08:00 via iPad
    想向楼主打听一下weico的表情键盘是哪个repo?
    qq2511296
        21
    qq2511296  
       2014-12-26 23:06:41 +08:00
    @xummer 你这个是怎么分析出来的?用什么工具?
    jox
        22
    jox  
    OP
       2014-12-26 23:07:10 +08:00
    @yellowV2ex 苹果的那个photoscroll的示例代码就是直接继承scroll view做的,也不是一次性将所有的图片都读进内存的。另外我说你激动个蛋,我又没说一定要那么做。你的说法才有问题,表情列表本身的数据结构是一个set,同一个set里彼此之间的顺序是不重要的,你说的顺序和增减这个才不现实,即使有也没什么,切个图需要几分钟?升级直接替换掉之前的图片就可以了,并且实现起来也并不比collection view麻烦好几倍,我觉得在表情不多的时候比collection view需要的工作量更少。


    @xummer 非常感谢
    jox
        23
    jox  
    OP
       2014-12-26 23:08:31 +08:00   ❤️ 1
    OctWu
        24
    OctWu  
       2014-12-26 23:44:32 +08:00 via iPhone
    collectionView应该是最简单的。并且有复用。因此稍微进行封装也就是ok的。另外不论TableView还是CollectiomView本质都是scrollView啊
    jox
        25
    jox  
    OP
       2014-12-26 23:57:04 +08:00
    @OctWu 同一个列表,每个cell渲染内容使用同样的代码,collection view比table view卡,就是类似这种百度贴吧帖子列表的那种样式,可以用collection view来实现,也可以使用table view来实现,也可以从零开始使用scroll view来实现,我最开始用的就是scroll view,包括重用都是自己写的,然后又试了一下collection view,结果发现我自己写的不如collection view好,就用的collection view,最后知道原来用table view也能实现,又换成了table view,用table view的话就是使用group table,然后每个section单独放一个cell,当然也可能我collection view用的不对,我没有做深入的研究,我总觉得那个collection layout是造成collection view比table view性能差一点的原因。

    现在我好奇腾讯为什么不直接使用collection view而要使用自己写的scroll view呢?哎,能跟腾讯的工程师问问就好了。。。
    OctWu
        26
    OctWu  
       2014-12-27 00:02:38 +08:00 via iPhone
    @jox 你说的卡,在现在机子的情况来看应该也不会很明显了。另外腾讯很多东西都是自己封装的。另外可能和上面有人提到的要支持iOS5有关。其实这个页面自己写重用也应该不会有很大压力
    jox
        27
    jox  
    OP
       2014-12-27 00:08:34 +08:00
    @OctWu 恩。。。很有道理,上面有人提到微信一直支持到iOS 5,刚才我又试了一下百度贴吧,发现只要加载过一次表情列表,之后就很顺畅了,他们应该是图片解码这块儿没有放到后台来做

    我刚学习iOS开发的时候就吃过几次亏,很多东西不知道用现成的可以做就自己写,结果过了一段时间就发现问题了,然后发现有更好的方式,然后就又回去返工,蛋疼的要死,所以现在要做之前没做过的东西时都会谨慎一些,不敢直接懂动手自己写。
    OctWu
        28
    OctWu  
       2014-12-27 00:15:26 +08:00 via iPhone
    @jox 自己写的好处是定制化强。但是我比较喜欢追求性能。不过技术功底不够,会造成很多无用功,也不好
    jox
        29
    jox  
    OP
       2014-12-27 00:23:43 +08:00
    @OctWu 自己写可以学到很多很多东西,即使用别人的代码我也喜欢搞清楚别人是怎么做的再用,不过工作上这样弄大概不行,我现在在做的这个iOS应用跟我的工作无关,其实是当初想找个iOS开发的工作挖的坑,当时写好了之后觉得他妈的就是一坨屎,就搁硬盘里了,然后iOS开发的工作也没找着,真是惨,最近突然有时间了,决定把这个坑给填了,所以可以慢慢搞,搞到我满意为止,搞了两个多月了,就差最后这个输入表情的键盘了。

    我也喜欢追求性能,别的什么都可以将就,但是程序一定要smooth,要fucking smooth,super fucking smooth,但无奈本身水平就是渣,所以花的时间也会多一些。
    OctWu
        30
    OctWu  
       2014-12-27 00:30:14 +08:00 via iPhone
    @jox 哈哈哈,那为啥不试试FB的AsyncDisplayKit,本来打算用那个的,可惜都是layer,autolayout无力。
    jox
        31
    jox  
    OP
       2014-12-27 00:36:46 +08:00
    @OctWu 看名字似乎是异步渲染的框架,我不知道有这么个东西啊,我是用的GCD写的异步渲染那部分的代码,效果也挺不错的,差不多的数据量同样的设备我的应用比百度贴吧的程序要流畅!smooth as fuck, man
    OctWu
        32
    OctWu  
       2014-12-27 00:40:55 +08:00 via iPhone
    @jox 其实我还是很好奇你的异步渲染。渲染我完全迷迷糊糊的。BTW我说的那个框架最早的目的就是为了让滚动的时候FPS无限接近60。不过不能AutoLayout也是郁闷。同时想问下你接触了iOS开发多久
    jox
        33
    jox  
    OP
       2014-12-27 00:57:41 +08:00
    @OctWu 我今年春节的时候从零开始学iOS开发,看了半个月的文档和各种guide,用了一个多月的时间写了一个应用,然后直到今年过完国庆节十月末的时候又重新捡起来,前后差不多有四五个月吧。

    我没买苹果的开发者计划,所以不能测试在真机的FPS,但是我很有信心能够达到60FPS,异步渲染代码写起来不是很难,但是也有点麻烦,我的源代码本来是打算写好之后给我们学校的学弟学妹们开放的,如果你感兴趣到时候可以找我要,但是写完之前我是不会给别人看源代码的。

    使用的技术其实很简单,就是text kit排版完成之后除非屏幕旋转否则不再进行排版,每次渲染的时候直接画就行了,这个我觉得挺关键的,其次就是使用off screen drawing技术,每次需要渲染cell的内容的时候直接使用GCD在后台开始画内容,画好之后再返回主线程看看当初需要提供内容的cell是否还是visible的,如果是,直接把画好的内容赋给layer的contents属性,这样的好处是同样是自己画,但是却没有使用drawRect,避免Core Animation整个没用的back store bitmap,既浪费内存又浪费CPU,同时主线程没有被阻塞,瓶颈就在GPU上,我的iPhone 4 GPU的性能已经足够给力了,一个高度超过10000points的图片从开始画到内容被GPU转化为屏幕上的像素几秒钟就完成了,同时GPU转化像素的过程非常非常地快,绝对不会超过16ms,所以用户只会看到屏幕一闪,内容就出现了,不会影响滚动,这就导致整个滚动的动画可以非常非常的流畅,达到了我希望的效果。你可以看看我在stackoverflow上的这个回答:

    http://stackoverflow.com/questions/27467351/how-do-i-make-a-part-of-a-uilabel-visually-be-a-block-quote/27631302#27631302

    这段代码是我用来画内容的,我稍微改了一下代码,不过技术是一样的,希望对你有帮助。异步渲染的代码原理就是我说的那个,你看看苹果的那个concurrent guide就行,没啥难的。
    jox
        34
    jox  
    OP
       2014-12-27 01:03:21 +08:00
    @OctWu 另外我的应用是使用了Auto Layout了的,哈,我现在挺喜欢用Auto Layout,刚用的时候挺痛苦,整明白了就觉得挺好用的。
    OctWu
        35
    OctWu  
       2014-12-27 01:06:39 +08:00 via iPhone
    @jox 哈,感觉完爆了我这工作了一年的啊,话说对于官方Guide。会有些不知道从何入手的感觉啊
    jox
        36
    jox  
    OP
       2014-12-27 01:12:36 +08:00
    @OctWu 啊,开始的时候我也觉着看完就跟没看似的,不过当我开始动手写程序的时候就会遇到问题,遇到问题的时候我就会再回去看guide,结合实际遇到的问题就能理解是怎么回事了,你是刚毕业一年吗?我已经毕业快三年啦,在学习iOS应用之前我就有过一些编程经验了,再加上我本科学的是机械类专业,对这种东西感觉能比较好理解吧,毕竟都是在鼓捣东西。
    OctWu
        37
    OctWu  
       2014-12-27 01:16:46 +08:00 via iPhone
    也确实是刚毕业一年……现在独立负责项目。都是逼出来的。跑题了,关于渲染这方面,官方的Guide有推荐么,还有关于哪些行为会block mainthread有详细些的资料么
    jox
        38
    jox  
    OP
       2014-12-27 01:25:17 +08:00
    @OctWu 才一年啊。。。我毕业第一年还没工作呢,到处玩儿。。。

    在主线程进行的所有操作都会阻塞主线程,只不过如果这些操作结束的非常快用户是不会感觉出来的,按照苹果工程师给的数据,16ms,主线程的操作要在16ms内完成用户就不会感觉到卡顿,如果操作需要时间比较长就要考虑放到其他线程去做了,这个就用GCD或者NSOperation,推荐GCD,用起来简单的要死,而且性能卓越。

    我看了好多guide,Core Animation的,Drawing and printing,text programming,core text,quartz(core graphics)。。。跟drawing相关的我都看了,也没啥好推荐的吧,我感觉苹果的guide其实挺烂的,信息碎片化严重,得都看看才能整明白iOS里数据到像素的过程。还看了好几个WWDC的session,主要是2010,2011,2012这三年的。苹果的这些技术名字还瞎取,整明白这些名字都是什么技术就花了我不少的时间,我唯一没看的是open GL ES的文档,那个是用来做游戏用的,我暂时还没有想做的iOS游戏。。你都看看吧,其实你得想明白程序的计算模型和过程是啥样的,然后程序就好写了。。
    OctWu
        39
    OctWu  
       2014-12-27 01:27:50 +08:00 via iPhone
    @jox 哈哈,好,太晚了。扛不住了,先睡了,安
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   2863 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 34ms · UTC 14:05 · PVG 22:05 · LAX 06:05 · JFK 09:05
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.