UISearchBar отмена кнопки сбоя - PullRequest
2 голосов
/ 07 февраля 2011

У меня есть UITableView, который на didSelectRowAtIndexPath выдвигает другой UITableView, чтобы выполнить поиск ...

    LocationSearchViewController *locationSearchViewController = [[LocationSearchViewController alloc] initWithNibName:@"LocationSearchViewController"  bundle:nil];
    locationSearchViewController.delegate = self;       
    UITableViewCell *cell = [myTableView cellForRowAtIndexPath:indexPath];
    locationSearchViewController.defaultLocation = cell.detailTextLabel.text;

    [[self navigationController]  pushViewController:locationSearchViewController animated:YES];
    [locationSearchViewController release];

Представление поиска содержит UISearchBar с включенной кнопкой отмены.Если пользователь нажимает кнопку отмены, приложение вылетает с objc_exception_throw.Консоль отображает ...

2011-02-06 22: 05: 43.960 JetLogger [2381: 207] * Ошибка подтверждения в - [UISearchDisplayController setActive: animated:],/SourceCache/UIKit_Sim/UIKit-1447.6.4/UISearchDisplayController.m:589

Однако, если пользователь касается элемента в табличном представлении (результаты поиска), я закрываю поисковое представление и тамэто не сбой.Я не могу понять, почему разница, поскольку я выкидываю представление поиска с тем же кодом ...

В LocationSearchViewController ...

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
   if ([self.delegate respondsToSelector:@selector(locationSearchViewDidDismiss:withLocation:)]) {
    [self.delegate locationSearchViewDidDismiss:self withLocation:[tableView cellForRowAtIndexPath:indexPath].textLabel.text];
   }
}
- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar{
   if ([self.delegate respondsToSelector:@selector(locationSearchViewDidDismiss:withLocation:)]) {
     [self.delegate locationSearchViewDidDismiss:self withLocation:@"No results found"];
   }
}

В делегате ...

- (void)locationSearchViewDidDismiss:(LocationSearchViewController *)controller withLocation:(NSString*)location{   
   if((location != @"") && (location != @"No results found")){
    //update the table data
    [myTableView reloadData];
   }
   [self.navigationController popViewControllerAnimated:YES];
}

Любая помощь приветствуется.

Джон

Ответы [ 6 ]

6 голосов
/ 19 июня 2012

Поскольку мы открываем viewController, панель поиска теряет фокус. Это вызывает вызов setActive, но в это время панель поиска уже освобождается. Поэтому нам нужно установить активное значение no, прежде чем мы выдохнемся.

Простой обходной путь, поэтому:

- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{
    [self.searchDisplayController setActive:NO animated:NO];
    [self.navigationController popViewControllerAnimated:YES]; 
}
3 голосов
/ 01 февраля 2013

Я думаю, что предоставленные ответы несовершенны, потому что они косвенным образом решают проблему, которая заключается в том, что searchDisplayControllerDidEndSearch: вызывается для делегата, освобожденного от обязательств.Вызов [self.searchDisplayController setActive:NO animated:NO] может работать в searchBarCancelButtonClicked:, но в других местах произойдет сбой, например, в searchBarTextDidEndEditing:.

Вместо этого просто очистите делегат непосредственно перед отключением контроллера: self.searchDisplayController.delegate = nil;

Это гарантирует, что метод делегата не будет вызываться для освобожденного экземпляра.

3 голосов
/ 29 июня 2011

Я столкнулся с той же проблемой.XCode 4 IOS 4.3

Для меня проблема была только тогда, когда фокус был внутри панели поиска. Я нашел какой-то обходной путь, который мог бы помочь.

Вот код:

static BOOL _cancelBtnClicked = NO;

- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar{
    Log(@"Enter"); 
    if(searchDisplayController.active){
        _cancelBtnClicked = YES;
    }else{
        [self back];
    }
}

- (void)searchDisplayControllerDidEndSearch:(UISearchDisplayController *)controller{
    Log(@"Enter");
    if(_cancelBtnClicked){
        _cancelBtnClicked = NO;
        [self back];
    }
}

-(void)back{
[self.navigationController popViewControllerAnimated:YES];
}
0 голосов
/ 10 декабря 2015

Swift Edition

func searchBarCancelButtonClicked(searchBar: UISearchBar) {
    self.searchDisplayController?.active = false
    self.dismissViewControllerAnimated(true, completion: nil)
}
0 голосов
/ 16 августа 2012

У меня была такая же проблема.

- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar
{
    [self.searchDisplayController setActive:NO animated:NO];
    [self.navigationController popViewControllerAnimated:YES]; 
}

НЕ решило это в моем случае. Вместо этого я вызвал [self.searchDisplayController setActive: NO animated: NO] в другом месте, чтобы он вызывался раньше.

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    // ....

    [self.searchDisplayController setActive:NO animated:NO];
}
0 голосов
/ 07 марта 2011

Я только что столкнулся с этой проблемой.

Я получаю эту ошибку, когда закрываю viewcontroller, содержащий элементы поиска, с popViewControllerAnimated.Если вы представляете тот же viewcontroller модально и отклоняете с помощью функции модального отклонения, это утверждение также не сработает.

Чтобы исправить эту проблему, мне пришлось добавить (используя ваш код в качестве примера)

- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar{
   [self.searchController setActive:NO animated:NO];
   if ([self.delegate respondsToSelector:@selector(locationSearchViewDidDismiss:withLocation:)]) {
     [self.delegate locationSearchViewDidDismiss:self withLocation:@"No results found"];
   }
}

Таким образом, searchcontroller неактивен перед вызовом любых внутренних функций, которые он хочет.Такое ощущение, что это ошибка с 4.2 SDK, но мне нужно проверить это с новым 4.3 г семян.

Нашли ли вы какое-либо другое решение?

Я скорее не использую вышеуказанное исправлениепотому что отбрасывать анимацию немного некрасиво: \

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...