我在一个多星期前提交了应用,今天收到了可怕的拒绝邮件。它告诉我,我的应用程序不能被接受,因为我使用的是非公共API;具体来说,它说,
应用程序中包含的非公共API是firstResponder。
现在,违规的API调用实际上是一个解决方案,我发现这里的SO:
UIWindow *keyWindow = [[UIApplication sharedApplication] keyWindow];
UIView *firstResponder = [keyWindow performSelector:@selector(firstResponder)];
如何在屏幕上显示当前的第一响应器?我正在寻找一种不会让我的应用程序被拒绝的方法。
第一响应者可以是类UIResponder的任何实例,所以有其他类可能是第一响应者,尽管有UIViews。例如,UIViewController也可能是第一响应器。
在这个要点中,您将找到一种递归方法,通过从应用程序窗口的rootViewController开始循环遍历控制器层次结构来获得第一个响应器。
你可以通过这样来检索第一个响应器
- (void)foo
{
// Get the first responder
id firstResponder = [UIResponder firstResponder];
// Do whatever you want
[firstResponder resignFirstResponder];
}
然而,如果第一响应器不是UIView或UIViewController的子类,这种方法将失败。
为了解决这个问题,我们可以采用不同的方法,在UIResponder上创建一个类别,并执行一些神奇的旋转,以便能够构建一个包含该类所有活实例的数组。然后,为了获得第一个responder,我们可以简单地迭代并询问每个对象是否-isFirstResponder。
这种方法可以在另一个要点中找到实现。
希望能有所帮助。
找到第一响应者的最简单方法:
func sendAction(_ action: Selector, to target: Any?, from sender: Any?, for event: UIEvent?) -> Bool
默认实现将动作方法分派给给定对象
目标对象,如果没有指定目标,则发送给第一个响应器。
下一步:
extension UIResponder
{
private weak static var first: UIResponder? = nil
@objc
private func firstResponderWhereYouAre(sender: AnyObject)
{
UIResponder.first = self
}
static var actualFirst: UIResponder?
{
UIApplication.shared.sendAction(#selector(findFirstResponder(sender:)), to: nil, from: nil, for: nil)
return UIResponder.first
}
}
用法:
只需要获取UIResponder。首先是为了你自己的目的。