I am trying to set the colour of the navigation bar in the limited library picker. To do this I have the following lines in AppDelegate.application:didFinishLaunchingWithOptions:
if (@available(iOS 13, *)) {
UINavigationBarAppearance *navigationBarAppearance = [UINavigationBarAppearance new];
navigationBarAppearance.backgroundColor = UIColor.yellowColor;
[UINavigationBar appearance].standardAppearance = navigationBarAppearance;
[UINavigationBar appearance].scrollEdgeAppearance = navigationBarAppearance;
}
[UINavigationBar appearance].barTintColor = UIColor.greenColor;
[UINavigationBar appearance].backgroundColor = UIColor.redColor;
This sets the colour to green as I would expect on iOS 14:
But a faded red colour on iOS 15:
How can I set the colour correctly on iOS 15?
EDIT: Minimum reproducible example (Set up a new iOS project with single view controller and add the NSPhotoLibraryUsageDescription key to info.plist)
import UIKit
import Photos
import PhotosUI
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
PHPhotoLibrary.requestAuthorization(for: .readWrite, handler: { _ in})
PHPhotoLibrary.shared().presentLimitedLibraryPicker(from: self)
}
}
AppDelegate.swift:
import UIKit
@main
class AppDelegate: UIResponder, UIApplicationDelegate {
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
if #available(iOS 13, *) {
let navigationBarAppearance = UINavigationBarAppearance()
navigationBarAppearance.backgroundColor = UIColor.yellow
UINavigationBar.appearance().standardAppearance = navigationBarAppearance
UINavigationBar.appearance().scrollEdgeAppearance = navigationBarAppearance
}
UINavigationBar.appearance().barTintColor = UIColor.green
UINavigationBar.appearance().backgroundColor = UIColor.red
return true
}
// MARK: UISceneSession Lifecycle
func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
// Called when a new scene session is being created.
// Use this method to select a configuration to create the new scene with.
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
}
EDIT: Objective-C version of Matt's solution:
UIGraphicsImageRenderer * imageRenderer = [[UIGraphicsImageRenderer alloc]initWithSize:CGSizeMake(1, 1)];
UIImage *image = [imageRenderer imageWithActions:^(UIGraphicsImageRendererContext *context){
[TOOLBAR_BACKGROUND_COLOUR setFill];
[context fillRect:CGRectMake(0, 0, 1, 1)];
}];
[[UINavigationBar appearance] setBackgroundImage:image forBarMetrics:UIBarMetricsDefault];
CodePudding user response:
The way to get completely control over a navigation bar's color is to use a background image. Make an image renderer. Fill the context with solid red and extract the image from the renderer. Call setBackgroundImage
on the appearance proxy.
I don't have time to translate the code from Swift to Objective-C so I leave it up to you:
let rend = UIGraphicsImageRenderer(size:.init(width:100, height:100))
let im = rend.image {
con in
UIColor.red.setFill()
con.fill(.init(x: 0, y: 0, width: 100, height: 100))
}
UINavigationBar.appearance().setBackgroundImage(im, for: .default)