iOS开发 - iOS15导航栏适配(Object-C、Swift)

iOS15导航栏适配

设置导航栏纯色/透明、解决ScrollView类上滑导航栏出现磨砂阴影的问题

Swift版导航栏适配参考>>

在iOS 13中给导航的UINavigationBar增加了scrollEdgeAppearance属性应用在iOS 14及更早版本的大标题导航栏上,在iOS 15中scrollEdgeAppearance属性适用于所有的导航栏

官方解释:描述当关联的UIScrollView到达与导航条相邻的边缘(导航条的上边缘)时要使用的导航条的外观属性。如果没有设置,将使用修改后的standardAppearance

/// Describes the appearance attributes for the navigation bar to use when an associated UIScrollView has reached the edge abutting the bar (the top edge for the navigation bar). If not set, a modified standardAppearance will be used instead.
@property (nonatomic, readwrite, copy, nullable) UINavigationBarAppearance *scrollEdgeAppearance UI_APPEARANCE_SELECTOR API_AVAILABLE(ios(13.0));

scrollEdgeAppearance 与 standardAppearance 一样同属于 UINavigationBarAppearance 类型 父类是 UIBarAppearance
其中影响导航栏颜色、阴影涉及到以下属性

  • backgroundEffect 基于backgroundColor或backgroundImage的磨砂效果

  • backgroundColor 背景色,层级在backgroundImage之下

  • backgroundImage 背景图片

  • backgroundImageContentMode渲染backgroundImage时的内容模式。 默认是UIViewContentModeScaleToFill

  • shadowColor 阴影颜色(底部分割线)
    1.当shadowImage为nil时,直接使用此颜色为阴影色。如果此属性为nil或clearColor(需要显式设置),则不显示阴影。
    2.如果shadowImage包含 template 图像,则使用该图像作为阴影并使用此属性中的值对其进行着色。如果此属性为nil或clearColor(需要显式设置),则不显示阴影。
    3.如果shadowImage不包含 template 图像,则此属性无效。

  • shadowImage阴影图片(可以使用图片的渲染模式:UIImageRenderingModeAlwaysOriginal 保持原色)

scrollEdgeAppearance

/// A specific blur effect to use for the bar background. This effect is composited first when constructing the bar's background.
@property (nonatomic, readwrite, copy, nullable) UIBlurEffect *backgroundEffect;
/// A color to use for the bar background. This color is composited over backgroundEffects.
@property (nonatomic, readwrite, copy, nullable) UIColor *backgroundColor;
/// An image to use for the bar background. This image is composited over the backgroundColor, and resized per the backgroundImageContentMode.
@property (nonatomic, readwrite, strong, nullable) UIImage *backgroundImage;
/// The content mode to use when rendering the backgroundImage. Defaults to UIViewContentModeScaleToFill. UIViewContentModeRedraw will be reinterpreted as UIViewContentModeScaleToFill.
@property (nonatomic, readwrite, assign) UIViewContentMode backgroundImageContentMode;

/// A color to use for the shadow. Its specific behavior depends on the value of shadowImage. If shadowImage is nil, then the shadowColor is used to color the bar's default shadow; a nil or clearColor shadowColor will result in no shadow. If shadowImage is a template image, then the shadowColor is used to tint the image; a nil or clearColor shadowColor will also result in no shadow. If the shadowImage is not a template image, then it will be rendered regardless of the value of shadowColor.
@property (nonatomic, readwrite, copy, nullable) UIColor *shadowColor;
/// Use an image for the shadow. See shadowColor for how they interact.
@property (nonatomic, readwrite, strong, nullable) UIImage *shadowImage;

兼容iOS15设置透明导航栏示例:

- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
       //navigation标题文字颜色
       NSDictionary *dic = @{NSForegroundColorAttributeName : HexAlphaColor(@"#FFFFFF",1.f),
                             NSFontAttributeName : [UIFont systemFontOfSize:18]};
    
       if (@available(iOS 13.0, *)) {
           UINavigationBarAppearance *barApp = [UINavigationBarAppearance new];
           barApp.backgroundColor = [UIColor clearColor];
           #//基于backgroundColor或backgroundImage的磨砂效果
           barApp.backgroundEffect = nil;
           #//阴影颜色(底部分割线),当shadowImage为nil时,直接使用此颜色为阴影色。如果此属性为nil或clearColor(需要显式设置),则不显示阴影。
           //barApp.shadowColor = nil;
           //标题文字颜色
           barApp.titleTextAttributes = dic;
           self.navigationController.navigationBar.scrollEdgeAppearance = nil;
           self.navigationController.navigationBar.standardAppearance = barApp;
       }else {
          self.navigationController.navigationBar.titleTextAttributes = dic;
          [self.navigationBar setShadowImage:[UIImage new]];
          UIImage *navBgImg = [[UIImage createImageWithColor:HexAlphaColor(@"#FFFFFF",0.0) size:CGSizeMake(SCREEN_WIDTH, 44.f)] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
          [self.navigationController.navigationBar setBackgroundImage:navBgImg forBarMetrics:UIBarMetricsDefault];
       }
    //透明设置
    self.navigationController.navigationBar.translucent = YES;
    //navigationItem控件的颜色
    self.navigationController.navigationBar.tintColor = [UIColor whiteColor];
}

解决设置透明导航栏,出现ScrollView类页面上滑,导航栏变成磨砂阴影效果

原因分析:

因为scrollEdgeAppearance = nil,当前控制器如果使用有ScrollView类的控件,当ScrollView向上滚动时scrollEdgeAppearance会默认使用standardAppearance的属性效果。所以backgroundEffectshadowColor属性需要显式设置为nil,以防止backgroundEffect、shadowColor有颜色值影响导航栏透明效果。

兼容iOS15设置不透明纯色导航栏示例:


- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
       //navigation标题文字颜色
       NSDictionary *dic = @{NSForegroundColorAttributeName : HexAlphaColor(@"#FFFFFF",1.f),
                             NSFontAttributeName : [UIFont systemFontOfSize:18]};
    
       if (@available(iOS 13.0, *)) {
           UINavigationBarAppearance *barApp = [UINavigationBarAppearance new];
           barApp.backgroundColor = [UIColor whiteColor];
           #//基于backgroundColor或backgroundImage的磨砂效果
           barApp.backgroundEffect = nil;
           #//阴影颜色(底部分割线),当shadowImage为nil时,直接使用此颜色为阴影色。如果此属性为nil或clearColor(需要显式设置),则不显示阴影。
           barApp.shadowColor = [UIColor whiteColor];
           //标题文字颜色
           barApp.titleTextAttributes = dic;
           self.navigationController.navigationBar.scrollEdgeAppearance = barApp;
           self.navigationController.navigationBar.standardAppearance = barApp;
       }else {
          self.navigationController.navigationBar.titleTextAttributes = dic;
          [self.navigationBar setShadowImage:[UIImage new]];
          UIImage *navBgImg = [[UIImage createImageWithColor:HexAlphaColor(@"#FFFFFF",1.f) size:CGSizeMake(SCREEN_WIDTH, 44.f)] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
          [self.navigationController.navigationBar setBackgroundImage:navBgImg forBarMetrics:UIBarMetricsDefault];
       }
    //透明设置
    self.navigationController.navigationBar.translucent = NO;
    //navigationItem控件的颜色
    self.navigationController.navigationBar.tintColor = [UIColor blackColor];
}

下一篇:Swift版导航栏适配>>


\color{gray}{欢迎大佬来指正纠错,共同学习} PERFECT!

你可能感兴趣的:(iOS开发 - iOS15导航栏适配(Object-C、Swift))