iOS 11-无法更改导航栏高度

iOS 11-无法更改导航栏高度,ios,swift,height,uinavigationbar,ios11,Ios,Swift,Height,Uinavigationbar,Ios11,我正在开发一个应用程序,我刚刚升级到Xcode 9/Swift 4,还将我的iPhone升级到了iOS 11。 该应用程序是在我安装iOS 11时安装的,在我从Xcode运行它之前,一切似乎都正常。现在我只能使用默认的导航栏高度 我用来更改高度的代码不再有效: class CustomNavControllerVC: UINavigationController { let navBarHeight : CGFloat = 64.0 let navbarBackButtonCol

我正在开发一个应用程序,我刚刚升级到Xcode 9/Swift 4,还将我的iPhone升级到了iOS 11。 该应用程序是在我安装iOS 11时安装的,在我从Xcode运行它之前,一切似乎都正常。现在我只能使用默认的导航栏高度

我用来更改高度的代码不再有效:

class CustomNavControllerVC: UINavigationController
{
    let navBarHeight : CGFloat = 64.0
    let navbarBackButtonColor = UIColor(red: 247/255, green: 179/255, blue: 20/255, alpha: 1)

    override func viewDidLoad()
    {
        super.viewDidLoad()

        print("CustomNavControllerVC > viewDidLoad")
    }

    override func viewDidLayoutSubviews()
    {
        print("CustomNavControllerVC > viewDidLayoutSubviews")

        super.viewDidLayoutSubviews()

        navigationBar.frame.size.height = navBarHeight
        navigationBar.tintColor = navbarBackButtonColor
    }

    override func didReceiveMemoryWarning()
    {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }
}


// In my VCs

override func viewDidLoad()
{
    customizeNavBar()
}


func customizeNavBar()
{
    let navbarBackItem = UIBarButtonItem()
    navbarBackItem.title = "Înapoi"
    navigationItem.backBarButtonItem = navbarBackItem

    let navbarImageView = UIImageView(frame: CGRect(x: 0, y: 0, width: 55, height: 20))
    navbarImageView.contentMode = .scaleToFill

    let navbarLogo = UIImage(named: "NavBarLogo.png")
    navbarImageView.image = navbarLogo

    navigationItem.titleView = navbarImageView
}
到目前为止,我在这个问题上唯一能找到的是:

但不幸的是,提供的信息没有帮助

有什么想法/建议吗?

更新于2017年10月6日

我也有同样的问题。下面是我的解决方案。我假设身高是66

我的解决方案在iOS 10、11上运行良好

如果有帮助,请选择我的答案

创建NavgationBar.swift

import UIKit

class NavigationBar: UINavigationBar {

    //set NavigationBar's height
    var customHeight : CGFloat = 66

    override func sizeThatFits(_ size: CGSize) -> CGSize {

        return CGSize(width: UIScreen.main.bounds.width, height: customHeight)

    }

    override func layoutSubviews() {
        super.layoutSubviews()

        frame = CGRect(x: frame.origin.x, y:  0, width: frame.size.width, height: customHeight)

        // title position (statusbar height / 2)
        setTitleVerticalPositionAdjustment(-10, for: UIBarMetrics.default)

        for subview in self.subviews {
            var stringFromClass = NSStringFromClass(subview.classForCoder)
            if stringFromClass.contains("BarBackground") {
                subview.frame = CGRect(x: 0, y: 0, width: self.frame.width, height: customHeight)
                subview.backgroundColor = .yellow

            }

            stringFromClass = NSStringFromClass(subview.classForCoder)
            if stringFromClass.contains("BarContent") {

                subview.frame = CGRect(x: subview.frame.origin.x, y: 20, width: subview.frame.width, height: customHeight - 20)

                subview.backgroundColor = UIColor(red: 20/255, green: 20/255, blue: 20/255, alpha: 0.4)

            }
        }
    }


}
设置故事板

设置自定义导航栏类

添加TestView+设置安全区域

ViewController.swift

import UIKit

class ViewController: UIViewController {

    var navbar : UINavigationBar!

    @IBOutlet weak var testView: UIView!

    override func viewDidLoad() {
        super.viewDidLoad()

        //update NavigationBar's frame
        self.navigationController?.navigationBar.sizeToFit()
        print("NavigationBar Frame : \(String(describing: self.navigationController!.navigationBar.frame))")

    }

    //Hide Statusbar
    override var prefersStatusBarHidden: Bool {

        return true
    }

    override func viewDidAppear(_ animated: Bool) {

        super.viewDidAppear(false)

        //Important!
        if #available(iOS 11.0, *) {

            //Default NavigationBar Height is 44. Custom NavigationBar Height is 66. So We should set additionalSafeAreaInsets to 66-44 = 22
            self.additionalSafeAreaInsets.top = 22

        }

    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }


}
import UIKit

class SecondViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.


        // Create BackButton
        var backButton: UIBarButtonItem!
        let backImage = imageFromText("Back", font: UIFont.systemFont(ofSize: 16), maxWidth: 1000, color:UIColor.white)
        backButton = UIBarButtonItem(image: backImage, style: UIBarButtonItemStyle.plain, target: self, action: #selector(SecondViewController.back(_:)))

        self.navigationItem.leftBarButtonItem = backButton
        self.navigationItem.leftBarButtonItem?.setBackgroundVerticalPositionAdjustment(-10, for: UIBarMetrics.default)


    }
    override var prefersStatusBarHidden: Bool {

        return true
    }
    @objc func back(_ sender: UITabBarItem){

        self.navigationController?.popViewController(animated: true)

    }


    //Helper Function : Get String CGSize
    func sizeOfAttributeString(_ str: NSAttributedString, maxWidth: CGFloat) -> CGSize {
        let size = str.boundingRect(with: CGSize(width: maxWidth, height: 1000), options:(NSStringDrawingOptions.usesLineFragmentOrigin), context:nil).size
        return size
    }


    //Helper Function : Convert String to UIImage
    func imageFromText(_ text:NSString, font:UIFont, maxWidth:CGFloat, color:UIColor) -> UIImage
    {
        let paragraph = NSMutableParagraphStyle()
        paragraph.lineBreakMode = NSLineBreakMode.byWordWrapping
        paragraph.alignment = .center // potentially this can be an input param too, but i guess in most use cases we want center align

        let attributedString = NSAttributedString(string: text as String, attributes: [NSAttributedStringKey.font: font, NSAttributedStringKey.foregroundColor: color, NSAttributedStringKey.paragraphStyle:paragraph])

        let size = sizeOfAttributeString(attributedString, maxWidth: maxWidth)
        UIGraphicsBeginImageContextWithOptions(size, false , 0.0)
        attributedString.draw(in: CGRect(x: 0, y: 0, width: size.width, height: size.height))
        let image = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return image!
    }




    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }



}
斯威夫特

import UIKit

class ViewController: UIViewController {

    var navbar : UINavigationBar!

    @IBOutlet weak var testView: UIView!

    override func viewDidLoad() {
        super.viewDidLoad()

        //update NavigationBar's frame
        self.navigationController?.navigationBar.sizeToFit()
        print("NavigationBar Frame : \(String(describing: self.navigationController!.navigationBar.frame))")

    }

    //Hide Statusbar
    override var prefersStatusBarHidden: Bool {

        return true
    }

    override func viewDidAppear(_ animated: Bool) {

        super.viewDidAppear(false)

        //Important!
        if #available(iOS 11.0, *) {

            //Default NavigationBar Height is 44. Custom NavigationBar Height is 66. So We should set additionalSafeAreaInsets to 66-44 = 22
            self.additionalSafeAreaInsets.top = 22

        }

    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }


}
import UIKit

class SecondViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.


        // Create BackButton
        var backButton: UIBarButtonItem!
        let backImage = imageFromText("Back", font: UIFont.systemFont(ofSize: 16), maxWidth: 1000, color:UIColor.white)
        backButton = UIBarButtonItem(image: backImage, style: UIBarButtonItemStyle.plain, target: self, action: #selector(SecondViewController.back(_:)))

        self.navigationItem.leftBarButtonItem = backButton
        self.navigationItem.leftBarButtonItem?.setBackgroundVerticalPositionAdjustment(-10, for: UIBarMetrics.default)


    }
    override var prefersStatusBarHidden: Bool {

        return true
    }
    @objc func back(_ sender: UITabBarItem){

        self.navigationController?.popViewController(animated: true)

    }


    //Helper Function : Get String CGSize
    func sizeOfAttributeString(_ str: NSAttributedString, maxWidth: CGFloat) -> CGSize {
        let size = str.boundingRect(with: CGSize(width: maxWidth, height: 1000), options:(NSStringDrawingOptions.usesLineFragmentOrigin), context:nil).size
        return size
    }


    //Helper Function : Convert String to UIImage
    func imageFromText(_ text:NSString, font:UIFont, maxWidth:CGFloat, color:UIColor) -> UIImage
    {
        let paragraph = NSMutableParagraphStyle()
        paragraph.lineBreakMode = NSLineBreakMode.byWordWrapping
        paragraph.alignment = .center // potentially this can be an input param too, but i guess in most use cases we want center align

        let attributedString = NSAttributedString(string: text as String, attributes: [NSAttributedStringKey.font: font, NSAttributedStringKey.foregroundColor: color, NSAttributedStringKey.paragraphStyle:paragraph])

        let size = sizeOfAttributeString(attributedString, maxWidth: maxWidth)
        UIGraphicsBeginImageContextWithOptions(size, false , 0.0)
        attributedString.draw(in: CGRect(x: 0, y: 0, width: size.width, height: size.height))
        let image = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return image!
    }




    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }



}

黄色是barbackgroundView。黑色不透明度为BarContentView

我删除了BarContentView的背景色


就是这样。

为什么不能使用自定义视图而不是
UINavigationBar
?UIKit团队似乎从未打算让
UINavigationBar
支持自定义高度。如果你想扩大导航栏的大小,我会使用苹果在这里推广的技术:@ MuksHyLokay-最初的Navbar应该有标准的高度与标志图像中间,所以我决定使用标准NavBarController。30个屏幕和很多类之后,有人决定它必须具有自定义高度,所以我决定使用该方法。@beyowulf-我看到了,但我希望找到解决方案。我将使用所提供的技术,看看会发生什么。令人遗憾的是,我们被苹果无能的开发人员所束缚。看起来唯一要做的就是忘记NavController,再一次自己动手。谢谢。我试试看。谢谢。但安全区的顶部并没有更新。安全区域的顶部仍然是44px。你有解决办法吗?设置导航栏高度后,我不知道如何更新安全区域的顶部。@VictorRay您能分享您的代码吗?我在我的项目中使用此代码。我希望帮助youios 11.2打破这一点在我的情况下,视觉外观工作正常,但我在这些额外的22像素中添加的任何控件都不会对触摸输入做出反应。我有一个跨越“边界”的大按钮,比如从顶部25px开始,到底部60px结束。我试着点击它,只有在顶部44px(默认条高)范围内的点击才会通过并被接收。