iOS13导航栏大标题未覆盖状态栏

50
在iOS 13上,使用iPhone X时,大标题导航栏不会覆盖状态栏,但是当滚动并过渡到传统导航栏时,它可以完美地工作。这不会影响没有刘海的设备。
大标题: 输入图像描述 传统导航栏: 它都嵌入在一个导航控制器中,所以我不知道为什么会发生这种情况。谢谢。

导航栏在IOS 13中的行为已经发生了变化,因此这可能是有意为之。 - matt
@matt 我想应该不会吧 - 这样的丑陋改变看起来不太像苹果的风格,而且普通导航栏应该保持正常行为;为什么大标题会有区别呢? - Harry J
你之前是如何覆盖导航栏背景颜色的? - Sebastian
@Sebastian,我发现这只是标准问题,只有更新到Xcode 11和iOS 13才会出现这个问题。 - Harry J
3个回答

102

在 iOS 13 之前,自定义 UINavigationBar 的官方方法如下:

// text/button color
UINavigationBar.appearance().tintColor = .white
// background color
UINavigationBar.appearance().barTintColor = .purple
// required to disable blur effect & allow barTintColor to work
UINavigationBar.appearance().isTranslucent = false

iOS 13改变了导航栏的工作方式,因此您需要略微不同地进行操作,以支持新旧两种方式:

if #available(iOS 13.0, *) {
    let appearance = UINavigationBarAppearance()
    appearance.backgroundColor = .purple
    appearance.titleTextAttributes = [.foregroundColor: UIColor.white]
    appearance.largeTitleTextAttributes = [.foregroundColor: UIColor.white]

    UINavigationBar.appearance().tintColor = .white
    UINavigationBar.appearance().standardAppearance = appearance
    UINavigationBar.appearance().compactAppearance = appearance
    UINavigationBar.appearance().scrollEdgeAppearance = appearance
} else {
    UINavigationBar.appearance().tintColor = .white
    UINavigationBar.appearance().barTintColor = .purple
    UINavigationBar.appearance().isTranslucent = false
}

1
更改为正确答案,因为它更常规且更可靠。谢谢。 - Harry J
@Koen。好的观点,答案没有包括更改UIBarButtons。我添加了UINavigationBar.appearance().tintColor = .white,这使得该更改生效。 - Sebastian
1
@MobileMon,你当前的彩色半透明导航栏代码是什么? - Sebastian
@MobileMon 你成功地让iOS13中的导航栏半透明了吗? - user3626411
1
如果你想模仿苹果的半透明导航栏,只需删除这一行代码 "UINavigationBar.appearance().barTintColor = MyColor":https://mobilemon.code.blog/2019/10/11/how-to-make-your-uinavigationbar-look-like-apples-in-ios-13/ - MobileMon
显示剩余6条评论

15

使用我的扩展程序,已测试 iOS 13 和 Swift 5

extension UIViewController {
func configureNavigationBar(largeTitleColor: UIColor, backgoundColor: UIColor, tintColor: UIColor, title: String, preferredLargeTitle: Bool) {
    if #available(iOS 13.0, *) {
        let navBarAppearance = UINavigationBarAppearance()
        navBarAppearance.configureWithOpaqueBackground()
        navBarAppearance.largeTitleTextAttributes = [.foregroundColor: largeTitleColor]
        navBarAppearance.titleTextAttributes = [.foregroundColor: largeTitleColor]
        navBarAppearance.backgroundColor = backgoundColor

        navigationController?.navigationBar.standardAppearance = navBarAppearance
        navigationController?.navigationBar.compactAppearance = navBarAppearance
        navigationController?.navigationBar.scrollEdgeAppearance = navBarAppearance

        navigationController?.navigationBar.prefersLargeTitles = preferredLargeTitle
        navigationController?.navigationBar.isTranslucent = false
        navigationController?.navigationBar.tintColor = tintColor
        navigationItem.title = title

    } else {
        // Fallback on earlier versions
        navigationController?.navigationBar.barTintColor = backgoundColor
        navigationController?.navigationBar.tintColor = tintColor
        navigationController?.navigationBar.isTranslucent = false
        navigationItem.title = title
    }
}}

使用方法:

configureNavigationBar(largeTitleColor: .yourColor, backgoundColor: .yourColor, tintColor: .yourColor, title: "yuorTitle", preferredLargeTitle: true)

如果您希望状态栏内容是浅色,请在info.plist中将ViewController-based status bar......设置为NO。

如果您不想要largeTitles,请将其设置为false。

要使导航栏不透明,请在navBarAppearance.configureWithOpaqueBackground()中进行更改:

navBarAppearance.configureWithDefaultBackground()
navigationController?.navigationBar.isTranslucent = true

将呼叫集背景颜色设置为.clear。

UPDATE: 如果您想从导航控制器和大标题开始第一个控制器,请不要忘记像这样在场景代理中设置启动控制器:

guard let windowScene = (scene as? UIWindowScene) else { return }
window = UIWindow(windowScene: windowScene)
window?.makeKeyAndVisible()
let vC = UINavigationController(rootViewController: YourFirstViewController())
window?.rootViewController = vC

希望这有所帮助 :)


2
你很棒。 - Fahim Rahman

1

为了完整的应用程序导航栏支持,请在您的代码中添加此扩展。

import UIKit
extension UIViewController {


    open func showNavigationBar(_ large: Bool,
                                _ animated: Bool,
                                titleColor: UIColor,
                                barTintColor: UIColor,
                                fontSize: CGFloat) {

        navigationController?.navigationBar.barTintColor = barTintColor
        navigationController?.navigationBar.backgroundColor = barTintColor
        navigationController?.navigationBar.isTranslucent = true
        self.navigationController?.setNavigationBarHidden(false, animated: animated)
        if large {
            self.navigationController?.navigationBar.prefersLargeTitles = true
            if #available(iOS 13.0, *) {
                let appearance = UINavigationBarAppearance()
                appearance.backgroundColor = barTintColor
                appearance.titleTextAttributes = [.foregroundColor: titleColor]
                appearance.largeTitleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor,
                                                       NSAttributedString.Key.font: UIFont(resource: R.font.robotoMedium, size: fontSize)!]

                navigationController?.navigationBar.standardAppearance = appearance
                navigationController?.navigationBar.compactAppearance = appearance
                navigationController?.navigationBar.scrollEdgeAppearance = appearance
            } else {
                self.navigationController?.navigationBar.largeTitleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor,
                                                                                     NSAttributedString.Key.font: UIFont(resource: R.font.robotoMedium, size: fontSize)!]
            }
        } else {
            self.navigationController?.navigationBar.prefersLargeTitles = false
            self.navigationController?.navigationBar.titleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor,
                                                                            NSAttributedString.Key.font: UIFont(resource: R.font.robotoMedium, size: 20.0)!]
        }
    }
}

然后简单地调用此方法。
self.showNavigationBar(true, true, titleColor: UIColor.blue, barTintColor: UIColor.red, fontSize: 32.0)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接