Перемещение клавиатуры при редактировании UITextField на iOS9
Чтобы мои клавиатуры поднялись вверх, чтобы открыть UITextField
в моем приложении iOS, я использовал этот ответ: qaru.site/info/749/... на iOS7 и 8, и он отлично работала. Однако на iOS 9.1 он больше не работает.
Чтобы быть более точным, даже если фоновый вид перемещается вверх, UITextField
не работает.
Любая идея о том, что так сильно изменилось с iOS9 и iOS 9.1?
Ответы
Ответ 1
Ответ, который вы связали, не рекомендуется. Вы не должны устанавливать рамку просмотра контроллера просмотра напрямую, особенно если вы используете автоматическую компоновку. Вместо того, чтобы менять рамку представления, вы должны добавить scrollview в качестве подсмотра в представление и отрегулировать вставку содержимого, когда клавиатура будет показана или скрыта.
Из официального яблока doc:
Когда его попросят отобразить клавиатуру, система переместит ее в нижней части экрана и позиционирует ее поверх содержимого вашего приложения. Поскольку он размещается поверх вашего содержимого, клавиатуру можно разместить поверх текстового объекта, который пользователь хотел изменить. Когда это произойдет, вы должны настроить свой контент таким образом, чтобы целевой объект оставался видимым.
Корректировка содержимого обычно включает временное изменение размера одного или нескольких видов и их размещение таким образом, чтобы текстовый объект оставался видимым. Самый простой способ управлять текстовыми объектами с помощью клавиатуры - встраивать их в объект UIScrollView (или один из его подклассов, например UITableView). Когда клавиатура отображается, все, что вам нужно сделать, это reset область содержимого прокрутки и прокрутка нужного текстового объекта в нужное положение. Таким образом, в ответ на UIKeyboardDidShowNotification, ваш метод обработчика будет делать следующее:
- Получить размер клавиатуры.
- Отрегулируйте нижнюю вставку содержимого вашего вида прокрутки по высоте клавиатуры.
- Прокрутите целевое текстовое поле в виде.
// Called when the UIKeyboardDidShowNotification is sent.
- (void)keyboardWasShown:(NSNotification*)aNotification
{
NSDictionary* info = [aNotification userInfo];
CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
UIEdgeInsets contentInsets = UIEdgeInsetsMake(0.0, 0.0, kbSize.height, 0.0);
scrollView.contentInset = contentInsets;
scrollView.scrollIndicatorInsets = contentInsets;
// If active text field is hidden by keyboard, scroll it so it visible
// Your app might not need or want this behavior.
CGRect aRect = self.view.frame;
aRect.size.height -= kbSize.height;
if (!CGRectContainsPoint(aRect, activeField.frame.origin) ) {
[self.scrollView scrollRectToVisible:activeField.frame animated:YES];
}
}
// Called when the UIKeyboardWillHideNotification is sent
- (void)keyboardWillBeHidden:(NSNotification*)aNotification
{
UIEdgeInsets contentInsets = UIEdgeInsetsZero;
scrollView.contentInset = contentInsets;
scrollView.scrollIndicatorInsets = contentInsets;
}
Ответ 2
Нулевые строки кода
Лишенный хаков, клопов, обходных путей и слушателей.
Этот вопрос задавался снова и снова с самого начала iOS. Никакой ответ на StackOverflow не выдержал более двух итераций iOS. Правильно, потому что UIKit продолжает меняться под вашими ногами. Существует проект, а не решение решения этой древней проблемы. Используйте UITableViewController
.
Использовать UITableViewController
Когда a UITableView
управляется UITableViewController
, прокрутка управляется автоматически для вас. Никогда не возитесь с UIKeyboardWillShowNotification
, когда-либо снова. Просто создайте статический или динамический UITableViewCells
для компоновки вашего интерфейса, добавьте UITextView
или UITextField
по мере необходимости; просто становясь первым ответчиком, прокрутите правильное местоположение.
@доступность (iOS, введено = 2.0)
![UITableViewController]()
Примечания
Ответ 3
Нам нужно взять фрейм клавиатуры из уведомления. Когда получите ссылку scrollView, tableView и т.д. Преобразуйте нижнюю границу вида в координаты окна. Когда вы определяете, насколько клавиатура закрывает наш вид, и если разница больше 0, мы можем добавить вложенную надпись ниже.
Попробуйте этот код:
- (void)subscribeKeyboardNotifications
{
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(keyboardWillShow:)
name:UIKeyboardWillShowNotification
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(keyboardWillHide:)
name:UIKeyboardWillHideNotification
object:nil];
}
- (void)unsubscribeKeyboardNotifications
{
[[NSNotificationCenter defaultCenter] removeObserver:self
name:UIKeyboardWillShowNotification
object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self
name:UIKeyboardWillHideNotification
object:nil];
}
- (void)keyboardWillShow:(NSNotification *)aNotification
{
CGRect keyBoardFrame = [[[aNotification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue];
UIWindow *keyWindow = [[[UIApplication sharedApplication] delegate] window];
UIScrollView *someScrollView = ......
CGPoint tableViewBottomPoint = CGPointMake(0, CGRectGetMaxY([someScrollView bounds]));
CGPoint convertedTableViewBottomPoint = [someScrollView convertPoint:tableViewBottomPoint
toView:keyWindow];
CGFloat keyboardOverlappedSpaceHeight = convertedTableViewBottomPoint.y - keyBoardFrame.origin.y;
if (keyboardOverlappedSpaceHeight > 0)
{
UIEdgeInsets tableViewInsets = UIEdgeInsetsMake(0, 0, keyboardOverlappedSpaceHeight, 0);
[someScrollView setContentInset:tableViewInsets];
}
}
- (void)keyboardWillHide:(NSNotification *)aNotification
{
UIEdgeInsets tableViewInsets = UIEdgeInsetsZero;
UIScrollView *someScrollView = ......
[someScrollView setContentInset:tableViewInsets];
}
Ответ 4
Добавьте все UITextField в UIScrollView и используйте TPKeyboardAvoiding
Ответ 5
Обычно я слушаю уведомления о клавиатуре и вношу изменения в ограничения макета. См. Мой другой ответ для получения более подробной информации и примерного проекта.
Ответ 6
Попробуйте использовать этот код, который я использовал в предыдущих проектах:
- (void)textFieldDidBeginEditing:(UITextField *)textField
{
[self didBeginEditingIn:textField];
}
- (void)textFieldDidEndEditing:(UITextField *)textField
{
[self didEndEditing];
}
static const CGFloat KEYBOARD_ANIMATION_DURATION = 0.3;
static const CGFloat MINIMUM_SCROLL_FRACTION = 0.2;
static const CGFloat MAXIMUM_SCROLL_FRACTION = 0.8;
static const CGFloat PORTRAIT_KEYBOARD_HEIGHT = 216+100;
static const CGFloat LANDSCAPE_KEYBOARD_HEIGHT = 162+100;
- (void)didBeginEditingIn:(UIView *)view
{
CGRect textFieldRect = [self.view.window convertRect:view.bounds fromView:view];
CGRect viewRect = [self.view.window convertRect:self.view.bounds fromView:self.view];
CGFloat midline = textFieldRect.origin.y + 0.5* textFieldRect.size.height;
CGFloat numerator = midline - viewRect.origin.y- MINIMUM_SCROLL_FRACTION * viewRect.size.height;
CGFloat denominator = (MAXIMUM_SCROLL_FRACTION - MINIMUM_SCROLL_FRACTION)* viewRect.size.height;
CGFloat heightFraction = numerator / denominator;
if (heightFraction < 0.0)
{
heightFraction = 0.0;
}
else if (heightFraction > 1.0)
{
heightFraction = 1.0;
}
UIInterfaceOrientation orientation =
[[UIApplication sharedApplication] statusBarOrientation];
if (orientation == UIInterfaceOrientationPortrait ||
orientation == UIInterfaceOrientationPortraitUpsideDown)
{
_animatedDistance = floor(PORTRAIT_KEYBOARD_HEIGHT * heightFraction);
}
else
{
_animatedDistance = floor(LANDSCAPE_KEYBOARD_HEIGHT * heightFraction);
}
CGRect viewFrame = self.view.frame;
viewFrame.origin.y -= _animatedDistance;
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationBeginsFromCurrentState:YES];
[UIView setAnimationDuration:KEYBOARD_ANIMATION_DURATION];
[self.view setFrame:viewFrame];
[UIView commitAnimations];
}
- (void)didEndEditing
{
CGRect viewFrame = self.view.frame;
viewFrame.origin.y += _animatedDistance;
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationBeginsFromCurrentState:YES];
[UIView setAnimationDuration:KEYBOARD_ANIMATION_DURATION];
[self.view setFrame:viewFrame];
[UIView commitAnimations];
}
Ответ 7
Я следовал за доком из @Istvan на сайт apple, и есть много недостающих вещей, чтобы заставить его работать:
1. Установите свой .h документ в <UITextFieldDelegate> (чтобы иметь возможность работать с "активным полем" )
2. В viewDidLoad установите делегаты в поля UIText и установите высоту содержимого scrollview с большей высотой (в моем случае я установил еще 500):
CGRect screenRect = [[UIScreen mainScreen] bounds];
CGFloat screenWidth = screenRect.size.width;
CGFloat screenHeight = screenRect.size.height + 500;
_scrollView.contentSize = CGSizeMake(screenWidth, screenHeight);
И теперь все работает...