UINavigationBar 纹理背景

Posted

技术标签:

【中文标题】UINavigationBar 纹理背景【英文标题】:UINavigationBar texture background 【发布时间】:2012-03-30 12:40:32 【问题描述】:

我查看了 SO,搜索了它,尝试了自己,但我无法想出一种方法来绘制带有背景纹理的 UINavigationBar。

在您开始向我指出覆盖 drawRectsetBackgroundImage:forBarMetrics: 或任何其他类似方法之前,让我解释一下:

我想要的是用我的背景纹理(附样本)绘制一个导航栏,并且仍然保持 UINavigationBar 提供的半透明渐变效果。从我搜索的内容来看,这样做的唯一方法是将该效果包含在图像本身中,但我宁愿使用 UINavigationBar 效果(动态,你看),或者如果没有办法创建 UIImageView,使用 Quartz绘制效果并将其添加为 UINavigationBar 子视图。

你怎么看?有什么办法可以在 Photoshop 中绘制效果吗?

谢谢

【问题讨论】:

【参考方案1】:

您仍然可以尝试在 UINavigationBar 的正确索引中插入自定义子视图。但该代码在每个 ios 版本上都会有所不同。你也会失去自动调整大小(旋转时)。但这可能是您最简单的方法。

更好的是,直接在图像上绘制光泽/反射效果并使用您已经提到的标准方法。示例:iPhone Glossy Icons Using Core Graphics

【讨论】:

我尝试将它插入到索引1(iOS 5)上,它可以工作,但没有绘制效果,似乎效果在UINavigationBar内的“背景视图”内。 索引 0 怎么样?还是在整个层次结构的另一点上? tintColor = [UIColor clearColor] 有效吗?比你可以把它放在下面。 我想最好将它直接绘制到图像中。直接在您的图像编辑器中,或者如果您需要动态使用它,请使用quartzcore/coreimage 将反射绘制到uiimage 上。 看这里:***.com/questions/5541457/…【参考方案2】:

回答我自己的问题:

似乎通常的方法确实是在图像本身上包含闪亮的渐变,但如果我设法通过使用 CAGradientLayer 绘制渐变以编程方式做到这一点。

我使用的代码是

    //Create a image view
    UIImageView *imgView = [[UIImageView alloc] initWithImage:image];    
    imgView.frame = navBar.bounds;
    imgView.autoresizingMask = UIViewAutoresizingFlexibleBottomMargin | UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleWidth;

    //Create a gradient layer
    //Thanks to Kris Johnson's code
    //https://bitbucket.org/KristopherJohnson/gradientbuttons/src/tip/Classes/GradientButton.m    
    CAGradientLayer *shineLayer = [CAGradientLayer layer];
    shineLayer.frame = imgView.bounds;
    shineLayer.colors = [NSArray arrayWithObjects:
                         (id)[UIColor colorWithWhite:1.0f alpha:0.4f].CGColor,
                         (id)[UIColor colorWithWhite:1.0f alpha:0.2f].CGColor,
                         (id)[UIColor colorWithWhite:0.75f alpha:0.2f].CGColor,
                         (id)[UIColor colorWithWhite:0.4f alpha:0.2f].CGColor,
                         (id)[UIColor colorWithWhite:1.0f alpha:0.4f].CGColor,
                         nil];
    shineLayer.locations = [NSArray arrayWithObjects:
                            [NSNumber numberWithFloat:0.0f],
                            [NSNumber numberWithFloat:0.5f],
                            [NSNumber numberWithFloat:0.5f],
                            [NSNumber numberWithFloat:0.8f],
                            [NSNumber numberWithFloat:1.0f],
                            nil];


    //Add the gradient layer to the imageView
    [imgView.layer insertSublayer:shineLayer atIndex:1];    

    //Add the imageview to the navbar
    [navBar insertSubview:imgView atIndex:1];

【讨论】:

【参考方案3】:

试试这个:

   self.navigationBar.tintColor = [UIColor colorWithPatternImage:[UIImage imageNamed:@"image.png"]];

【讨论】:

这样不行,如果你这样做,导航栏会保持黑色。【参考方案4】:

试试这个:

if ([self.navigationController.navigationBar respondsToSelector:@selector(setBackgroundImage:forBarMetrics:)])

    [self.navigationController.navigationBar setBackgroundImage:[UIImage imageNamed:@"your_navbar.png"] forBarMetrics:UIBarMetricsDefault];

else

    UIImageView *imageView = imageView = [[UIImageView alloc] initWithImage:
                     [UIImage imageNamed:@"your_navbar.png"]];
    [imageView setTag:1];
    [self.navigationController.navigationBar insertSubview:imageView atIndex:0];
    [imageView release];

【讨论】:

对不起...太高兴了 那么,您对这个问题有什么宝贵意见吗? 可悲的是,没有...尽管编写好的和简洁的解决方案是显而易见的答案,但您为什么不接受前面提到的解决方案? 我想我解释了为什么这些解决方案对我来说似乎很糟糕,我更喜欢动态的东西,而不是必须为 UINavigationBar、按钮等制作特定的资源......

以上是关于UINavigationBar 纹理背景的主要内容,如果未能解决你的问题,请参考以下文章

如何在 iOS 8 中将 UIVisualEffectView 添加到 UINavigationBar?

导航栏标题中的多个叠加图像

如何从 AppDelegate 更改 UINavigationBar 背景颜色

UINavigationBar 问题的自定义背景

ios - UINavigationBar添加背景图片的几种简单思路

使用 UIAppearance 使 UINavigationBar 具有渐变背景