Странный UISearchDisplayController Сбой со скрытой клавиатурой - PullRequest
1 голос
/ 25 марта 2012

У меня есть IUSearchBar с UISearchDisplayController, и все работает хорошо:

  • Когда я касаюсь панели поиска, появляется клавиатура, TableView имеет черную крышку и я могу запуститьнабрав

снимок экрана 1 http://joeranbosma.nl/xcode/sdc1.png

  • Когда я что-то печатаю, появляется кнопка очистки (x), а также результаты поиска.

снимок экрана 1 http://joeranbosma.nl/xcode/sdc2.png

  • Это прекрасно работает.Когда я нажимаю кнопку очистки (x), она просто возвращается к первому состоянию снимка экрана (пустая строка поиска и черный прямоугольник над результатами)

Но вот оно!

  • Когда я набираю что-то, а затем перемещаю результат поиска, клавиатура прячется (стандартная вещь UISearchDisplayController) Вот так:

снимок экрана 1 http://joeranbosma.nl/xcode/sdc3.png

Когда я , а затем нажимаю кнопку очистки (x), программа вылетает с ошибкой SIGABRT:

снимок экрана 1 http://joeranbosma.nl/xcode/sdc4.png

.. иЯ не знаю, как это исправить: (

Вот мой исходный код: (не знаю, что вам нужно, чтобы решить вопрос) http://joeranbosma.nl/xcode/wearch_stack.zip

Но я думаю, что это наиболее полезночасть:

- (void)viewDidLoad {
    [super viewDidLoad];

    //Initialize the array.
    listOfItems = [[NSMutableArray alloc] init];
    copyListOfItems = [[NSMutableArray alloc] init];
    staticlist = [[NSMutableArray alloc] init];

    staticlist = listOfItems;

    //Add items
    [listOfItems addObject:@"Iceland"];
    [listOfItems addObject:@"Greenland"];
    [listOfItems addObject:@"Switzerland"];
    [listOfItems addObject:@"Norway"];
    [listOfItems addObject:@"New Zealand"];
    [listOfItems addObject:@"Greece"];
    [listOfItems addObject:@"Rome"];
    [listOfItems addObject:@"Ireland"];

    //Set the title
    self.navigationItem.title = @"Wearch";

    // Uncomment the following line to display an Edit button in the navigation bar for this view controller.
    // self.navigationItem.rightBarButtonItem = self.editButtonItem;
}
// Customize the number of sections in the table view.
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
   return 1;
}
// Customize the number of rows in the table view.
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    if (searching)
        return [copyListOfItems count];
    else {
        return [listOfItems count];
    }
}
// Customize the appearance of table view cells.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

    static NSString *CellIdentifier = @"Cell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }

    // Configure the cell.
    if(searching)
        cell.textLabel.text = [copyListOfItems objectAtIndex:indexPath.row];
    else {
        NSString *txtLbl = [listOfItems objectAtIndex:indexPath.row];
        cell.textLabel.text = [txtLbl stringByAppendingString:@"x"];
    }

    cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;

    return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {

    //Get the selected word

    NSString *selectedWord = nil;

    if(searching)
        selectedWord = [copyListOfItems objectAtIndex:indexPath.row];
    else {
        selectedWord = [listOfItems objectAtIndex:indexPath.row];
    }

    //Initialize the detail view controller and display it.
    DetailViewController *dvController = [[DetailViewController alloc] initWithNibName:@"DetailView" bundle:[NSBundle mainBundle]];
    dvController.selectedWord = selectedWord;
    [self.navigationController pushViewController:dvController animated:YES];
    [dvController release];
    dvController = nil;  
}
- (void) searchBarTextDidBeginEditing:(UISearchBar *)theSearchBar {
    searching = YES;
}
- (void)searchBar:(UISearchBar *)theSearchBar textDidChange:(NSString *)searchText {
    //Remove all objects first.
    [copyListOfItems removeAllObjects];

    if([searchText length] > 0) {
        searching = YES;
        [self searchTableView];
    }
    else {
        searching = NO;
    }

    [self.tableView reloadData];
}
- (void) searchBarSearchButtonClicked:(UISearchBar *)theSearchBar {
    [self searchTableView];
}
- (void) searchTableView {

    NSString *searchText = searchBar.text;
    NSMutableArray *searchArray = [[NSMutableArray alloc] init];

    NSMutableArray *results1 = [[NSMutableArray alloc] init];
    NSMutableArray *results2 = [[NSMutableArray alloc] init];

    [searchArray addObjectsFromArray:listOfItems];

    for (NSString *sTemp in searchArray) {
        NSRange titleResultsRange = [sTemp rangeOfString:searchText options:NSCaseInsensitiveSearch];

        if (titleResultsRange.length > 0){
            if (titleResultsRange.location == 0) {
                [results1 addObject:sTemp];
            }
            else{
                [results2 addObject:sTemp];
            }
        }
    }

    for (NSString *sTemp in results1) {
        [copyListOfItems addObject:sTemp];
    }
    for (NSString *sTemp in results2) {
        [copyListOfItems addObject:sTemp];
    }

    [searchArray release];
    searchArray = nil;
}

Я надеюсь, что один из вас может решить эту проблему.

Можете ли вы также сказать, если вам нравятся изображения?

1 Ответ

4 голосов
/ 25 марта 2012

Это интересный. Длинный ответ заключается в том, что searchBarTextDidBeginEditing: вызывается после tableView:numberOfRowsInSection:, но до tableView:cellForRowAtIndexPath:. В результате tableView ожидает [listOfItems count] количество строк, но к моменту вызова tableView:cellForRowAtIndexPath: searching BOOL равно YES, поэтому контроллер представления использует copyListOfItems для заполнения таблицы, что, конечно, не содержит достаточного количества объектов для заполнения таблицы.

Короткий ответ: перестаньте говорить контроллеру вида, который вы ищете, пока вы не ищете; Установите searching = YES;, когда есть фактический текст, который вы используете для поиска, а не только тогда, когда searchBar является первым респондентом.

Действительно короткий ответ:

- (void) searchBarTextDidBeginEditing:(UISearchBar *)theSearchBar {
    // Comment this assignment out
    //searching = YES;
}

Кажется, он работает нормально.

Несколько советов по такому сценарию:

1) Посмотрите на напечатанную трассировку стека в вашей консоли. Это позволило бы вам увидеть, что проблема была:

'NSRangeException', reason: '*** -[__NSArrayM objectAtIndex:]: index 0 beyond bounds for empty array'

2) Используйте NSLog s обильно; Я считаю наиболее полезным:

NSLog(@"%@",NSStringFromSelector(_cmd));

Редактировать В ответ на несимвольную трассировку стека в консоли (т. Е. 0x14d3ec9 0x36e5c2):

3) Использовать точку останова исключения; как на фото:

enter image description here

4) Добавить необработанный обработчик исключений; Как описано здесь .

...