Resize the UITextView when keyboard appears
In viewWillAppear
method, add the following:
- (void) viewWillAppear:(BOOL)paramAnimated{
[super viewWillAppear:paramAnimated];
[[NSNotificationCenter defaultCenter]
addObserver:self
selector:@selector(handleKeyboardDidShow:)
name:UIKeyboardDidShowNotification object:nil];
[[NSNotificationCenter defaultCenter]
addObserver:self
selector:@selector(handleKeyboardWillHide:)
name:UIKeyboardWillHideNotification object:nil];
}
Then implement the two methods of the notification center, like this:
- (void) handleKeyboardDidShow:(NSNotification *)paramNotification{
NSValue *keyboardRectAsObject =
[[paramNotification userInfo]
objectForKey:UIKeyboardFrameEndUserInfoKey];
CGRect keyboardRect = CGRectZero;
[keyboardRectAsObject getValue:&keyboardRect];
yourTextView.contentInset =
UIEdgeInsetsMake(0.0f,
0.0f,
keyboardRect.size.height,
0.0f);
}
And the other one like:
- (void) handleKeyboardWillHide:(NSNotification *)paramNotification{
yourTextView.contentInset = UIEdgeInsetsZero;
}
It will work for all devices ;)
Swift / Modified Version
Using the above, I made some adjustments to use NSLayoutConstraint
's changing the height constant
property when the keyboard shows and hides. This also works if you rotate the device.
1. Set up TextView Constraints
Then control drag an outlet from you height constraint to the class.
2. Add The Following
override func viewWillAppear(animated: Bool) {
super.viewWillAppear(animated)
NSNotificationCenter.defaultCenter().addObserver(self, selector:#selector(SkillDescriptionViewController.keyboardWillShowHandle(_:)), name: UIKeyboardDidShowNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector:#selector(SkillDescriptionViewController.keyboardWillHideHandle), name: UIKeyboardWillHideNotification, object: nil)
}
func keyboardWillShowHandle(note:NSNotification) {
guard let keyboardRect = note.userInfo![UIKeyboardFrameEndUserInfoKey] as? NSValue else { return }
let kbFrame = keyboardRect.CGRectValue()
tvHeight.constant = -kbFrame.height
view.layoutIfNeeded()
}
func keyboardWillHideHandle() {
tvHeight.constant = 0
view.layoutIfNeeded()
}
Swift 5 solution based on answers above
Notification API has changed (20190707) as well as how to use #selector
The solution here can be used when the keyboard pop covers UITextView which causes user unable to see the text been edited.
import UIKit
class DCNodeLogEntryViewController: UIViewController {
@IBOutlet weak var textViewNodeLogEntry: UITextView!
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
NotificationCenter.default.addObserver(
self,
selector: #selector(DCNodeLogEntryViewController.handleKeyboardDidShow(notification:)),
name: UIResponder.keyboardDidShowNotification,
object: nil
)
NotificationCenter.default.addObserver(
self,
selector: #selector(DCNodeLogEntryViewController.handleKeybolardWillHide),
name: UIResponder.keyboardWillHideNotification,
object: nil
)
}
@objc func handleKeyboardDidShow(notification: NSNotification) {
guard let keyboardRect = notification
.userInfo![UIResponder.keyboardFrameEndUserInfoKey]
as? NSValue else { return }
let frameKeyboard = keyboardRect.cgRectValue
textViewNodeLogEntry.contentInset = UIEdgeInsets(
top: 0.0,
left: 0.0,
bottom: frameKeyboard.size.height,
right: 0.0
)
view.layoutIfNeeded()
}
@objc func handleKeybolardWillHide() {
textViewNodeLogEntry.contentInset = .zero
}
}