UIPopoverController presented modally doesn't

2019-05-25 21:46发布

问题:

First of all, can we talk about iOS 5 here? Or is it still under NDA? If we can't talk about it, just ignore my question.

By testing my app with an iPad with iOS 5 installed I discovered a problem with my "modal" popover: This can be closed by tapping outside of it, in other words, it's not modal! I have no idea what I'm doing wrong.

A view controller opens the popover with this code:

AddProjectViewController *addProjectViewController = [[AddProjectViewController alloc] initWithStyle:UITableViewStyleGrouped];
[addProjectViewController setDelegate:self];

UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:addProjectViewController];
[addProjectViewController release];

CGRect popoverFrame = [sender frame];

UIPopoverController *tempPopover = [[UIPopoverController alloc] initWithContentViewController:navController];
[tempPopover presentPopoverFromRect:popoverFrame inView:[self view] permittedArrowDirections:UIPopoverArrowDirectionAny animated:YES];
self.currentPopover = tempPopover;
[tempPopover release];
[navController release];

The view controller that's inside of the popover has this line in it's viewDidLoad.

- (void)viewDidLoad
{
    [self setModalInPopover:YES];

    // Do other stuff
}

Is there anything missing?

回答1:

I found it. The setModalInPopover assignment must be inside of the viewDidAppear method of the embedded view controller for the popover to be modal:

- (void)viewDidAppear:(BOOL)animated
{
    [super viewDidAppear:animated];

    [self setModalInPopover:YES];
}


回答2:

The approved answer will work if you are using a custom view controller that knows the view is going to be a in a popover. However, if you are using a generic view controller created programmatically or a view controller whose viewDidAppear method you do not have the ability to override for whatever reason, you can also implement the UIPopoverControllerDelegate protocol in a class, set the popover delegate to that class and return NO, in the popoverControllerShouldDismissPopover.

Example

In some class that implements UIPopoverControllerDelegate:

- (BOOL) popoverControllerShouldDismissPopover:(UIPopoverController *) popoverController {
    return NO;
}

In the code that creates your popover controller:

UIPopoverController * pc = initialize and setup 

pc.delegate = instance of class that impleements UIPopoverControllerDelegate


回答3:

Have you tried setting the modalInPopover property of the navigation controller? This is the view controller that is actually "owned" by the popover, so I would expect that the popover uses its modalInPopover property to determine whether it is modal or not.

Perhaps UINavigationController did pass this on to its currently visible child view controller in iOS 4.x.