0

How is this done? I'm looking for iOS7/8 solutions. keyboardWillShow is not satisfactory because I need to resize a view based on the keyboard height before the keyboard actually shows.

StefanS
  • 1,089
  • 1
  • 11
  • 38
po.studio
  • 4,007
  • 5
  • 25
  • 37
  • are trying to adjust super view to show the selected input? If yes, you are using UIScrollView, arent you? – Klevison Aug 05 '15 at 14:41
  • trying to adjust height of a text box, which should be variable based on the size of the phone. – po.studio Aug 05 '15 at 14:42
  • i can do this easily *after* the keyboard is shown, but i don't want it animated. i want the size of the box to be determined before the box actually appears – po.studio Aug 05 '15 at 14:42
  • So, have you tried `UIKeyboardWillShowNotification`? – Klevison Aug 05 '15 at 14:45
  • yes - i have tried UIKeyboardWillShowNotification, but i don't think this solves my problem for trying to determine the keyboard height and adjusting the UIView based on this height *before* it shows – po.studio Aug 05 '15 at 14:47
  • i'm trying to adjust a UIView, not UIScrollView – po.studio Aug 05 '15 at 14:48
  • Why don't you think the `UIKeyboardWillShowNotification` is satisfactory. It includes details about what the keyboard's final frame will be. Just what you need to adjust the view. – rmaddy Aug 05 '15 at 15:36
  • i don't like the way the view animates from large down to small when the keyboard opens - i want it to be sized before it or the keyboard appears – po.studio Aug 05 '15 at 15:37

2 Answers2

1

keyboardWillShow is fired before the keyboard is shown. If that's not satisfactory for you, then you'll need to be smart about the keyboard size.

If the keyboard has never been shown on screen in your app before, you can make an educated guess by first checking for the device type and orientation and then having a quick lookup table of the default keyboard sizes. This will cover you 99% of the time.

In the event that the user has a custom keyboard in use that is not a standard size, you can use the keyboard size from keyboardWillShow, store it and the orientation (NSUserDefaults would work well here) and then reference the stored value the next time you need the size.

This wouldn't cover your needs every time because you wouldn't know which keyboard is going to be pulled up until keyboardWillShow is called. For example, you could replace the inputView on two different UITextField's with your own custom views; those views could be different sizes. You wouldn't know which one was going to be shown until keyboardWillShow would be called.

EDIT

There is another possibility...if you know the view that you want to show the keyboard for explicitly.

I added this to viewDidLoad:

[[NSNotificationCenter defaultCenter] addObserver:self
                                         selector:@selector(keyboardWillShowFirstTimeNotification:)
                                             name:UIKeyboardWillShowNotification
                                           object:nil];
[self.view addSubview:self.textField];
[self.textField becomeFirstResponder];

Then, add a method for handling that notification. This method should only be called once and then inside of it remove the notification so it's never called again.

- (void)keyboardWillShowFirstTimeNotification:(NSNotification*)notification {
    NSDictionary* keyboardInfo = [notification userInfo];
    NSValue* keyboardFrameBegin = [keyboardInfo valueForKey:UIKeyboardFrameBeginUserInfoKey];
    CGRect keyboardFrameBeginRect = [keyboardFrameBegin CGRectValue];

    NSLog(@"keyboardFrameBeginRectHeight: %f", keyboardFrameBeginRect.size.height);

    [[NSNotificationCenter defaultCenter] removeObserver:self];
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(keyboardWillShow)
                                                 name:UIKeyboardWillShowNotification
                                               object:nil];
    [self.textField resignFirstResponder];
}

This will log the keyboard height without ever showing it on screen.

If you wanted to extend this further, you could subclass UITextField and UITextView to have properties for keyboard height for different orientations and then you could store that value directly in the text fields and text views. Then, you'd be able to have multiple input view sizes and know what they will be prior to showing them.

Community
  • 1
  • 1
Fennelouski
  • 2,411
  • 1
  • 18
  • 26
0

Currently the time for the keyboard to show is 0.3 seconds, but Apple may change that at any time. This is also true for the keyboard size. The default keyboard in portait mode is 216px in height and in landscape it is 162px, but that may also change at any time. If (for any reason) you need to find out the keyboard size you can do that pretty easily.

   [[NSNotificationCenter defaultCenter] addObserver:self
                                    selector:@selector(keyboardWillShow:)
                                        name:UIKeyboardWillShowNotification
                                      object:nil];

    // Read the userInfo for the key UIKeyboardFrameBeginUserInfoKey
    -(void)keyboardWillShow:(NSNotification*)notification {
        NSDictionary* keyboardInfo = [notification userInfo];
        NSValue* keyboardFrameBegin = [keyboardInfo valueForKey:UIKeyboardFrameBeginUserInfoKey];
        CGRect keyboardFrameBeginRect = [keyboardFrameBegin CGRectValue];

        NSLog(@"%@", NSStringFromCGRect(keyboardFrameBeginRect));
    }
Klevison
  • 3,342
  • 2
  • 19
  • 32
  • 1
    Well, the size is not 216 px because the keyboard may contain the dictionary (from iOS8 and above), and the user may change it whenever he want. If the user will close or open the dictionary, the notification will fire again and the keyboard rect will contain the new relevant value. – Yedidya Reiss Aug 05 '15 at 15:01