问题描述:
iOS游戏接了自定义window类SDK或者自定义了window,becomeFirstResponder方法在iOS9、iOS10系统环境下运行能正常调起键盘,但iOS11、iOS12系统环境下无法弹起软键盘。
原因:
SDK中自定义的window或者自定义的Window初始化过程中抢占了系统window成为keyWindow。
分析:
游戏引擎中(如cocos2d)输入框使用的控件是:CCEditBox,查看源码,其实现为:
在ViewController上渲染的GLView添加一个TextField,将其使能为第一响应者。从而弹起软键盘。
此处存在一个问题,若存在自定义Window的情况下,其keyWindow不一定为UIWindow,导致GLView所属ViewController的Window非keywindow,GLView上控件无法响应称为第一响应者的消息。
已知了问题的原因,创建一个Demo复现一下:
新建一个控制器导入window类型的SDK,并初始化完毕,在ViewController中添加一个button和一个textField对象,在按钮的点击方法中实现:
在iOS11-iOS12上输出为:
提示:keyWindow为MainWindow,非UIWindow,此时键盘无法弹出。
修改按钮点击事件实现:
其日志输出为:
至此,已经确定了是KeyWindow导致becomeFirstResponder无法弹起键盘了。
解决方案:
其解决方案有三:
1、若为游戏引擎或者使用第三方的SDK,可以在响应第一响应者消息的方法中增加:
[[UIApplication sharedApplication].windows.firstObject makeKeyWindow];
[[UIApplication sharedApplication].windows.firstObject makeKeyAndVisible];
2、若改window为自定义window:
应在初始化界面完毕后交还keyWindow的所有权,初始化完毕后实现1中的两个方法。
3、简单粗暴的方法是联系第三方SDK的开发者对其进行修改。