Как создать прозрачный модальный UIViewController на iPhone iOS7+?

У меня относительно простой вопрос, который я не могу понять.

Я нахожусь внутри UIViewController (myViewController), который встроен где-то в иерархию UIViewController (где-то под родительским UITabBarController).

myViewController имеет кнопку. Когда эта кнопка нажата, я хочу наложить на весь экран (включая всю липкость родительского UITabBarController) черный полупрозрачный модальный UIViewController (myModalViewController) с другой липкостью на нем.

Если я просто позвоню

[myViewController presentViewController:myModalViewController..]

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

Если я установлю myModalViewController в качестве дочернего контроллера представления myViewController и добавлю myModalViewController.view в качестве подпредставления myViewController.view, контроллер модального представления с полупрозрачным черным фоном появится ПОД всеми кнопками UITabBarController. Это плохо, потому что я хочу, чтобы весь экран был перекрыт.

Итак, вместо этого я ищу самый верхний контроллер представления в иерархии и добавляю myModalViewController в качестве его дочернего элемента следующим образом:

UIViewController* root = myViewController;
while (root.parentViewController) {
    root = root.parentViewController;
}

[root addChildViewController:myModalViewController];
[root.view addSubview:myModalViewController.view];

Если это правильный способ справиться с этим сценарием? Кажется клёвым.

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


person pfg2009    schedule 10.02.2015    source источник


Ответы (2)


Если вам нужен прозрачный ViewController, вы должны использовать UIModalPresentationCustom Что-то вроде этого...

...
[yourModalCtrl setModalPresentationStyle:UIModalPresentationCustom];
[yourModalCtrl setModalTransitionStyle:UIModalTransitionStyleCrossDissolve];
[self setModalPresentationStyle:UIModalPresentationCurrentContext]; //new
//yourModalCtrl.modalPresentationCapturesStatusBarAppearance = YES;
[self presentViewController: yourModalCtrl animated:Yes completion:completion];

[self presentViewController:....] или какой у вас "Презентирующий контроллер"...

http://b2cloud.com.au/how-to-guides/invisible-background-modal-view/

Обновить

для совместимости с iOS 7 нужно добавить новый [self setModalPresentationStyle:UIModalPresentationCurrentContext]; - проверьте весь код. Кроме того, вы должны установить animate : No (это работает с Да, но у вас будет сообщение в консоли :)

person TonyMkenu    schedule 11.02.2015
comment
У меня это не работает (iOS8.1). Вы могли бы подумать, что это будет так просто, но представляющий контроллер по-прежнему исчезает после завершения анимации. Я использую UIViewController, который не является корневым. Позвольте мне вместо этого попробовать сделать это на корневом контроллере... - person pfg2009; 11.02.2015
comment
Это полностью работает. Спасибо Спасибо спасибо! Я делал что-то не по порядку (поскольку все эти константы UIModelXYZ визуально похожи друг на друга). Однако использование того же порядка, который вы указали, прекрасно справляется с задачей. - person pfg2009; 11.02.2015
comment
Я беру это обратно. Это работает на iOS8 как шарм. Однако на iOS 7 это не работает. Хм... Может быть, вы знаете какой-нибудь способ решить эту проблему и на iOS 7? - person pfg2009; 12.02.2015
comment
Вот еще один ответ, посвященный проблеме iOS7: stackoverflow.com /вопросы/11236367/ - person pfg2009; 12.02.2015
comment
да. Ознакомьтесь с дополнительной липкой добавкой, которую вам нужно добавить для iOS7, здесь: .com/questions/11236367/ - person pfg2009; 19.02.2015

В аналогичной ситуации я сделал следующее:

Я добавил UIImageView в качестве фонового изображения моего контроллера модального представления.

Затем я использовал UIImage + ImageEffects категорию, предоставленную Apple. , для создания размытого изображения моего родительского контроллера представления.

Я реализовал метод в своем родительском классе, например:

// Returns the blurred image
- (UIImage *)getBlurredImage
{
    // You will want to calculate this in code based on the view you will be presenting.
    CGSize size = self.view.frame.size;

    UIGraphicsBeginImageContext(size);

    // view is the view you are grabbing the screen shot of. The view that is to be blurred.
    [self.view drawViewHierarchyInRect:(CGRect)self.view.bounds afterScreenUpdates:YES];
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();

    // Gaussian Blur
    image = [image applyDarkEffect];

    // Box Blur
    // image = [image boxblurImageWithBlur:0.2f];

    return image;
}

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

person Midhun MP    schedule 10.02.2015
comment
Да, это один из способов справиться с ситуацией, спасибо. Мне любопытно, однако, могу ли я обойтись без кэширования чего-либо. - person pfg2009; 11.02.2015
comment
Другими словами, я ищу менее жесткое решение. - person pfg2009; 11.02.2015