I want to be able to dismiss the iPhone keyboard when the user taps anywhere outside of the keyboard. How can I go about doing this? I know I need to dismiss the responder, but need to know how to implement it when a user taps out of the keyboard space.
9 Answers
You'll need to add an UITapGestureRecogniser
and assign it to the view, and then call resign first responder on the textfield on it's selector.
The code:
In viewDidLoad
UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] initWithTarget:self
action:@selector(dismissKeyboard)];
[self.view addGestureRecognizer:tap];
In dismissKeyboard:
-(void)dismissKeyboard {
[aTextField resignFirstResponder];
}
(Where aTextField is the textfield that is responsible for the keyboard)
OPTION 2
If you can't afford to add a gestureRecognizer then you can try this
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
UITouch * touch = [touches anyObject];
if(touch.phase == UITouchPhaseBegan) {
[aTextField resignFirstResponder];
}
}
The simplest solution I have used is this:
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
[self.view endEditing:YES];
}
The endEditing command can be used on any view that contains your textfield as a subview. The other advantage of this method is that you don't need to know which textfield triggered the keyboard. So even if you have a multiple textfields, just add this line to the superview.
Based on the Apple documentation, I think this method exists specifically to solve this problem.
You'll need to add an UITapGestureRecogniser and assign it to the view, and then call resign first responder on the textfield on it's selector.
The code:
In viewDidLoad
UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] initWithTarget:self
action:@selector(dismissKeyboard)];
[self.view addGestureRecognizer:tap];
In dismissKeyboard:
-(void)dismissKeyboard {
[self.view endEditing:true];
}
You need to add a transparent UIVIew as a subview below the keyboard and handle touches there, to dismiss the keyboard. Below code is for your reference.
UITapGestureRecognizer* gesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(overlayTouched:)];
gesture.delegate = self;
[(UITapGestureRecognizer *)gesture setNumberOfTouchesRequired:1];
UIView* trans = [[UIView alloc] initWithFrame:[[delegate view] bounds]];
[trans setOpaque:NO];
[trans setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin];
[trans setAlpha:0.3];
[trans setUserInteractionEnabled:YES];
trans.multipleTouchEnabled = YES;
[trans addGestureRecognizer:gesture];
[trans setBackgroundColor:[UIColor blackColor]];
[trans setTag:BLACK_SCREEN_VIEW];
Other way to do is simple:
Makes your UIView as UIControl in custom class in the interface builder
, then you can attach an IBAction
method in Touch up inside event
of your UIView : UIControl
, then you put [yourTextField resignFirstResponder]
inside the IBAction method
, like this:
- (IBAction) hideKeyboard: (id) sender
{
// If you have more than one textfield to dismiss, of course only can be active 1, but here you can't know who is it, because sender will be the UIView : UIControl
[alias resignFirstResponder];
[password resignFirstResponder];
}
Then, you have other option and it's to put in your textfield the return key of the keyboard as Done
(It can be any of those you want, but Done it's good for this, because return means to do an action with the form) in the interface builder, so you can press Done
and hide the keyboard, but in that case you have to attach the previous IBAction method to the Did end on exit
event.
And in this way the keyboard will hide touching outside
or touching Done
from the keyboard.
If you want to improve the code, if only will hide the keyboard touching Done
from the keyboard the method should be:
// Attach all textFields here on Did end on exit event, will not work if touch outside the keyboard
- (IBAction) hideKeyboard: (id) sender
{
[sender resignFirstResponder];
}