2017-09-22 175 views
3

到目前爲止我處理梯度導航欄下面的manner_處理導航欄背景漸變

let gradient = CAGradientLayer() 
    let sizeLength = UIScreen.main.bounds.size.height * 2 
    let defaultNavigationBarFrame = CGRect(x: 0, y: 0, width: sizeLength, height: 64) 
    gradient.frame = defaultNavigationBarFrame 
    gradient.colors = [UIColor(hex:"92CF1F").cgColor, UIColor(hex:"79AB1B").cgColor] 

    UINavigationBar.appearance().setBackgroundImage(self.image(fromLayer: gradient), for: .default) 
    UINavigationBar.appearance().tintColor = UIColor.white 
    UINavigationBar.appearance().isTranslucent = false 
    UINavigationBar.appearance().clipsToBounds = false 

    if DeviceType.IS_IPAD{ 
     UINavigationBar.appearance().titleTextAttributes = [NSFontAttributeName : UIFont .systemFont(ofSize: 24, weight: UIFontWeightLight), NSForegroundColorAttributeName: UIColor.white] 
    } 
    else 
    { 
     UINavigationBar.appearance().titleTextAttributes = [NSFontAttributeName : UIFont .systemFont(ofSize: 20, weight: UIFontWeightLight), NSForegroundColorAttributeName: UIColor.white] 
    } 

    UISearchBar.appearance().backgroundColor = UIColor.clear 

但現在在iPhone XI有問題,由於「64」作爲導航欄高度梯度below_

enter image description here

請建議本可以在每種情況下可以使用動態修復。

回答

0

您不僅可以再假定導航欄高度爲64,您不能再假設靜態高度。

我認爲實現你想要做的最簡單的方法是使用UINavigationControllerinit(navigationBarClass:toolbarClass:)方法與自定義UINavigationBar子類覆蓋layerClass直接指定CAGradientLayer

不幸的是,我不認爲有一種方法可以通過UIAppearance「發射並忘記」。

1

我已經通過屏幕高度檢查了iPhone X模式,然後更改生成的漸變圖像以填充導航欄。 我認爲這不是最好的解決方法,但它現在工作正常。

class func checkiPhoneModel() -> String { 
    if UIDevice().userInterfaceIdiom == .phone { 
     switch UIScreen.main.nativeBounds.height { 
     case 1136: 
      return "5, 5s, 5c, se" 
     case 1334: 
      return "6, 6s, 7" 
     case 2208: 
      return "6+, 6S+, 7+" 
     case 2436: 
      return "X" 
     default: 
      return "unknown" 
     } 
    } 
    return "" 
} 

然後可以創建用於UINavigationBar的擴展,增加了方法來改變顏色的梯度圖像:

extension UINavigationBar { 

    func setGradientBackground(colors: [UIColor]) { 

     var size:CGFloat 

     if Reachability.checkiPhoneModel() == "X" { 
      size = 44 
     } 
     else { 
      size = 20 
     } 

     var updatedFrame = bounds 
     updatedFrame.size.height += size 
     let gradientLayer = CAGradientLayer(frame: updatedFrame, colors: colors) 

     setBackgroundImage(gradientLayer.creatGradientImage(), for: UIBarMetrics.default) 
    } 
} 

大小變量被設置爲44時是iPhone X,等機型它接收20

然後在您的viewDidLoad,只需調用最近創建的方法:

self.navigationController?.navigationBar.setGradientBackground(colors: [.red, .yellow]) 

The result is something like this. In my case, the gradient uses alpha zero at the bottom of the navigationBar

+0

那麼,這是一個很好的實現方式,但現在我只是檢查了 static let IS_IPHONE_X = UIDevice.current.userInterfaceIdiom == .phone && max(UIScreen.main.bounds.size.width,UIScreen.main.bounds .size.height)== 812.0 如果DeviceType.IS_IPHONE_X { defaultNavigationBarFrame =的CGRect(X:0,Y:0,寬度:sizeLength,高度:88) } 否則{ defaultNavigationBarFrame =的CGRect(X:0, y:0,width:sizeLength,height:64) } –

0

使用阿利森Barauna的回答你的問題,我設法只是更新我的UINavigationBar的擴展來解決這個問題是這樣的:

extension UINavigationBar { 

@objc func setGradientBackground(colors: [UIColor]) { 

    var updatedFrame = bounds 

    if UIDevice().userInterfaceIdiom == .phone { 
     if UIScreen.main.nativeBounds.height == 2436{ 
      updatedFrame.size.height += 44 
     } else { 
      updatedFrame.size.height += 20 
     } 
    } 

    let gradientLayer = CAGradientLayer(frame: updatedFrame, colors: colors) 
    setBackgroundImage(gradientLayer.createGradientImage(), for: UIBarMetrics.default) 
} 

通過該做的高度將只是被設置爲大iPhone X大小(44),如果程序檢測到正在使用iPhone X(因爲屏幕高度爲2436)。