Incorrect height of iPad floating keyboard

I'm using the following code to get the height of the keyboard:

class ViewController: UIViewController {
    override func viewDidLoad() {
        super.viewDidLoad()
        NotificationCenter.default.addObserver(
            self,
            selector: #selector(keyboardHeight),
            name: UIResponder.keyboardDidChangeFrameNotification,
            object: nil
        )
    }

    @objc private func keyboardHeight(notification: Notification) {
        guard let keyboardRect = (notification.userInfo?[UIResponder.keyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue else { return }

        print("==> keyboardFrameEndUserInfoKey height: \(keyboardRect.size.height)")

    }
}

This code on iPad work correctly when the keyboard is normal but it does not work when the keyboard is floating.

After the user tap on a text field, the keyboard appear and the keyboardDidChangeFrameNotification notification is called.

If the keyboard is floating then the first time we get a wrong height of 362. If the user then manually move somewhere the floating keyboard the notification is called again and the correct value of 308 is returned.

It is a bug or I miss something? I need to be able to get the correct height the first time the keyboard appear.

This is happening on iOS 13 and iOS 14.

Any idea?

That seems to be an old issue with keyboard size.

I filed a bug, in 2018 (radar ID 38117524 - FB5721145) for keyboard size issues.

Here's an abstract:

Value for keyboard height returned by

 note.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue 

is erroneous after turning iPad from Portrait to Landscape

  • This is for a numeric keypad on iPad (numbers at top, special characters below, help line at the top).
  • This occurs both on device and in Xcode simulator

Steps to Reproduce:

  • On iPad, select numeric keypad (numbers at top, special characters below, help line at the top), for a textField
  • In keyboardWillShow, get the keyboard size, and ask for printing it :
    @objc func keyboardWillShow(_ note : Notification) -> Void {  
          if let keyboardSize = (note.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue {  
                    print("keyboardSize", keyboardSize)  
  • Start in landscape,
  • click on field to show keyboard,
  • then turn portrait then return landscape, the keyboard staying displayed on screen.

Expected Results:

  • Height should be 398 when returning to landscape
  • Actual Results:
Height is 142 after returning to landscape.
keyboardSize (0.0, 768.0, 1024.0, 398.0)     // Landscape, seems correct
keyboardSize (0.0, 1024.0, 768.0, 313.0)     // Portrait, effectively smaller in height
keyboardSize (0.0, 768.0, 1024.0, 142.0)     // Return to landscape: height is now clearly wrong
keyboardSize (0.0, 626.0, 1024.0, 142.0)     // Note: keyboardWillShow is called a second time and removes 142.0 from origin.y.

Version/Build: IOS 11.2.5 (15D100) Xcode Version 9.2 beta (9C34b) OSX Version 10.13.3 (17D102)

Incorrect height of iPad floating keyboard
 
 
Q