ipad - отклонение UIPopoverController - PullRequest
8 голосов
/ 13 апреля 2010

У меня есть кнопка внутри содержимого UIPopoverController. Эта кнопка запускает метод myAction.

MyAction имеет вид

- (void) myAction:(id)sender 

Итак, myAction получает идентификатор кнопки звонящего.

Теперь внутри этого метода я хотел бы закрыть UIPopoverController, но единственное, что у меня есть, это идентификатор кнопки звонящего. Помните, что кнопка находится внутри UIPopoverController.

Есть ли способ узнать идентификатор UIPopoverController, если у меня уже есть идентификатор кнопки?

спасибо.

Ответы [ 4 ]

19 голосов
/ 13 апреля 2010

К сожалению нет. По крайней мере, не в рамках стандартных практик. Возможно, вам удастся пройтись по стеку респондента, чтобы найти его, но это хак, он глючит и действительно очень грязный.

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

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

5 голосов
/ 23 августа 2012

Вы можете получить доступ к представляемому popoverController, открыв "popoverController" с помощью KVC.

[[self valueForKey:@"popoverController"] dismissPopoverAnimated:YES]
4 голосов
/ 23 апреля 2010

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

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

Это код метода на контроллере вида, который отображается внутри всплывающего окна:

- (void) exitView: (id)sender {
    MyAppDelegate *appDelegate = (MyAppDelegate *)[[UIApplication sharedApplication] delegate];

    [appDelegate.detailViewController exitDrill];
}

Тогда простой метод отклонения на контроллере подробного представления:

- (void) exitDrill {
    if(dtController != nil){
      [dtController dismissPopoverAnimated: YES];
      [dtController release];
    }
}

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

0 голосов
/ 30 октября 2012

Как уже писал Эд Марти

Если вы хотите отклонить всплывающее окно нажатием кнопки, в каком-то соответствующем месте должна быть ссылка на всплывающее окно

Это очень верно; однако при отображении UIPopoverController класс, открывающий popovercontroller, уже сохраняет этот ресурс. Итак, что вы можете сделать, это использовать этот класс в качестве класса делегата для вашего Popover Controller.

Для этого вы можете сделать следующее, которое я использую в своем коде. В классе, открывающем поповер, это мой код:

- (void)showInformationForView:(Booking*)booking frame:(CGRect)rect
{
    BookingDetailsViewController *bookingView = [[BookingDetailsViewController alloc] initWithStyle:UITableViewStyleGrouped booking:booking];
    [bookingView setDelegate:self];

    UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:bookingView];

    self.popController = [[UIPopoverController alloc] initWithContentViewController:navController];
    [self.popController setDelegate:self];
    [self.popController setPopoverContentSize:CGSizeMake(320, 320)];

    rect.size.width = 0;

    [self.popController presentPopoverFromRect:rect inView:self.view permittedArrowDirections:UIPopoverArrowDirectionLeft animated:YES];
}

- (void)dismissPopoverAnimated:(BOOL)animated
{
    [self.popController dismissPopoverAnimated:animated];
}

Итак, я делаю UINavigationController и устанавливаю BookingDetailsViewController в качестве rootViewController. Затем я также добавляю текущий класс в качестве делегата к этому BookingDetailsViewController.

Второе, что я добавил, это метод увольнения под названием dismissPopoverAnimated:animated.

В мой BookingDetailsViewController.h я добавил следующий код:

[...]
@property (nonatomic, strong) id delegate;
[...]

И в мой BookingDetailsViewController.m я добавил этот код:

[...]

@synthesize delegate = _delegate;

- (void)viewDidLoad

{
    UIBarButtonItem *closeButton = [[UIBarButtonItem alloc] initWithTitle:@"Close" style:UIBarButtonItemStylePlain target:self action:@selector(closeView)];
    [self.navigationItem setRightBarButtonItem:closeButton];

    [super viewDidLoad];
}

- (void)closeView
{
    if ([self.delegate respondsToSelector:@selector(dismissPopoverAnimated:)]) {
        [self.delegate dismissPopoverAnimated:YES];
    }
    else {
        NSLog(@"Cannot close the view, nu such dismiss method");
    }
}

[...]

Что происходит, когда при нажатии кнопки «Закрыть» в UINavigationController вызывается метод closeView. Этот метод проверяет, отвечает ли делегат на dismissPopoverAnimated:animated и, если это так, он вызывает его. Если он не отвечает на этот метод, он покажет сообщение в журнале и больше ничего не будет делать (поэтому он не потерпит крах).

Я написал свой код с использованием ARC, поэтому управление памятью отсутствует.

Надеюсь, это помогло вам.

...