简体   繁体   English

旋转后键盘扩展高度不正确

[英]Incorrect Keyboard Extension height after rotation

I have iOS custom keyboard that changes height when it rotates. 我有iOS自定义键盘,可在旋转时更改高度。

My code works fine 95% times... But in some cases (see below) the height is not changed when rotated to landscape - portrait height is kept. 我的代码可以在95%的时间内正常工作...但是在某些情况下(见下文),旋转到横向时高度不会改变-保持纵向高度。

Issue can be reproduced with this (almost) minimal code - create new Keyboard Extension target and copy this code to KeyboardViewController : 可以用此(几乎)最少的代码来复制问题-创建新的Keyboard Extension目标并将此代码复制到KeyboardViewController

class KeyboardViewController: UIInputViewController {
    private var orangeView = UIView()
    private var heightConstraint: NSLayoutConstraint!
    @IBOutlet var nextKeyboardButton: UIButton!

    override func updateViewConstraints() {
        super.updateViewConstraints()
        let screenSize = UIScreen.mainScreen().bounds.size
        let screenH = screenSize.height
        let screenW = screenSize.width
        let isLandscape = !(self.view.frame.size.width == screenW * ((screenW < screenH) ? 1 : 0) + screenH * ((screenW > screenH) ? 1 : 0))
        let desiredHeight: CGFloat = isLandscape ? 193 : 252
        if heightConstraint.constant != desiredHeight {
            heightConstraint!.constant = desiredHeight
            orangeView.frame = CGRect(x: 0, y: 0, width: screenW, height: isLandscape ? 193 : 252)
        }
    }

    override func viewDidLoad() {
        super.viewDidLoad()
        nextKeyboardButton = UIButton(type: .System)
        nextKeyboardButton.setTitle("Next Keyboard", forState: .Normal)
        nextKeyboardButton.sizeToFit()
        nextKeyboardButton.translatesAutoresizingMaskIntoConstraints = false
        nextKeyboardButton.addTarget(self, action: "advanceToNextInputMode", forControlEvents: .TouchUpInside)
        heightConstraint = NSLayoutConstraint(item:self.inputView!, attribute:.Height, relatedBy:.Equal, toItem:nil, attribute:.NotAnAttribute, multiplier: 0.0, constant: 0) //preparing heightConstraint
        heightConstraint?.priority = 999
        orangeView.backgroundColor = UIColor.orangeColor()
        view.addSubview(orangeView)
        view.addSubview(self.nextKeyboardButton)
        let nextKeyboardButtonLeftSideConstraint = NSLayoutConstraint(item: self.nextKeyboardButton, attribute: .Left, relatedBy: .Equal, toItem: self.view, attribute: .Left, multiplier: 1.0, constant: 0.0)
        let nextKeyboardButtonBottomConstraint = NSLayoutConstraint(item: self.nextKeyboardButton, attribute: .Bottom, relatedBy: .Equal, toItem: self.view, attribute: .Bottom, multiplier: 1.0, constant: 0.0)
        view.addConstraints([nextKeyboardButtonLeftSideConstraint, nextKeyboardButtonBottomConstraint])
    }

    override func viewWillAppear(animated: Bool) {
        if self.view.constraints.filter({c in c == self.heightConstraint}).isEmpty {
            self.view.addConstraint(heightConstraint)
        }
        view.setNeedsUpdateConstraints() //ensures that updateViewConstraints always gets called at least once
        super.viewWillAppear(animated)
    }
}

For more info on how it works see this and this answer. 有关它是如何工作的详细信息请参见这个答案。

When you run the keyboard it will probably work fine - it is slightly higher and after rotation the orange view covers the whole keyboard: 运行键盘时,它可能会正常工作-稍微高一点,旋转后,橙色视图将覆盖整个键盘:

在此处输入图片说明

However you might also get this (portrait height is kept after rotation): 但是,您也可能会得到以下信息(旋转后保持肖像高度):

在此处输入图片说明

Steps to reproduce the isue (with code above): 重现此问题的步骤(上面的代码):

  1. Open keyboard in Messages app, rotate landscape and back 在“消息”应用中打开键盘,旋转横向和向后
  2. If you did not see the issue kill Messages app (press home button 2x -> swipe messages up) 如果您没有看到问题,请杀死消息应用程序(按两次主屏幕按钮->向上滑动消息)
  3. Open messages again, rotate landscape and back 再次打开邮件,旋转风景并返回
  4. You might need to repeat steps 1-3 few times to see the issue (usually no more than 2-4 times) 您可能需要重复1-3几次才能看到此问题(通常不超过2-4次)

What I know: 我知道的:

  • If you see the issue you will keep seing it until keyboard is hidden and re-displayed 如果您看到此问题,将一直关注它,直到隐藏并重新显示键盘
  • If you see the issue hide and re-display the keyboard withing same app - the issue always disapears 如果您发现问题隐藏并使用同一应用重新显示键盘-问题总是消失
  • The issue might appear again only after killing and restarting the hosting app 仅在终止并重新启动托管应用后,该问题才可能再次出现
  • Debuger shows that heightConstraint!.constant is 193 but both view.frame.height and view.window?.frame.height are still 253 (changing frame directly does not fix it) 调试器显示heightConstraint!.constant193view.frame.heightview.window?.frame.height仍为253 (直接更改框架不能解决问题)

What I have tried: 我尝试过的

  • Instead of just setting the constraint heightConstraint!.constant = desiredHeight first remove it from view , set new value and then re-add it 而不是仅设置约束heightConstraint!.constant = desiredHeight首先将其从view删除,设置新值,然后重新添加
  • I verified that heightConstraint!.constant is always changed when it should be 我验证了heightConstraint!.constant始终在应更改的时间进行了更改

How do I fix or workaround this issue? 如何解决或解决此问题? There has to be a solution because SwiftKey does not have this issue. 因为SwiftKey没有这个问题,所以必须有一个解决方案。

I faced a similar issue with a keyboard extension -- on iPhone 6+ models, it always failed to set its height correctly on rotations the first time the keyboard was invoked in an app, and occasionally on iPhone 6 and other iPhone models. 我在键盘扩展方面也遇到了类似的问题-在iPhone 6+机型上, 首次在应用程序中调用键盘时,旋转时总是无法正确设置其高度,偶尔在iPhone 6和其他iPhone机型上也是如此。

I eventually found a solution, though it has its own drawbacks. 我最终找到了一个解决方案,尽管它有其自身的缺点。

Firstly, the documentation states that 首先,文档指出

In iOS 8.0, you can adjust a custom keyboard's height any time after its primary view initially draws on screen. 在iOS 8.0中,您可以在主视图最初显示在屏幕上后的任何时间调整自定义键盘的高度。

You're setting the height constraint in -[UIViewController viewWillAppear:] , which, under a strict interpretation of the documentation, is too early. 您要在-[UIViewController viewWillAppear:]设置高度限制,根据文档的严格解释,这还为时过早。 If you set it in -[UIViewController viewDidAppear:] , the problem that you're currently having should be solved. 如果在-[UIViewController viewDidAppear:] ,则应该解决当前遇到的问题。

However, you may then find that your height adjustment is visually jarring, as it is occurring after the keyboard is appearing. 但是,然后您可能会发现高度调整在视觉上令人讨厌,因为它出现在键盘出现之后。

I have no idea how SwiftKey manages to set their height (seemingly) before the keyboard appears and avoid this issue. 我不知道SwiftKey如何在键盘出现之前设法(似乎)设置其高度避免出现此问题。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM