-
Notifications
You must be signed in to change notification settings - Fork 1
AA 1.20. Displaying Long Lines of Text with UITextView
Let’s create a text view and see how it works. We start off by declaring the text view in our view controller’s implementation file:
#import "ViewController.h" @interface ViewController () @property (nonatomic, strong) UITextView *myTextView; @end
Now it’s time to create the text view itself. We will make the text view as big as the view controller’s view:
- (void)viewDidLoad { [super viewDidLoad]; self.myTextView = [[UITextView alloc] initWithFrame:self.view.bounds]; self.myTextView.text = @"Some text here..."; self.myTextView.contentInset = UIEdgeInsetsMake(10.0f, 0.0f, 0.0f, 0.0f); self.myTextView.font = [UIFont systemFontOfSize:16.0f]; [self.view addSubview:self.myTextView]; }
If you tap on the text field, you will notice a keyboard pop up from the bottom of the screen, concealing almost half the entire area of the text view. That means if the user starts typing text and gets to the middle of the text view, the rest of the text that she types will not be visible to her. To remedy this, we have to listen for certain notifications:
UIKeyboardWillShowNotification Gets sent by the system whenever the keyboard is brought up on the screen for any component, be it a text field, a text view, etc.
UIKeyboardDidShowNotification Gets sent by the system when the keyboard has already been displayed.
UIKeyboardWillHideNotification Gets sent by the system when the keyboard is about to hide.
UIKeyboardDidHideNotification Gets sent by the system when the keyboard is now fully hidden.
The keyboard notifications contain a dictionary, accessible through the userInfo property, that specifies the boundaries of the keyboard on the screen. This property is of type NSDictionary. One of the keys in this dictionary is UIKeyboardFrameEndUserInfoKey, which contains an object of type NSValue that itself contains the rectangular bound‐ aries of the keyboard when it is fully shown. This rectangular area is denoted with a CGRect.
So our strategy is to find out when the keyboard is getting displayed and then somehow resize our text view. For this, we will use the contentInset property of UITextView to specify the margins of contents in the text view from top, left, bottom, and right:
- (void) handleKeyboardDidShow:(NSNotification *)paramNotification{ /* Get the frame of the keyboard */ NSValue *keyboardRectAsObject = [[paramNotification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey]; /* Place it in a CGRect */ CGRect keyboardRect = CGRectZero; [keyboardRectAsObject getValue:&keyboardRect]; /* Give a bottom margin to our text view that makes it reach to the top of the keyboard */ self.myTextView.contentInset = UIEdgeInsetsMake(0.0f, 0.0f, keyboardRect.size.height, 0.0f); } - (void) handleKeyboardWillHide:(NSNotification *)paramNotification{ /* Make the text view as big as the whole view again */ self.myTextView.contentInset = UIEdgeInsetsZero; } - (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]; self.myTextView = [[UITextView alloc] initWithFrame:self.view.bounds]; self.myTextView.text = @"Some text here..."; self.myTextView.font = [UIFont systemFontOfSize:16.0f]; [self.view addSubview:self.myTextView]; } - (void) viewWillDisappear:(BOOL)paramAnimated{ [super viewWillDisappear:paramAnimated]; [[NSNotificationCenter defaultCenter] removeObserver:self]; }
In this code, we start looking for keyboard notifications in viewWillAppear: and we stop listening to keyboard notifications in viewWillDisappear:. Removing your view controller as the listener is important, because when your view controller is no longer displayed, you probably don’t want to receive keyboard notifications fired by any other view controller. There may be times when a view controller in the background needs to receive notifications, but these are rare, and you must normally make sure to stop lis‐ tening for notifications in viewWillDisappear:. I’ve seen many programmers break their apps by not taking care of this simple logic.