iPhone X how to handle View Controller inputAccessoryView?

前端 未结 15 2655
长情又很酷
长情又很酷 2020-11-30 00:43

I have a messaging app that has the typical UI design of a text field at the bottom of a full screen table view. I am setting that text field to be the view controller\'s

15条回答
  •  小蘑菇
    小蘑菇 (楼主)
    2020-11-30 01:18

    inputAccessoryView and safe area on iPhone X

    • when the keyboard is not visible, the inputAccessoryView is pinned on the very bottom of the screen. There is no way around that and I think this is intended behavior.

    • the layoutMarginsGuide (iOS 9+) and safeAreaLayoutGuide (iOS 11) properties of the view set as inputAccessoryView both respect the safe area, i.e on iPhone X :

      • when the keyboard is not visible, the bottomAnchor accounts for the home button area
      • when the keyboard is shown, the bottomAnchor is at the bottom of the inputAccessoryView, so that it leaves no useless space above the keyboard

    Working example :

    import UIKit
    
    class ViewController: UIViewController {
    
        override var canBecomeFirstResponder: Bool { return true }
    
        var _inputAccessoryView: UIView!
    
        override var inputAccessoryView: UIView? {
    
            if _inputAccessoryView == nil {
    
                _inputAccessoryView = CustomView()
                _inputAccessoryView.backgroundColor = UIColor.groupTableViewBackground
    
                let textField = UITextField()
                textField.borderStyle = .roundedRect
    
                _inputAccessoryView.addSubview(textField)
    
                _inputAccessoryView.autoresizingMask = .flexibleHeight
    
                textField.translatesAutoresizingMaskIntoConstraints = false
    
                textField.leadingAnchor.constraint(
                    equalTo: _inputAccessoryView.leadingAnchor,
                    constant: 8
                ).isActive = true
    
                textField.trailingAnchor.constraint(
                    equalTo: _inputAccessoryView.trailingAnchor,
                    constant: -8
                ).isActive = true
    
                textField.topAnchor.constraint(
                    equalTo: _inputAccessoryView.topAnchor,
                    constant: 8
                ).isActive = true
    
                // this is the important part :
    
                textField.bottomAnchor.constraint(
                    equalTo: _inputAccessoryView.layoutMarginsGuide.bottomAnchor,
                    constant: -8
                ).isActive = true
            }
    
            return _inputAccessoryView
        }
    
        override func loadView() {
    
            let tableView = UITableView()
            tableView.keyboardDismissMode = .interactive
    
            view = tableView
        }
    }
    
    class CustomView: UIView {
    
        // this is needed so that the inputAccesoryView is properly sized from the auto layout constraints
        // actual value is not important
    
        override var intrinsicContentSize: CGSize {
            return CGSize.zero
        }
    }
    

    See the result here

提交回复
热议问题