Подтвердить что ты не робот

Как установить делегата с помощью раскадровки

Я обсуждал это какое-то время, надеюсь, что вы можете мне помочь.

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

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

enter image description here

Проблема заключается в настройке делегата, так что вот мои два вопроса:

1- В моем классе корневого представления (My Tab) есть делегат класса Add (модальный), все настроено правильно, кроме этого:

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    if ([[segue identifier] isEqualToString:@"showAdd"]) {
        [[segue destinationViewController] setDelegate:self];

    }
}

Проблема заключается в том, что [segue destinationViewController] возвращает навигационный контроллер, а не класс AddDrinkViewController (см. раскадровку). Как мне обойти это? Если я вообще удаляю навигационный контроллер, код отлично работает с соответствующим делегатом.

2 Есть ли способ установить делегат, перетаскивая розеток в раскадровку?

Спасибо!

4b9b3361

Ответ 1

Вы правы, destinationViewController будет UINavigationController в этом случае. Я написал категорию, чтобы справиться с этой общей ситуацией:

// category .h file
@interface UIStoryboardSegue (NavControllerExtensions)
// Gets destinationViewCotroller. But if that controller 
// is a NavigationController, returns the nav controller 
// top level view controller instead.
@property (readonly) id topLevelDestinationViewController;
@end

// category .m file
@implementation UIStoryboardSegue (NavControllerExtensions)
- (id)topLevelDestinationViewController
{
  id dest = self.destinationViewController;
  if ([dest isKindOfClass:[UINavigationController class]]) {
    UINavigationController* nav = dest;
    dest = nav.topViewController;
  }
  return dest;
}
@end

Итак, теперь вы можете просто сделать это в любом из ваших методов prepareForSegue, и не нужно беспокоиться о том, существует ли даже NavigationController:

[[segue topLevelDestinationViewController] setDelegate:self]
// another example:
MyViewController *vc = segue.topLevelDestinationViewController;
vc.delegate = self; // etc.

Чтобы ответить на ваш второй вопрос, я не смог найти способ установить делегат внутри IB.

Ответ 2

Я нашел более короткий способ в моем случае (так же, как ваш):

AddDrinkViewController *controller=[[[segue destinationViewController]viewControllers]objectAtIndex:0];

Ответ 3

В основном вам нужно создать
Экземпляр UINavigationController и назначить ему destinationViewController
и захватите его контроллер topView

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    if ([[segue identifier] isEqualToString:@"showAdd"]) {

    UINavigationController *navigationController = segue.destinationViewController;
    AddDrinkViewController *addDrinkcontroller = (AddDrinkViewController *)navigationController.topViewController;

    addDrinkcontroller.delegate = self;

   }
}