Статьи

iOS SDK: хранение содержимого из-под клавиатуры

Иногда содержание формы должно заполнять весь экран iOS. Итак, что вы делаете, когда клавиатура закрывает ваш UITextField или UITextView? В этом кратком совете я покажу, как использовать UIScrollView, чтобы предотвратить скрытие содержимого формы, когда клавиатура открывается.

Согласно официальной документации Apple, лучший способ управлять вертикально сложенным списком объектов UITextField которые могут быть скрыты клавиатурой, — это встраивать их в объект UIScrollView . Когда отображается клавиатура, UIKeyboardDidShowNotification и может использоваться для настройки отображаемых текстовых полей. Чтобы перехватить это сообщение, вам необходимо выполнить следующие три шага:

  1. Определите размер клавиатуры.
  2. Обновите нижнюю вставку содержимого представления прокрутки содержимого по высоте клавиатуры.
  3. Прокрутите целевой контент в поле зрения.

Во-первых, нам нужно зарегистрировать двух наблюдателей для уведомлений клавиатуры. Один для UIKeyboardDidShowNotification и один для UIKeyboardWillHideNotification . Мы делаем это в viewDidLoad: метод, поэтому наблюдатели будут зарегистрированы при загрузке представления. Вы можете добавить наблюдателей с помощью следующего кода:

1
2
3
4
5
6
7
8
9
[[NSNotificationCenter defaultCenter] addObserver:self
                                         selector:@selector(keyboardWasShown:)
                                             name:UIKeyboardDidShowNotification
                                           object:nil];
   
[[NSNotificationCenter defaultCenter] addObserver:self
                                         selector:@selector(keyboardWillHide:)
                                             name:UIKeyboardWillHideNotification
                                           object:nil];

Если вы регистрируете наблюдателя в viewDidLoad: метод, вы также должны удалить его в viewDidUnload: и dealloc: Поэтому добавьте следующий код в оба этих метода:

1
[[NSNotificationCenter defaultCenter] removeObserver:self];

keyboardWasShown: метод будет отвечать на уведомление UIKeyboardDidShowNotification: . В этом методе мы реализуем три шага, рекомендованных Apple для перемещения контента. Добавьте следующий код в ваш проект:

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
— (void)keyboardWasShown:(NSNotification *)notification
{
     
    // Step 1: Get the size of the keyboard.
    CGSize keyboardSize = [[[notification userInfo] objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
     
     
    // Step 2: Adjust the bottom content inset of your scroll view by the keyboard height.
    UIEdgeInsets contentInsets = UIEdgeInsetsMake(0.0, 0.0, keyboardSize.height, 0.0);
    theScrollView.contentInset = contentInsets;
    theScrollView.scrollIndicatorInsets = contentInsets;
     
     
    // Step 3: Scroll the target text field into view.
    CGRect aRect = self.view.frame;
    aRect.size.height -= keyboardSize.height;
    if (!CGRectContainsPoint(aRect, activeTextField.frame.origin) ) {
        CGPoint scrollPoint = CGPointMake(0.0, activeTextField.frame.origin.y — (keyboardSize.height-15));
        [theScrollView setContentOffset:scrollPoint animated:YES];
    }
}

На первом шаге мы получаем размер клавиатуры. На втором шаге мы настраиваем нижнюю вставку содержимого вида прокрутки по высоте клавиатуры. На третьем и последнем шаге мы сначала создаем новый прямоугольник с высотой экрана минус высота клавиатуры. Затем мы проверяем, находится ли активное текстовое поле под клавиатурой. Если он не находится под клавиатурой, представление прокрутки не будет обновлять смещение содержимого. Если активное текстовое поле находится под клавиатурой, мы обновляем смещение содержимого представления прокрутки. Я использовал (keyboardSize.height-15), поэтому активное текстовое поле не будет находиться прямо над текстовым полем, а будет иметь дополнительные 15 пикселей между ними. activeTextField — это пользовательская переменная, в которой хранится активное поле.

Нам также нужно добавить keyboardWillHide: метод, который будет отвечать на UIKeyboardWillHideNotification . Добавьте следующий код в ваш проект:

1
2
3
4
5
6
— (void) keyboardWillHide:(NSNotification *)notification {
     
    UIEdgeInsets contentInsets = UIEdgeInsetsZero;
    theScrollView.contentInset = contentInsets;
    theScrollView.scrollIndicatorInsets = contentInsets;
}

Здесь мы устанавливаем contentInset и scrollIndicatorInsets представления прокрутки в UIEdgeInsetsZero , чтобы больше не было вставки содержимого.

С помощью этих методов мы отслеживаем активное текстовое поле:

1
2
3
4
5
6
7
8
9
— (void)textFieldDidBeginEditing:(UITextField *)textField
{
    self.activeTextField = textField;
}
 
— (void)textFieldDidEndEditing:(UITextField *)textField
{
    self.activeTextField = nil;
}

Когда мы начинаем с редактирования, переменная activeTextField: устанавливается в активное поле. Когда мы заканчиваем редактирование, переменная activeTextField: устанавливается в nil. Обратите внимание, что мы объявили свойство activeTextField с помощью (nonatomic, assign) , поэтому количество (nonatomic, assign) для активного текстового поля никогда не увеличивается с помощью нашего присваивания.

Добавьте этот код, чтобы отклонить клавиатуру:

1
2
3
4
— (IBAction)dismissKeyboard:(id)sender
{
    [activeTextField resignFirstResponder];
}

Это действие имело didEndOnExit в качестве типа события, поэтому, если вы нажмете клавишу возврата , клавиатура будет отклонена. Вам необходимо подключить это действие к каждому текстовому полю. Также подключите делегата от каждого текстового поля к владельцу файла .

Спасибо за чтение этого быстрого совета о перемещении контента из-под клавиатуры! Если у вас есть вопросы или комментарии к этому уроку, оставьте их в разделе комментариев ниже!