iOS 8 move UIView up when keyboard appears | Issue

2019-02-26 19:59发布

问题:

I have a UIView with a UITextField placed at the bottom of the screen which will move up when a keyboard appears.

I have been following the below method prior to iOS 8 and seems to work perfectly.

// When Keyboard appears
- (void)keyboardWillShow:(NSNotification *)notification {

[UIView beginAnimations:nil context:nil];
[UIView setAnimationDuration:[notification.userInfo[UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
[UIView setAnimationCurve:[notification.userInfo[UIKeyboardAnimationCurveUserInfoKey]integerValue]];
[UIView setAnimationBeginsFromCurrentState:YES];

// Frame Update
CGRect frame = self.bottomView.frame;
frame.origin.y = self.view.frame.size.height - 266.0f;
self.bottomView.frame = frame;

[UIView commitAnimations];
}

// When keyboard disappears
- (void) keyboardHides : (NSNotification *) notification {

[UIView beginAnimations:nil context:NULL];
[UIView setAnimationDuration:[notification.userInfo[UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
[UIView setAnimationCurve:[notification.userInfo[UIKeyboardAnimationCurveUserInfoKey] integerValue]];
[UIView setAnimationBeginsFromCurrentState:YES];

// Frame update
CGRect frame = self.bottomView.frame;
frame.origin.y = self.view.frame.size.height - self.bottomView.frame.size.height;
self.bottomView.frame = frame;

[UIView commitAnimations];
}

But the above code doesn't seem to work in iOS 8 as the keyboard blocks the UIView behind it.

After a little research, I found out an almost-similar answer. But here the whole UIView was being pushed up, and what I would like to achieve was just to move the bottom UIView.

回答1:

Get TPKeyboardAvoidingScrollView from https://github.com/michaeltyson/TPKeyboardAvoiding

use it as follows.

drop the TPKeyboardAvoidingScrollView.m and TPKeyboardAvoidingScrollView.h source files into your project, pop a UIScrollView into your view controller's xib, set the scroll view's class to TPKeyboardAvoidingScrollView, and put all your controls within that scroll view. You can also create it programmatically, without using a xib - just use the TPKeyboardAvoidingScrollView as your top-level view.

To disable the automatic "Next" button functionality, change the UITextField's return key type to anything but UIReturnKeyDefault.



回答2:

I'm not sure if this is your problem but you should use the block based APIs to animate a UIView

Example (not tested)

- (void)animateTextField:(UITextField*)textField
                      up:(BOOL)up
{
    const float movementDuration = 0.5f;
    const int movementDistance = 380;
    int movement = (up ? -movementDistance : movementDistance);
    [UIView animateWithDuration:movementDuration
                     animations:
                     ^{
                        CGRect frame = self.bottomView.frame;
                        frame.origin.y = self.view.frame.size.height - 266.0f;
                        self.bottomView.frame = frame;

                     }
    ];
}

You can read in Apple's doc:

Use of this method is discouraged in iOS 4.0 and later. You should use the block-based animation methods to specify your animations instead.

https://developer.apple.com/Library/ios/documentation/WindowsViews/Conceptual/ViewPG_iPhoneOS/AnimatingViews/AnimatingViews.html

Hope it helps you!



回答3:

I used this code. It didn't move up in a scroll view. but changed their XY positions. but this is effective in my iPhone 6. i didn't check them with other iPhones.

 func textViewDidBeginEditing(textView: UITextView){
    textView.frame = CGRectMake(textView.frame.origin.x, textView.frame.origin.y - 216 , textView.frame.size.width, textView.frame.size.height)
    buttonProp.frame = CGRectMake(buttonProp.frame.origin.x, buttonProp.frame.origin.y - 216, buttonProp.frame.size.width, buttonProp.frame.size.height)
     MessageView.frame = CGRectMake(MessageView.frame.origin.x, MessageView.frame.origin.y - 216, MessageView.frame.size.width, MessageView.frame.size.height)
     datePicked.frame = CGRectMake(datePicked.frame.origin.x, datePicked.frame.origin.y - 216, datePicked.frame.size.width, datePicked.frame.size.height)

}

func textViewDidEndEditing(textView: UITextView){
    textView.frame = CGRectMake(textView.frame.origin.x, textView.frame.origin.y + 216, textView.frame.size.width, textView.frame.size.height)
     buttonProp.frame = CGRectMake(buttonProp.frame.origin.x, buttonProp.frame.origin.y + 216, buttonProp.frame.size.width, buttonProp.frame.size.height)
    MessageView.frame = CGRectMake(MessageView.frame.origin.x, MessageView.frame.origin.y + 216, MessageView.frame.size.width, MessageView.frame.size.height)
    datePicked.frame = CGRectMake(datePicked.frame.origin.x, datePicked.frame.origin.y + 216, datePicked.frame.size.width, datePicked.frame.size.height)
}

All my components are programmed to move when editing begins. and move back after editing. manual editing. yes.