2014-11-01 2 views
23

Я новый, и я начинаю с Swift для iOS.Scrollview и клавиатура Swift

Я начал создавать простое приложение, которое выполняет некоторые операции. Но у меня возникают проблемы, когда появляется клавиатура, скрывая один из моих текстовых полей. Я думаю, что это обычная проблема, и я сделал некоторые исследования, но я не мог найти ничего, что могло бы решить мою проблему. И я хочу использовать Scroll, а не анимировать textField, чтобы сделать его видимым.

Спасибо !!!!! (извините за ошибки на английском языке)

ответ

2

Вы можете анимировать свою прокрутку в центре на вашем UITextField по виду на клавиатуре (т. Е. Сделать свое текстовое поле первым ответчиком) с помощью сдвига прокрутки. Вот несколько хороших ресурсов, чтобы вы начали (есть связка на этом сайте):

How programmatically move a UIScrollView to focus in a control above keyboard?

How to make a UIScrollView auto scroll when a UITextField becomes a first responder

Кроме того, если вы просто использовать UITableView с содержанием в клетках, когда текстовое поле становится первым ответчиком, UITableViewController автоматически прокручивается до ячейки текстового поля для вас (хотя я не уверен, что это то, что вы хотите сделать).

3

Чтение ссылок вы послали мне, я нашел способ, чтобы заставить его работать, спасибо !:

func textFieldDidBeginEditing(textField: UITextField) {    
    if (textField == //your_field) { 
     scrollView.setContentOffset(CGPointMake(0, field_extra.center.y-280), animated: true) 
     callAnimation() 
     viewDidLayoutSubviews() 
    } 
} 

func textFieldDidEndEditing(textField: UITextField) {  
    if (textField == //your_field){ 
     scrollView .setContentOffset(CGPointMake(0, 0), animated: true) 
     viewDidLayoutSubviews() 
    } 
} 
77

В ViewDidLoad, регистрации уведомления:

NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(keyboardWillShow), name:UIKeyboardWillShowNotification, object: nil) 
NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(keyboardWillHide), name:UIKeyboardWillHideNotification, object: nil) 

Добавить ниже методов наблюдателя, выполняет автоматическую прокрутку при появлении клавиатуры.

func textFieldShouldReturn(textField: UITextField) -> Bool { 
    textField.resignFirstResponder() 
    return true 
} 

func keyboardWillShow(notification:NSNotification){ 

    var userInfo = notification.userInfo! 
    var keyboardFrame:CGRect = (userInfo[UIKeyboardFrameBeginUserInfoKey] as! NSValue).CGRectValue() 
    keyboardFrame = self.view.convertRect(keyboardFrame, fromView: nil) 

    var contentInset:UIEdgeInsets = self.scrollView.contentInset 
    contentInset.bottom = keyboardFrame.size.height 
    scrollView.contentInset = contentInset 
} 

func keyboardWillHide(notification:NSNotification){ 

    let contentInset:UIEdgeInsets = UIEdgeInsetsZero 
    scrollView.contentInset = contentInset 
} 

EDIT: Этот пост был обновлен с учетом передового опыта в области Swift 2.2 для Objective C селекторов.

+2

Используя эти символы вместе с Scrollview спас мою жизнь. Просто добавьте 20 contentInset.bottom, чтобы прокрутить его правильно. contentInset.bottom = keyboardFrame.size.height + 20 – Engnyl

+1

Работает отлично! ContentInset может быть установлен на «let» вместо «var» в клавиатуреWillHide, хотя :) –

+1

Не работает с UITextView внутри файла UIBiew UIView. –

44

Верхний ответ для быстрого 3:

NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow), name:NSNotification.Name.UIKeyboardWillShow, object: nil) 
NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide), name:NSNotification.Name.UIKeyboardWillHide, object: nil) 

И потом:

func keyboardWillShow(notification:NSNotification){ 
    //give room at the bottom of the scroll view, so it doesn't cover up anything the user needs to tap 
    var userInfo = notification.userInfo! 
    var keyboardFrame:CGRect = (userInfo[UIKeyboardFrameBeginUserInfoKey] as! NSValue).cgRectValue 
    keyboardFrame = self.view.convert(keyboardFrame, from: nil) 

    var contentInset:UIEdgeInsets = self.theScrollView.contentInset 
    contentInset.bottom = keyboardFrame.size.height 
    theScrollView.contentInset = contentInset 
} 

func keyboardWillHide(notification:NSNotification){ 
    let contentInset:UIEdgeInsets = UIEdgeInsets.zero 
    theScrollView.contentInset = contentInset 
} 
+0

Также возможно, чтобы метод textFieldShouldReturn был выше, если вы хотите использовать ключ возврата для отклонения клавиатура. Thx для обновления! – Mattk90

+0

Не работает с UITextView внутри файла UIBiew UIView. –

+3

Не забывайте «NotificationCenter.default.removeObserver (self)» – nikans

1

Ответ на Swift 3, на основе предложенной Дэниелом Джонсом, но более безопасные (благодаря охраннику), более лаконичные и с последовательными вставками индикатора прокрутки:

@objc private func keyboardWillBeShown(notification: NSNotification) { 
    guard let keyboardFrameValue = notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue else { return } 
    let keyboardFrame = view.convert(keyboardFrameValue.cgRectValue, from: nil) 
    scrollView.contentInset.bottom = keyboardFrame.size.height 
    scrollView.scrollIndicatorInsets = scrollView.contentInset 
} 

@objc private func keyboardWillBeHidden() { 
    scrollView.contentInset = .zero 
    scrollView.scrollIndicatorInsets = scrollView.contentInset 
} 
+0

Я получаю ViewController не имеет члена для 'self.scrollView' – Siddharth

+0

@Siddharth Это потому, что вам нужно создать IBOutlet для вашего scrollview – user30646

0
override func viewDidLoad() { 
    super.viewDidLoad() 
    // Do any additional setup after loading the view, typically from a nib. 

    NotificationCenter.default.addObserver(self, selector: #selector(ViewController.keyboardWillShow), name: NSNotification.Name.UIKeyboardWillShow, object: nil) 

    NotificationCenter.default.addObserver(self, selector: #selector(ViewController.keyboardWillHide), name: NSNotification.Name.UIKeyboardWillHide, object: nil) 

} 

func keyboardWillShow(_ notification:Notification) { 

    if let keyboardSize = (notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue { 
     tableView.contentInset = UIEdgeInsetsMake(0, 0, keyboardSize.height, 0) 
    } 
} 
func keyboardWillHide(_ notification:Notification) { 

    if let keyboardSize = (notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue { 
     tableView.contentInset = UIEdgeInsetsMake(0, 0, 0, 0) 
    } 
} 
3

contentInset не работает для меня, потому что я хочу, чтобы прокрутка просматривалась выше клавиатуры. Поэтому я использую contentOffset:

func keyboardWillShow(notification:NSNotification) { 
    guard let keyboardFrameValue = notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue else { 
     return 
    } 
    let keyboardFrame = view.convert(keyboardFrameValue.cgRectValue, from: nil) 
    scrollView.contentOffset = CGPoint(x:0, y:keyboardFrame.size.height) 
} 

func keyboardWillHide(notification:NSNotification) { 
    scrollView.contentOffset = .zero 
} 
+0

Это был тот, который действительно работал для меня! – Alexander

+0

Это сработало для меня, спасибо! – Grease

2

Вот полное решение в Swift 3, используя охрану и лаконичный код. Плюс правильный код в keyboardWillHide только сбросить bottom к 0.

@IBOutlet weak var scrollView: UIScrollView! 

override func viewWillAppear(_ animated: Bool) { 
    super.viewWillAppear(animated) 
    registerNotifications() 
} 

override func viewWillDisappear(_ animated: Bool) { 
    super.viewWillDisappear(animated) 
    unregisterNotifications() 
} 

func registerNotifications() { 
    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow), name: .UIKeyboardWillShow, object: nil) 
    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide), name: .UIKeyboardWillHide, object: nil) 
} 

func unregisterNotifications() { 
    NotificationCenter.default.removeObserver(self, name: .UIKeyboardWillShow, object: nil) 
    NotificationCenter.default.removeObserver(self, name: .UIKeyboardWillHide, object: nil) 
} 

func keyboardWillShow(notification: NSNotification){ 
    guard let keyboardFrame = notification.userInfo![UIKeyboardFrameBeginUserInfoKey] as? NSValue else { return } 
    scrollView.contentInset.bottom = view.convert(keyboardFrame.cgRectValue, from: nil).size.height + 20 
} 

func keyboardWillHide(notification: NSNotification){ 
    scrollView.contentInset.bottom = 0 
} 
+1

Хороший ответ. Чтобы быть более кратким, вы можете сказать «.UIKeyboardWillShow» вместо «NSNotification.Name.UIKeyboardWillShow». Я обновил ваш ответ, если вы не возражаете. – crashoverride777

0

Из ответа по Sudheer Palchuri, переоборудованные для Swift 4.

В ViewDidLoad, регистрации уведомления:

NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow), name:NSNotification.Name.UIKeyboardWillShow, object: nil) 
NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide), name:NSNotification.Name.UIKeyboardWillHide, object: nil) 

А потом:

// MARK: - Keyboard Delegates 
func textFieldShouldReturn(textField: UITextField) -> Bool { 
    textField.resignFirstResponder() 
    return true 
} 

@objc func keyboardWillShow(notification:NSNotification){ 

    var userInfo = notification.userInfo! 
    var keyboardFrame:CGRect = (userInfo[UIKeyboardFrameBeginUserInfoKey] as! NSValue).cgRectValue 
    keyboardFrame = self.view.convert(keyboardFrame, from: nil) 

    var contentInset:UIEdgeInsets = self.scrollView.contentInset 
    contentInset.bottom = keyboardFrame.size.height 
    self.scrollView.contentInset = contentInset 
} 

@objc func keyboardWillHide(notification:NSNotification){ 

    let contentInset:UIEdgeInsets = UIEdgeInsets.zero 
    self.scrollView.contentInset = contentInset 
} 
Смежные вопросы