web-dev-qa-db-fra.com

Dans iOS13, la couleur d'arrière-plan de la barre d'état est différente de la barre de navigation en mode texte volumineux

Problems demo

Conditions préalables pour reproduire le problème:

  1. Xcode 11 beta + iOS 13 (dernière version jusqu'au 12 juin 2019)
  2. La barre de navigation est en mode texte Large
  3. Spécifiez la couleur de la barre de navigation.

La barre d'état restera en blanc dans un appareil réel, au-dessus de la barre de navigation verte.

Solutions que j'ai essayées:

  1. Revenir sur iOS12 le résoudra, mais nous rencontrerons éventuellement iOS13 ...
  2. la désactivation du mode texte volumineux le résoudra ...
  3. masquer la barre d'état le corrigera, mais cela entraînera le chevauchement du texte d'état avec l'élément de la barre de navigation.

Des idées? apprécier toute aide.

47
steven

Aucun hacks ou funkiness requis ici. La clé définit l'apparence souhaitée et définit cette valeur à la fois sur standardAppearance ET sur scrollEdgeAppearance de la barre de navigation. J'ai les éléments suivants dans l'initialisation de ma sous-classe de contrôleur de navigation de base pour l'ensemble de mon application:

if #available(iOS 13.0, *) {
    let navBarAppearance = UINavigationBarAppearance()
    navBarAppearance.configureWithOpaqueBackground()
    navBarAppearance.titleTextAttributes = [.foregroundColor: UIColor.white]
    navBarAppearance.largeTitleTextAttributes = [.foregroundColor: UIColor.white]
    navBarAppearance.backgroundColor = <insert your color here>
    navigationBar.standardAppearance = navBarAppearance
    navigationBar.scrollEdgeAppearance = navBarAppearance
}

enter image description here

123
Mike

Sur iOS 13, les barres de navigation utilisant un grand titre ont une couleur transparente par Apple directives d'interface humaine. Voir plus d'infos ici :

Dans iOS 13 et versions ultérieures, une grande barre de navigation par titre n'inclut pas de fond ni d'ombre par défaut. De plus, un grand titre passe à un titre standard lorsque les gens commencent à faire défiler le contenu

12
Hans Knöchel

Si le problème est que vous souhaitez donner une couleur à la barre de navigation lorsque le grand titre s'affiche, utilisez la nouvelle classe UINavigationBarAppearance.

    let app = UINavigationBarAppearance()
    app.backgroundColor = .blue
    self.navigationController?.navigationBar.scrollEdgeAppearance = app
9
matt

Code universel

        let navBarAppearance = UINavigationBarAppearance()
        navBarAppearance.configureWithOpaqueBackground()
        navBarAppearance.backgroundColor = // your color
        navBarAppearance.shadowImage = nil // line
        navBarAppearance.shadowColor = nil // line
        UINavigationBar.appearance(whenContainedInInstancesOf: [UINavigationController.self]).standardAppearance = navBarAppearance
        UINavigationBar.appearance(whenContainedInInstancesOf: [UINavigationController.self]).scrollEdgeAppearance = navBarAppearance
6
Chris Van Buskirk

mon extension navigationBar, 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
    }
}}

Comment utiliser:

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

Réglez la barre d'état basée sur ViewController ...... sur NO dans info.plist si vous voulez un contenu léger

Si vous ne voulez pas que les grands titres le définissent sur faux

Testé sur iOS 13, j'espère que cette aide :)

6
Fabio

Solutions Objective C et iOS 13

UINavigationBarAppearance* navBarAppearance = [self.navigationController.navigationBar standardAppearance];
        [navBarAppearance configureWithOpaqueBackground];
        navBarAppearance.titleTextAttributes = @{NSForegroundColorAttributeName:TitleColor};
        navBarAppearance.largeTitleTextAttributes = @{NSForegroundColorAttributeName: TitleColor};
        navBarAppearance.backgroundColor = TopColor;
        self.navigationController.navigationBar.standardAppearance = navBarAppearance;
        self.navigationController.navigationBar.scrollEdgeAppearance = navBarAppearance;
5
mohammad alabid

Pour iOS 13, j'avais un problème avec la ligne d'ombre de la barre. La définition de l'image d'ombre Bars sur nil a résolu ce problème.

Avant

func configureNavigation() {
        let navBarAppearance = UINavigationBarAppearance()
        navBarAppearance.configureWithOpaqueBackground()
        navBarAppearance.largeTitleTextAttributes = [.foregroundColor: UIColor.myColor,
                                                     .font: UIFont(name: "MyFont", size: 42)!]
        navBarAppearance.backgroundColor = .white
        navigationController?.navigationBar.isTranslucent = false
        navigationController?.navigationBar.scrollEdgeAppearance = navBarAppearance
    }

Image with shadow

Après

func configureNavigation() {
        let navBarAppearance = UINavigationBarAppearance()
        navBarAppearance.configureWithOpaqueBackground()
        navBarAppearance.largeTitleTextAttributes = [.foregroundColor: UIColor.myColor,
                                                     .font: UIFont(name: "MyFont", size: 42)!]
        navBarAppearance.backgroundColor = .white
        navBarAppearance.shadowColor = nil
        navigationController?.navigationBar.isTranslucent = false
        navigationController?.navigationBar.scrollEdgeAppearance = navBarAppearance
    }

Image without shadow

3
Andrew Edwards

Merci à la réponse de Mike et Hans. Mon cas est une barre d'état à moitié transparente et une barre de navigation avec alpha 0.5. iOS13 semble compliqué. Ci-dessous est mon résultat de test, fonctionnera si vous voulez transparent pour les deux.

if #available(iOS 13.0, *) {
                let navBarAppearance = UINavigationBarAppearance()
                // This only set top status bar as transparent, not the nav bar.
                navBarAppearance .configureWithTransparentBackground()
                // This set the color for both status bar and nav bar(alpha 1).
                navBarAppearance.backgroundColor = UIColor.red.withAlphaComponent(0.5)
                navigationController?.navigationBar.standardAppearance = navBarAppearance
                navigationController?.navigationBar.scrollEdgeAppearance = navBarAppearance
                // Nav bar need sets to translucent for both nav bar and status bar to be translucent.
                navigationController?.navigationBar.isTranslucent = true
                // // Need to reset nav bar's color to make it clear to display navBarAppearance's color
                navigationController?.navigationBar.backgroundColor = UIColor.clear
               } 
1
Ning

J'ai eu un problème similaire lors de la mise à jour d'une de mes applications pour être plus compatible avec iOS 13. Comme Hans mentionné ci-dessus, les grands titres sont transparents par défaut. Si vous êtes un gros utilisateur de Storyboard comme moi, il y a un autre paramètre dans la barre latérale qui est facile à activer.

Si vous cliquez sur votre barre de navigation dans le story-board, la valeur par défaut est généralement la sélection de Navigation Item, et vous n'aurez aucune option de personnalisation. Sélectionnez le Navigation Bar option au-dessus, puis vous pouvez choisir une couleur d'arrière-plan personnalisée de tout ce que vous voulez dans l'inspecteur de droite.

enter image description here

1
Drew

Swift 5

override func traitCollectionDidChange(_ previousTraitCollection: UITraitCollection?) {
    super.traitCollectionDidChange(previousTraitCollection)

    let userInterfaceStyle = traitCollection.userInterfaceStyle
    modeDetect(userInterfaceStyle: userInterfaceStyle)

}

override func viewDidAppear(_ animated: Bool) {
    navigationController?.navigationBar.barStyle = .black
    navigationController?.navigationBar.titleTextAttributes = [.foregroundColor: UIColor.white]
}

func modeDetect(userInterfaceStyle: UIUserInterfaceStyle) {
    switch userInterfaceStyle {
    case .light:
        navigationController?.navigationBar.barTintColor = .systemPink
    case .dark:
        navigationController?.navigationBar.barTintColor = .systemBackground
    default:
        break
    }
}
0
Dumex

Appelez cette fonction avec un argument approprié. Ce code fonctionne correctement.

open func showNavigationBar(large: Bool,
                            animated: Bool,
                            isTransparabar: Bool,
                            titleColor: UIColor,
                            barBackGroundColor: UIColor,
                            fontSize: CGFloat) {

        navigationController?.navigationBar.barTintColor = barBackGroundColor
        navigationController?.navigationBar.backgroundColor = barBackGroundColor
        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 = barBackGroundColor
                appearance.titleTextAttributes = [.foregroundColor: titleColor]
                appearance.largeTitleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor]

                navigationController?.navigationBar.standardAppearance = appearance
                navigationController?.navigationBar.compactAppearance = appearance
                navigationController?.navigationBar.scrollEdgeAppearance = appearance
            } else {
                self.navigationController?.navigationBar.largeTitleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor]
            }
        } else {
            self.navigationController?.navigationBar.prefersLargeTitles = false
            self.navigationController?.navigationBar.titleTextAttributes = [NSAttributedString.Key.foregroundColor: titleColor!]
        }
    }
0
Kiran Sarvaiya

Le code Objective-C suivant a fait en sorte que la barre de navigation iOS 13 se comporte comme la version précédente pour moi:

    if (@available(iOS 13.0, *)) {
        // Setup iOS 13 navigation bar
        sharedSelector.navigationBar.scrollEdgeAppearance = sharedSelector.navigationBar.standardAppearance;
    } else {
        // Fallback on earlier versions
    }
0
André Pinto

J'ai découvert qu'avec les storyboards, vous devez simuler la barre de navigation (ne fonctionne vraiment qu'avec les barres de navigation opaques, en supposant que votre vert soit opaque). La meilleure façon que j'ai trouvée était de créer une vue de l'espace réservé (violet) qui correspond aux encarts de zone de sécurité, puis d'ajouter une fausse vue derrière la barre de navigation (cyan/bleu) qui est la hauteur restante. Fonctionne pour mon projet, mais oui, c'est un peu un hack. Screenshot from Xcode 11 beta 4 displaying constraints required for status bar hack

Modifier: c'est principalement pour LaunchScreen.storyboard où vous ne pouvez pas utiliser une classe de contrôleur de vue personnalisée.

0
SunburstEnzo