前言
为啥我一个做社交、直播、图片后编辑方向的iOS开发突然想学输入法开发呢,这一切还得从我看到搜狗输入法的招聘JD说起....
我看到搜狗输入法的招聘里写到一条:
了解逆向优先
,此时我有个疑问,做输入法App开发和逆向有什么关系? 于是就有了想了解输入法App开发的兴趣,也就有个这篇文章
首先在写这个前言的时候,我是压根不知道输入法怎么开发的。当想到要做一个输入法App时,我有如下疑问
- 为什么安装了搜狗输入法App后,系统键盘设置里会出现搜狗输入法,且有完全访问的选项(UISwith),完全访问是做什么的?
- 为什么安装了搜狗输入法App后,在我自己的App里调起输入法后,调起的是第三方的搜狗输入法键盘
- 搜狗输入法App和搜狗输入法键盘两者之间有什么关联? 如何关联?
- 第三方输入法和逆向之间有什么关联?逆向知识能为输入法类App带来什么?
如果你也有以上疑问,请耐心看下去(其实写到此处时能不能解答我也不知道... 下文均有解答)
本文目录:
- 调研着手
- App实现(简单实现一个能在其它App内使用的输入法App)
- 输入法类App原理
- 输入法App和逆向(个人瞎猜,可能鲁迅人本身根本没这么想)
1. 调研着手
1.1 砸壳
因为了解输入法App的念头起源于逆向
,所以此处我先砸壳,看看什么发现...
在砸完搜狗输入法
壳后,看ipa内部的文件,我并没有看到与其它App有什么区别,无非是icon资源
,infoPlist
,.mpa资源
,Frameworks
、lottie json文件夹
、开启完全访问的.mp4教程
、MJRefresh等第三方库
、/PlugIns/SogouAction.appex
以及mach-o
。
通过ipa,我发现两个关键点:
- 搜狗工程师比较喜欢用plist做配置类数据存储(这点我觉得挺挺好的,便于管理,当然用.json也没问题)
- 在
plugins
路径下,有一个SogouAction.appex
文件,.appex
一般是iOS拓展Extension
生成的文件,比如接入NotificationService
同样会生成push.appex
文件
此时,我对百度输入法
同样进行砸壳操作,发现在PlugIns
文件夹下,同样有BaiduInputMethod.appex
、NotificationContent.appex
这两个.appex结尾的文件
此时根据直觉,我觉得输入法类App的关键在添加了一个类似于inputKeyboard
的拓展Extension
实现
1.2 class-dump
头文件里搜索了SogouAction
仍然一无所获
1.3 Reveal
简单看了下搜狗的UI架构,想通过Reveal看看能不能找出对应的class,结果不但没找到,Reveal里压根没显示出来键盘的UI(键盘是系统层UI,所有Reveal不到)。想到我们的目标是了解如何开发一个输入法App。此时我们暂时停止逆向,直接去百度...
1.3 利用搜索引擎
百度搜到的东西很少,大多是检测键盘弹出高度,只搜到关键性的三篇文章:
其中文章一是苹果官方文档,主要讲构建输入法App用到的API
其中文章二主要将输入法App的App架构与通信,通过此文章我们大概知道为什么搜狗的iOS需要逆向经验
其中文章三是构建一个简单的输入法App
我决定跟着文章三开发一个简单的App,了解其原理
2. App搭建
2.1 创建一个名为InputApp的项目(为了练练手,我们采用OC编码,与链接内不同,后续我应该会创建Swift版本上传Github)
创建项目
2.2 创建键盘Target
拓展Target命名为CustomKeyboard
CustomKeyboard
弹出Activate “CustomKeyboard” scheme?
选择activate
此时我们注意到,添加CustomKeyboard后,默认生成了一个类
KeyboardViewController
image.png
!!! 注意一个很容易忽视的问题:记得修改CustomKeyboard
Target支持的最低版本,如果支持的最低版本高于设备版本,xcode编译时不会报错,但运行时这个target不会运行,添加NotificationService时同样
有这个容易忽视的问题
此时我们启动App,在设置-通用-键盘-添加键盘里能看到我们的自定义键盘,同时,也有开启完全访问的选项
<center class="half">
<img src="https://p6-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/cd521dabf02e448f9c5e13561773e081~tplv-k3u1fbpfcp-watermark.image" width="200"/> <> <img src="https://p6-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/c0064cb4727d40d8b0fc809060529240~tplv-k3u1fbpfcp-watermark.image" width="200"/> <> <img src="https://p9-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/5c3fc8f9bb244e5aa16fb69c8064c84e~tplv-k3u1fbpfcp-watermark.image"
width = "200">
</center>
添加键盘后,我们将键盘切换到我们自定义的键盘,任意App内调起键盘可以看到如图
<center class="half">
<img src="https://p1-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/79496fdbb6cc435b9a24de9928df0e44~tplv-k3u1fbpfcp-watermark.image" width="200"/> <> <img src="https://p1-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/38a51d7209194ab1a071807cb8146a25~tplv-k3u1fbpfcp-watermark.image" width="200"/>
</center>
此时弹出我们的自定义键盘,可以看到,键盘有一个添加Extension时默认生成代码的button。我们将会在KeyboardViewController
类里做键盘的自定义布局