I\'m using the UISearchBar (but not the SearchDisplayController that\'s typically used in conjunction) and I\'d like to dismiss the keyboard when you hit the \'X\' button.
Update:
Well, this is a total hack but I was able to make it work. Basically the code invokes the handler for the cancel button. To make it work I had to invoke the selector with a delay, and I'm not sure why this had to be. Also, I had to write an accessor for the cancel button just like you did for the text field.
Again, this is a total hack. I'm not sure I'd do this myself in an app.
// this in the context of the search bar
- (UIButton*) cancelButton
{
for (UIView* v in self.subviews)
{
if ( [v isKindOfClass: [UIButton class]] )
return (UIButton*)v;
}
return nil;
}
// this is the textField delegate callback
- (BOOL)textFieldShouldClear:(UITextField *)textField
{
[textField resignFirstResponder];
UIButton* cb = _searchBar.cancelButton;
NSObject* target = [[cb allTargets] anyObject];
NSArray* actions = [cb actionsForTarget: target forControlEvent:UIControlEventTouchUpInside];
NSString* selectorName = [actions objectAtIndex:0];
SEL selector = NSSelectorFromString( selectorName );
[target performSelector: selector withObject: cb afterDelay: 0.1];
return YES;
}
Original answer:
How do you get the clear 'X' button to display in the first place? In my test case I dont see it displaying...
Try doing a resignFirstResponder on the searchBar, not the textField.
Swift 2 version:
func searchBar(searchBar: UISearchBar, textDidChange searchText: String) {
// The user clicked the [X] button or otherwise cleared the text.
if (searchText.characters.count == 0) {
searchBar.performSelector("resignFirstResponder", withObject: nil, afterDelay: 0.1)
}
}
Credit to Maxhs for original answer : This is swift 2.2 version : Work like charm for me
if searchBar.text == "" {
dispatch_async(dispatch_get_main_queue(), {
self.searchBar.resignFirstResponder()
})
}
This works:
[searchBar performSelector:@selector(resignFirstResponder) withObject:nil afterDelay:0.1];
- (void)searchBarTextDidEndEditing:(UISearchBar *)searchBar
{
SearchBar.showsCancelButton =NO;
}
- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{
[SearchBar resignFirstResponder];
}
When you click the 'x' button, the string in the search bar text field becomes an empty collection of characters.
Checking the length of the collection helps to detect when the 'x' button has been clicked.
I had a similar issue and this solution worked for me:
func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) {
//let searchText = searchText.trimmingCharacters(in: .whitespaces)
if searchText.isEmpty{
DispatchQueue.main.async { [weak self] in
guard let self = self else{ return }
self.searchBar.resignFirstResponder()
}
}
}