获取内容资料
iOS开发

ios 第三方输入法开发教程

搜狗输入法 iOS 版负责人 李腾杰

请介绍一下您和目前的工作,以及关注/正在研究的技术。

李腾杰: 我目前在搜狗公司从事 iOS 平台搜狗输入法的相关研发工作,重点关注输入法关键性能指标(如键盘调起速度、内存、CPU 等)和代码架构的优化。同时,也在研究 Swift 3,在合适的时间点安排项目适配 Swift 3。

在 iOS 开发新的技术点方面,搜狗输入法 iOS 版开发团队有着怎样的尝试与实践?

李腾杰: 在 iOS 动态更新方案上,我们跟进了对 JSPatch 和 React Native 的调研,最后根据输入法的项目实际情况,择选 JSPatch 应用于输入法,完成了输入法热更新的工作。JSPatch 集成较为简单,是一种应用较广泛的热修复解决方案,它可以通过服务器后台下发 JavaScript 脚本,实时修改 Objective-C 方法的实现,达到修复 Bug 和动态运营的目的。

由于 JSPatch 存在性能方面的限制,实际项目中仅用于做一些轻量级代码的修复,并没有频繁的使用。考虑到安全性,输入法自行部署了服务器后台来分版本管理下发的脚本,针对键盘扩展和其容器 App 两种类型的下发脚本。同时,由于输入法键盘扩展的特殊性,受到键盘允许完全访问控制权限的影响,输入法尝试了通过键盘容器 App 来获取修复脚本,借由相同 Group 的共享目录来影响键盘。在输入法关键性能指标的优化上,我们也跟进了 FBRetainCycleDetector(Facebook开源的一个内存泄漏检测解决方案)、FastImageCache(Path 团队开发的一个开源库,用于提升图片的加载和渲染速度)的调研,并运用于项目实践,优化产出效果较好,确实发现了一些代码实现中的问题,并改进了输入法换肤的稳定性。

在搜狗输入法 iOS 版研发与更新过程中,遇到过哪些比较棘手的问题,如何解决的?

李腾杰: 最棘手的问题,往往是和 iOS 系统相关的,这里举一个输入法遇到的字符绘制产生的诡异崩溃。我们在分析输入法收集的崩溃日志时,曾经遇到一种特别诡异的崩溃,从崩溃栈来看是崩溃在候选绘制上,其占比也挺大,直接影响到输入法的稳定性。单纯分析崩溃栈对应的代码调用,并没有任何问题,也确认了并不是内存越界等造成的崩溃,我们尝试了各种自动化评测或人工操作方案,都没能复现该崩溃。经过初步分析,怀疑是和系统绘制某些特定字符异常导致的崩溃,于是就对崩溃日志收集进行了改进,增加了对崩溃异常时当前候选内容的收集,上线版本后通过收集的崩溃日志,发现对应的候选内容在绘制时并没有任何问题。

鉴于这种情况,我们在原有自动化评测的基础上,单独抽调一台 iMac 机器,通过 Xcode 真机调试的方式来分多个机型和系统进行更细致的评测,最终在其中一台测试机器上发现了类似崩溃。且发生崩溃时,在 Xcode 上看到的当前绘制候选字符是一个表示“哭”的颜文字表情。一般情况下绘制该表情并不会有什么问题,我们在该机型上又持续进行了三次长时间的模拟输入评测,有一次崩溃还是与该表情相关。根据这个情况,我们在后续的上线版本中,从词库中剔除了该表情,根据后台监测到的崩溃情况,这个困扰许久的崩溃问题终于得到解决。最终分析结论是 iOS 系统在某些条件下绘制该复杂的表情可能会产生崩溃,而为何会如此,一直也没弄清楚,虽然这个崩溃确实是修复了。

中文字体文件大,以 Webfonts 的方式加载困难加载比较困难,搜狗输入法是怎么优化的?

李腾杰: 由于中文字体比较大,且从 iOS 8 开始被系统一旦加载,并不能立即释放,而是由系统决定在什么时机释放,且不能完全释放。针对这种情况,搜狗输入法的候选词绘制并没有开放让用户自定义,而是根据不同的 iOS 系统,使用其默认的系统字体;输入法在皮肤个性化里,允许皮肤作者自定义键盘区域的文本显示字体,并建议皮肤作者将该皮肤对应的字体文件包含的字符集控制在最小够用,避免字体太大导致皮肤下载流量和内存占用的增加。如果输入法被启用的皮肤没有指定字体,则输入法使用当前系统的默认字体。上述方案是输入法认真权衡用户输入性能优先,并兼顾输入法皮肤功能多样性之后,得到的一个优化方案,也避免了中文字体过大对输入法性能带来的压力。

在输入法框架方面,搜狗输入法是如何实现不同平台代码复用的?

李腾杰: 搜狗输入法会将某些不同平台共有的基础模块(如输入法内核)使用C/C 来实现,并用宏分隔开平台相关的某些具体 API 实现,封装成统一的接口来供平台调用。在更新某些模块的功能实现时,对平台调用始终透明,尽量保证接口的一致性。

搜狗输入法的内核模块,划分了接口层、功能逻辑层和设备层三个层次,接口层对应平台代码调用,接口一般相对较为固定,除非大的功能调整才变化。功能逻辑层封装了具体的内核功能逻辑的实现代码,对各个平台是透明的,主要用于接口层的调用。设备层封装了与平台相关的某些API实现,不同平台会有不同的技术实现,如字符串操作、文件操作等,供功能逻辑层调用,一般很少变化。通过这三个层次的封装,内核实现某个新功能时,一般只需要调整功能逻辑层的实现,然后通过内核自动化测试工具来完成测试,就可以方便地提供给各个平台使用,平台调用也不用做什么接口层的更改。

搜狗输入法的 Emoji、颜文字一直以来都颇受用户喜爱,使用率非常高,在这方面你们做了哪些工作?

李腾杰: 在不同的 iOS 系统上,Emoji 表情的显示效果可能会有差异,且随着 iOS 系统的更新,Emoji 表情编码也会有新增或更改,这就要求输入法始终关注每个 iOS 系统的 Emoji 全集,及时更新到输入法中。搜狗输入法通过自动化评测的手段来分析每个 iOS 版本其系统表情键盘的 Emoji 表情全集,看是否有新的变化,并及时跟进更新。同时,Emoji、颜文字等表情字符的绘制又比较消耗资源,输入法尝试了提前将字符绘制成图片打包的方式来解决实时绘制表情字符造成的内存压力;并考虑到相同 Emoji 编码在不同 iOS 系统上的显示效果差异,又调研了在 iOS 9 及以上系统绘制 Emoji 表情不缓存的技术解决方案,将图片和绘制两种方式结合使用,保证了 Emoji 和颜文字表情功能的良好性能。除此之外,输入法提供了表情商城,用户可以在里面很方便地下载到颜文字表情包、图片表情等,大大丰富了用户的输入体验。

Emoji、颜文字功能内存方面的优化实践,在后续的 MDCC 2016 移动开发者大会上会详细介绍。

从 2009 年加入搜狗从事输入法的相关研发工作至今,从您的亲身实践来看,iOS 系统对于第三方输入法研发的支持有着怎样的改进与发展?就目前而言,在开发过程中,还有哪些特别想吐槽的限制?

李腾杰: iOS 系统在 iOS 8 上才开始开放第三方输入法的研发,在这之前,只能通过越狱的方式来进行第三方输入法的研发,Hook 系统输入法相关的 API 来实现输入法的功能。越狱方式开发输入法不容易,每每 iOS 系统更新,第三方输入法都需要及时跟进,调研该 iOS 系统输入法相关 API 是否有变更,并在新的越狱工具出来之后,以最快的速度去跟进适配,保证用户率先用上最稳定的输入法。

但越狱输入法由于 iOS 系统的限制,性能和稳定性方面难免存在一些避免不了的问题,很难将输入法体验做到完美。且越狱输入法的安装门槛也比较高,阻隔了很大一部分用户的第三方输入法需求。从 iOS 8 开始,iOS 系统对第三方输入法的研发提供了支持,接口也比较稳定,开发者在适配不同 iOS 系统上耗费的精力也少了很多,广大用户也能很便捷地通过 App Store 安装自己想要的输入法,皆大欢喜的场面。

即便如此,iOS 系统至今仍有的某些限制,仍给第三方输入法造了不少麻烦事儿,主要有以下三个点:

首先,是系统第三方自定义键盘框架的稳定性不够,诸如升级输入法后旧版本的输入法进程仍存在、未能及时更新导致某些界面显示异常或崩溃;键盘无法调起;键盘需要重新添加等等,都给用户体验造成了较大影响,而第三方输入法又无能为力。

其次,是iOS系统对第三方键盘的诸多限制,如允许完全访问控制权限的限制,限制了用户需要开启入口隐蔽的权限开关,才能体验到输入法的某些特色功能;而且,由于iOS系统的限制,第三方键盘并没有如系统键盘一样被系统一视同仁,键盘调起体验始终无法像系统键盘那么流畅。

再者,是iOS系统对第三方键盘的资源使用限制比普通App更为严格,一旦第三方键盘使用的内存被它认为较多或系统内存紧张,就会直接kill键盘进程,切换成其它输入法,直接影响了输入法的稳定性,也对输入法开发的性能优化提出了相比越狱输入法更高的挑战。

根据您的经验,当前在开发第三方 iOS 输入法方面,开发团队所面临的主要挑战是什么?在此过程中又容易陷入怎样的误区?

李腾杰: 输入法不同于普通 App 的开发,对性能非常敏感,开发团队面临的主要挑战是兼顾功能效率的同时如何充分保障性能,并让每个开发组员都对性能足够敏感和关注。在实际项目过程中,针对某些涉及敏感性能的技术实现方案,可能会涉及到新技术的使用,需要避免“它性能应该没问题”这种猜测方式,通过评测来评估新技术的性能如何,这看起来有点麻烦,但确实省不得。

输入法在最初适配不同键盘尺寸的按键布局时,使用了 Autolayout 的解决方案,Autolayout 方法简单、强大易用、可读性强,但是 updateConstraints 调用时

Similar Posts

发表评论

邮箱地址不会被公开。 必填项已用*标注