我试图在导航控制器的顶部创建一个透明的模态视图。有人知道这是否可能吗?
我试图在导航控制器的顶部创建一个透明的模态视图。有人知道这是否可能吗?
模态视图将覆盖其顶部的视图以及导航控制器的导航栏。但是,如果您使用-presentModalViewController:animated:方法,则一旦动画完成,实际上就会消失所覆盖的视图,这使得您的模态视图的任何透明度都毫无意义。(您可以通过在根视图控制器中实现-viewWillDisappear:和-viewDidDisappear:方法来验证此操作)。
您可以像下面这样直接将模态视图添加到视图层次结构中:
UIView *modalView =
[[[UIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];
modalView.opaque = NO;
modalView.backgroundColor =
[[UIColor blackColor] colorWithAlphaComponent:0.5f];
UILabel *label = [[[UILabel alloc] init] autorelease];
label.text = @"Modal View";
label.textColor = [UIColor whiteColor];
label.backgroundColor = [UIColor clearColor];
label.opaque = NO;
[label sizeToFit];
[label setCenter:CGPointMake(modalView.frame.size.width / 2,
modalView.frame.size.height / 2)];
[modalView addSubview:label];
[self.view addSubview:modalView];
将modalView作为子视图添加到根视图中,像这样做实际上不会覆盖导航栏,但它会覆盖其下方的整个视图。我尝试了调整用于初始化modalView的frame的origin值,但负值会导致它不显示。我发现覆盖整个屏幕(除了状态栏)最好的方法是将modalView作为窗口本身的子视图添加:
TransparentModalViewAppDelegate *delegate = (TransparentModalViewAppDelegate *)[UIApplication sharedApplication].delegate;
[delegate.window addSubview:modalView];
最简单的方法是使用navigationController的modalPresentationStyle属性(但您需要自己制作动画):
self.navigationController.modalPresentationStyle = UIModalPresentationCurrentContext;
[self presentModalViewController:modalViewController animated:NO];
modalViewController.view.alpha = 0;
[UIView animateWithDuration:0.5 animations:^{
modalViewController.view.alpha = 1;
}];
presentModalViewController
切换为 presentViewController
即可。 - John Erck我最容易实现这个功能的方法是设置一个"OverlayViewController",它位于窗口或根视图的所有其他子视图之上。在您的应用程序委托或根视图控制器中设置此项,并将OverlayViewController设置为单例,以便可以从代码或视图控制器层次结构中的任何位置访问它。然后,您可以调用显示模态视图、显示活动指示器等方法,每当需要时,它们可能会覆盖任何选项卡栏或导航控制器。
根视图控制器的示例代码:
- (void)viewDidLoad {
OverlayViewController *o = [OverlayViewController sharedOverlayViewController];
[self.view addSubview:o.view];
}
以下是您可以使用的示例代码来显示您的模态视图:
[[OverlayViewController sharedOverlayViewController] presentModalViewController:myModalViewController animated:YES];
我实际上并没有使用-presentModalViewController:animated:
与我的OverlayViewController,但我认为这应该可以正常工作。
#pragma mark - Transparent Modal View
-(void) presentTransparentModalViewController: (UIViewController *) aViewController
animated: (BOOL) isAnimated
withAlpha: (CGFloat) anAlpha{
self.transparentModalViewController = aViewController;
UIView *view = aViewController.view;
view.opaque = NO;
view.alpha = anAlpha;
[view.subviews enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
UIView *each = obj;
each.opaque = NO;
each.alpha = anAlpha;
}];
if (isAnimated) {
//Animated
CGRect mainrect = [[UIScreen mainScreen] bounds];
CGRect newRect = CGRectMake(0, mainrect.size.height, mainrect.size.width, mainrect.size.height);
[self.view addSubview:view];
view.frame = newRect;
[UIView animateWithDuration:0.8
animations:^{
view.frame = mainrect;
} completion:^(BOOL finished) {
//nop
}];
}else{
view.frame = [[UIScreen mainScreen] bounds];
[self.view addSubview:view];
}
}
-(void) dismissTransparentModalViewControllerAnimated:(BOOL) animated{
if (animated) {
CGRect mainrect = [[UIScreen mainScreen] bounds];
CGRect newRect = CGRectMake(0, mainrect.size.height, mainrect.size.width, mainrect.size.height);
[UIView animateWithDuration:0.8
animations:^{
self.transparentModalViewController.view.frame = newRect;
} completion:^(BOOL finished) {
[self.transparentModalViewController.view removeFromSuperview];
self.transparentModalViewController = nil;
}];
}
}
效果如下:
我尝试过自己动画叠加视图,但效果不太好。我遇到了一个崩溃,没有任何指示表明已经崩溃。与其追踪这个问题,我做了背景视图,效果非常好。
模态视图中的代码 - 我想你可以解决其他部分,即设置属性modalView.bgImage...
- (void)viewDidAppear:(BOOL)animated {
// background
// Get status bar frame dimensions
CGRect statusBarRect = [[UIApplication sharedApplication] statusBarFrame];
UIImageView *imageView = [[UIImageView alloc] initWithImage:self.bgImage];
imageView.tag = 5;
imageView.center = CGPointMake(imageView.center.x, imageView.center.y - statusBarRect.size.height);
[self.view insertSubview:imageView atIndex:0];
}
- (void)viewWillDisappear:(BOOL)animated {
[[self.view viewWithTag:5] removeFromSuperview];
}
self.modalPresentationStyle = UIModalPresentationCurrentContext;
[self presentModalViewController:newview animated:YES];
请确保将模态视图的背景设置为透明。
self.view.background = .... alpha:0.x;
controller.modalTransitionStyle = UIModalTransitionStyleFlipHorizontal;
更改为controller.modalPresentationStyle = 17;
。 - Mindaugas@property (weak, nonatomic) IBOutlet UIImageView *backgroundImageView;
- (void) backgroundInitialize;
- (void) backgroundAnimateIn;
- (void) backgroundAnimateOut;
.m file:
- (void) backgroundInitialize{
UIGraphicsBeginImageContextWithOptions(((UIViewController *)delegate).view.window.frame.size, YES, 0.0);
[((UIViewController *)delegate).view.window.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage * screenshot = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
backgroundImageView.image=screenshot;
}
- (void) backgroundAnimateIn{
CGRect backgroundImageViewRect = backgroundImageView.frame;
CGRect backgroundImageViewRectTemp = backgroundImageViewRect;
backgroundImageViewRectTemp.origin.y=-480;
backgroundImageView.frame=backgroundImageViewRectTemp;
[UIView animateWithDuration:0.4 delay:0.0 options:UIViewAnimationCurveEaseInOut animations:^{
backgroundImageView.frame=backgroundImageViewRect;
} completion:^(BOOL finished) {
}];
}
- (void) backgroundAnimateOut{
CGRect backgroundImageViewRect = backgroundImageView.frame;
backgroundImageViewRect.origin.y-=480;
[UIView animateWithDuration:0.4 delay:0.0 options:UIViewAnimationCurveEaseInOut animations:^{
backgroundImageView.frame=backgroundImageViewRect;
} completion:^(BOOL finished) {
}];
}
[self backgroundInitialize];
[self backgroundAnimateIn];
在任何地方我们关闭模态视图控制器,都需要调用:
[self backgroundAnimateOut];