UINavigationController visibleViewControllers

#iphone #uiviewcontroller #uinavigationcontroller #uitabbarcontroller

#iPhone #uiviewcontroller #uinavigationcontroller #uitabbarcontroller

Вопрос:

У меня есть UITabBarController, а одна вкладка — это UINavigationController. У меня есть строка поиска, которая переходит к определенному представлению в UINavigationController. Проблема в том, что если UINavigationController не отправляет первое представление, оно выходит из строя, потому что мой поиск не распознает visibleViewController из этого вызова:

 UINavigationController *navController = [self.MainTab.viewControllers objectAtIndex:1];
FirstViewController *fVC = [navController visibleViewController];
  

Чего я не понимаю, так это того, что перед этим кодом я делаю это:

     self.MainTab.selectedIndex = 1;
  

Этот код сам по себе выбирает ViewController на этой вкладке, где, насколько мне известно, загружается представление. Так разве этого не должно быть достаточно для [NavController visibleViewController], чтобы получить текущий ViewController? Спасибо.

Комментарии:

1. Что [navController visibleViewController] возвращает? И что такое сообщение о сбое?

2. @sergio Я получаю нераспознанный селектор, отправленный в экземпляр для сообщения о сбое? Как мне проверить, что возвращает visibleViewController, поскольку в случае сбоя мой FirstViewController не имеет правильной информации, верно?

3. кажется, что navController нет UINavigationController , поэтому вызов visibleViewController завершается неудачно… вы уверены в индексе, который используете для его получения self.MainTab.viewControllers ?

4. @sergio Да, я проверил индекс. Если я оставлю код поиска, который у меня есть в этом блоке, и просто использую self. MainTab.SelectedIndex = 1, затем я получаю UINavigationController с первым представлением в viewDidLoad, помещенным в стек. Кроме того, пока я сначала выбираю эту вкладку, а затем возвращаюсь на вкладку home, выполняется этот блок кода, и поиск выбирает правильный элемент.

5. @sergio Я только что попробовал это: if ([NavController isKindOfClass:[UINavigationController class]]) , и он возвращает true .

Ответ №1:

Попробуйте topViewController вместо visibleViewController.

 FirstViewController *fVC = [navController topViewController];
  

Комментарии:

1. К сожалению, я получаю ту же ошибку. Нераспределенный селектор отправлен в экземпляр.

Ответ №2:

Из того, что вы объясняете в своем вопросе и комментариях, я понимаю, что ваш код пытается получить доступ к объекту типа FirstViewController , предположительно первому виду, который будет передан вашему UINavigationController , когда он еще не создан.

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

Решение, которое я бы предложил, заключается в том, чтобы избежать UINavigationController visibleViewController прямого доступа к вашей вкладке поиска; вместо этого позвольте вашему коду поиска получить доступ к модели (как в Model-View-Controller) для вашего приложения и сохранить там результат; затем из упомянутого viewDidLoad метода снова обратитесь к модели, чтобы прочитать результат поиска и обновить /показать пользовательский интерфейс.

Это чистое решение, IMO. Если вам нужен какой-то обходной путь для вашего текущего дизайна, затем проверьте fVC значение, которое вы получаете обратно, visibleViewController и если оно не соответствует ожидаемому, затем создайте экземпляр представления правильно.

Я надеюсь, что это поможет.

Ответ №3:

Я знаю, что на этот вопрос был дан ответ, но я нашел другое решение, которое может быть полезным. В моем случае я по-разному обрабатывал вращение для некоторых ViewControllers в моем NavigationController, я сделал следующее:

Подкласс UINavigationController, затем, при необходимости, в вашем новом подклассе вы можете получить доступ к текущему названию visibleViewController следующим образом:

 - (BOOL)shouldAutorotate
{
    if ([[self visibleViewController].title isEqualToString:@"Special Case"]) {
        return NO;
    }
    return YES;
}
  

Это не относится конкретно к вращению, это именно то, для чего я его использовал. Единственное, что вам нужно сделать, это установить свой self.title для каждого из ViewControllers, которые вы проверяете в их viewDidLoad , если они установлены в IB или не установлены, они будут nil .