约束不使用导航控制器

时间:2017-12-02 17:30:39

标签: ios swift keyboard constraints navigationcontroller

我会尽量尽快。我有一个主视图,其中一个容器的高度为0,每当键盘启用时,我将容器设置为与键盘相同的高度,我有一个按钮和一个电子邮件字段,我已经为这个容器设置了约束,基本上推动元素。我已经将键盘设置为在加载视图时启用,并且在主视图下工作正常但是只要按下按钮转到下一个视图,键盘就会打开,但按钮和电子邮件字段会保留在键盘后面因为约束不起作用,但当我按下主页按钮并关闭应用程序(而不是从后台)并重新打开它时,约束工作正常。这只有在我将导航控制器嵌入主视图时才会发生,否则它会完美地工作。有什么想法吗?

我在两个视图上都有完全相同的代码。 Ps:对不起,我不知道如何解释它。

@IBOutlet weak var emailTF: UITextField!

@IBOutlet weak var bottomHeight: NSLayoutConstraint!`

override func viewWillAppear(_ animated: Bool)
{
    super.viewWillAppear(animated)

    NotificationCenter.default.addObserver(
        self,
        selector: #selector(keyboardWillShow),
        name: NSNotification.Name.UIKeyboardWillShow,
        object: nil
    )

    // Show keyboard by default
    emailTF.becomeFirstResponder()
}

@objc func keyboardWillShow(_ notification: Notification)
{
       if let userInfo = notification.userInfo
    {
        if let keyboardSize = (userInfo[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue
        {
            bottomHeight.constant = keyboardSize.height
            view.setNeedsLayout()
        }
    }
}

更新:我发现了部分问题。 当加载第二个视图时我无法获得键盘高度,我将第二个视图代码从“viewWillAppear”更改为“viewDidAppear”,使容器与键盘高度相同,但还有另一个问题。当我加载第一个视图时,键盘高度为271(这是正确的),当我移动到第二个视图时,由于某种原因键盘高度为226,使textField移动45.同样的事情发生在我按下后退按钮从第二个视图返回到第一个,键盘高度是226.当我按下主页按钮并重新打开应用程序时,无论我在哪个屏幕上都得到键盘高度为271,这是正确的高度。我做错了什么?

更新2:已解决!

因为我的代码只在没有导航控制器的情况下工作,我感觉这是导航控制器具有快速动画和转换的东西,并且它阻止了代码在加载之前被读取,所以我试着写这行代码 emailTF.resignFirstResponder()我的按钮操作,它工作了!所以基本上我不得不在下一个视图中加载之前解除键盘。我希望我帮助一些用户遇到同样的问题。

2 个答案:

答案 0 :(得分:0)

首先确保包含正在更改的视图的VC是textfield / textview的委托,然后从viewWillAppear调用.becomeFirstResponder()。确保正确注册/取消注册键盘通知。如果可能的话,您可以使用滚动视图(在默认的UIView上)来包含ViewControllers子视图,而不是更改约束。

func registerForKeyboardNotifications(){
    //Adding notifies on keyboard appearing
    NotificationCenter.default.addObserver(forName: Notification.Name.UIKeyboardWillShow, object: nil, queue: nil, using: keyboardWasShown)
    NotificationCenter.default.addObserver(forName: Notification.Name.UIKeyboardWillHide, object: nil, queue: nil, using: keyboardWillBeHidden)
}

func deregisterFromKeyboardNotifications(){
    //Removing notifies on keyboard appearing
    NotificationCenter.default.removeObserver(self, name: Notification.Name.UIKeyboardDidShow, object: nil)
    NotificationCenter.default.removeObserver(self, name: Notification.Name.UIKeyboardWillHide, object: nil)
}

func keyboardWasShown(notification: Notification) -> Void {
    //Need to calculate keyboard exact size due to Apple suggestions
    self.scrollView.isScrollEnabled = true
    var info = notification.userInfo!
    var keyboardSize:CGRect = (info[UIKeyboardFrameBeginUserInfoKey] as! NSValue).cgRectValue
    if keyboardSize.size.height <= 0 { // to fix bug on iOS 11
        keyboardSize = (info[UIKeyboardFrameEndUserInfoKey] as! NSValue).cgRectValue
    }
    self.scrollView.contentInset.bottom = keyboardSize.height //add this much
    self.scrollView.scrollIndicatorInsets.bottom = keyboardSize.height //scroll too it.

    var aRect : CGRect = self.view.frame
    aRect.size.height -= keyboardSize.height
    if let activeField = self.activeTextView {
        if (!aRect.contains(activeField.frame.origin)){
            self.scrollView.scrollRectToVisible(activeField.frame, animated: true)
        }
    }
}

func keyboardWillBeHidden(notification: Notification){
    self.scrollView.contentInset.bottom = 0
    self.scrollView.isScrollEnabled = true
    self.scrollView.alwaysBounceVertical = true
}

答案 1 :(得分:0)

使用这行代码self.view.layoutIfNeeded()而不是view.setNeedsLayout()

确保键盘的高度与正确的高度有关。

谢谢!