web-dev-qa-db-fra.com

iOS 7 - La barre d'état recouvre la vue

J'ai un ViewController qui se trouve à l'intérieur d'un UINavigationcontroller, mais la barre de navigation est masquée. Lorsque j'exécute l'application sur iOS 7, la barre d'état s'affiche en haut de ma vue. Y a-t-il un moyen d'éviter cela?

Je ne veux pas écrire de code spécifique à l'OS.

Enter image description here

J'ai essayé de régler View controller-based status bar appearance sur NO, mais le problème n'a pas été résolu.

109
aryaxt

Xcode 5 a iOS 6/7 Deltas qui est spécialement conçu pour résoudre ce problème. Dans le storyboard, j'ai déplacé mes vues de 20 pixels vers le bas pour bien regarder sur iOS 7 et, afin de le rendre compatible avec iOS 6, j'ai changé Delta y en -20.

enter image description here

Étant donné que mon scénarimage n'utilise pas la disposition automatique, afin de redimensionner correctement la hauteur des vues sur iOS 6, je devais définir Delta height ainsi que Delta Y.

95
aryaxt

Si vous ne voulez simplement PAS du tout une barre d'état, vous devez mettre à jour votre plist avec ces données: Pour ce faire, dans la plist, ajoutez ces 2 paramètres:

<key>UIStatusBarHidden</key>
<true/>
<key>UIViewControllerBasedStatusBarAppearance</key>
<false/>

Dans iOS 7, vous devez concevoir votre application en gardant à l'esprit une barre d'état transparente superposée. Voir la nouvelle application iOS 7 Weather par exemple.

69
Nathan H

Ceci est le comportement par défaut de UIViewController sur iOS 7. La vue sera en plein écran, ce qui signifie que la barre d'état couvrira le haut de votre vue.

Si vous avez un UIViewController dans un UINavigationController et que la barre de navigation est visible, vous pouvez avoir le code suivant dans votre viewDidLoad ou disposer d’une image d’arrière-plan pour la barre de navigation.

self.edgesForExtendedLayout = UIRectEdgeNone;

Si vous avez masqué la barre de navigation, vous devez ajuster tous les éléments UIView en décalant de 20 points. Je ne vois pas d'autre solution. Utiliser la mise en page automatique aidera un peu.

Voici l'exemple de code permettant de détecter la version iOS, si vous souhaitez une compatibilité ascendante.

NSUInteger DeviceSystemMajorVersion() {
    static NSUInteger _deviceSystemMajorVersion = -1;
    static dispatch_once_t onceToken;

    dispatch_once(&onceToken, ^{
        NSString *systemVersion = [UIDevice currentDevice].systemVersion;
        _deviceSystemMajorVersion = [[systemVersion componentsSeparatedByString:@"."][0] intValue];
    });

   return _deviceSystemMajorVersion;
}
43
Vincent

Seule solution de travail que j'ai faite par moi-même.

Voici ma sous-classe UIViewController https://github.com/comonitos/ios7_overlaping

1 sous-classe de UIViewController

2 Sous-classe votre window.rootViewController de cette classe.

3 Voilà!

- (void) viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];

    if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0) {
        CGRect screen = [[UIScreen mainScreen] bounds];
        if (self.navigationController) {
            CGRect frame = self.navigationController.view.frame;
            frame.Origin.y = 20;
            frame.size.height = screen.size.height - 20;
            self.navigationController.view.frame = frame;
        } else {
            if ([self respondsToSelector: @selector(containerView)]) {
                UIView *containerView = (UIView *)[self performSelector: @selector(containerView)];

                CGRect frame = containerView.frame;
                frame.Origin.y = 20;
                frame.size.height = screen.size.height - 20;
                containerView.frame = frame;
            } else {
                CGRect frame = self.view.frame;
                frame.Origin.y = 20;
                frame.size.height = screen.size.height - 20;
                self.view.frame = frame;
            }
        }
    }
}

4 Ajoutez ceci pour que votre barre d'état soit blanche, juste après le [self.window makeKeyAndVisible]; !!!

if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0) {
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
}
15
comonitos
-(UIStatusBarStyle)preferredStatusBarStyle
{
    return UIStatusBarStyleLightContent;
}

-(void)viewWillLayoutSubviews{

 if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7) 
  {
    self.view.clipsToBounds = YES;
    CGRect screenRect = [[UIScreen mainScreen] bounds];
    CGFloat screenHeight = 0.0;
    if(UIDeviceOrientationIsPortrait([[UIApplication sharedApplication] statusBarOrientation]))
        screenHeight = screenRect.size.height;
    else
        screenHeight = screenRect.size.width;
    CGRect screenFrame = CGRectMake(0, 20, self.view.frame.size.width,screenHeight-20);
    CGRect viewFrame1 = [self.view convertRect:self.view.frame toView:nil];
    if (!CGRectEqualToRect(screenFrame, viewFrame1))
    {
        self.view.frame = screenFrame;
        self.view.bounds = CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.height);
    }
  }
}

Ajouter une clé dans la fenêtre --- Afficher l’apparence de la barre d’état basée sur le contrôleur: NON

13
Darshit Shah

Pour masquer la barre d'état dans iOS 7, suivez ces étapes simples:

Dans Xcode, allez dans le dossier "Resources" et ouvrez le fichier "(app name)-Info.plist file".

  • recherchez la clé "View controller based status bar appearance" et définissez sa valeur "NO"
  • recherchez la clé "Status bar is initially hidden" et définissez sa valeur "YES"

Si les clés ne sont pas là, vous pouvez les ajouter en sélectionnant "information property list" en haut et cliquez sur l'icône +

4
Mandeep Pasbola

Si vous utilisez xibs, une implémentation très simple consiste à encapsuler toutes les sous-vues dans une vue de conteneur avec des indicateurs de redimensionnement (que vous utiliserez déjà pour la compatibilité 3.5 "et 4") voir la hiérarchie ressemble à quelque chose comme ça

xib heirarchy

puis dans viewDidLoad, faites quelque chose comme ceci:

- (void)viewDidLoad
{
  [super viewDidLoad];
  // initializations
  if(SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"7.0")) // only for iOS 7 and above
  {
    CGRect frame = containerView.frame;
    frame.Origin.y += 20;
    frame.size.height -= 20;
    containerView.frame = frame;
  }
}

De cette façon, les nibs ne doivent pas être modifiés pour la compatibilité iOS 7. Si vous avez un arrière-plan, vous pouvez le garder en dehors de containerView et le laisser couvrir tout l'écran.

3
tipycalFlow

C'est tout ce qui est nécessaire pour supprimer la barre d'état. enter image description here

3
Tony

Si vous voulez le cacher complètement et simplement éviter de le traiter, cela fonctionne bien.

-(BOOL) prefersStatusBarHidden
{
    return YES;
}

référence https://stackoverflow.com/a/18873777/1030449

3
Kalel Wade

Pour la barre de navigation:

Écrire ce code:

self.navigationController.navigationBar.translucent = NO;

vient de faire le tour pour moi.

2
CoderSaru

La réponse de Vincent, edgeForExtendedLayout, a fonctionné pour moi.

Ces macros aident à déterminer la version du système d'exploitation le facilitant

// 7.0 and above 
#define IS_DEVICE_RUNNING_IOS_7_AND_ABOVE() ([[[UIDevice currentDevice] systemVersion] compare:@"7.0" options:NSNumericSearch] != NSOrderedAscending) 

// 6.0, 6.0.x, 6.1, 6.1.x
#define IS_DEVICE_RUNNING_IOS_6_OR_BELOW() ([[[UIDevice currentDevice] systemVersion] compare:@"6.2" options:NSNumericSearch] != NSOrderedDescending) 

ajouter ces macros au fichier prefix.pch de votre projet et être accessible n'importe où

if(IS_DEVICE_RUNNING_IOS_7_AND_ABOVE())
{
 //some iOS 7 stuff
 self.edgesForExtendedLayout = UIRectEdgeNone;
}

if(IS_DEVICE_RUNNING_IOS_6_OR_BELOW())
{
 // some old iOS stuff
}
1

J'ai posté ma réponse à un autre message avec la même question avec celui-ci.

De Apple Guide de transition iOS7, https://developer.Apple.com/library/ios/documentation/UserExperience/Conceptual/TransitionGuide/AppearanceCustomization.html#//Apple_ref/doc/uid/ TP40013174-CH15-SW1

Plus précisément, automaticallyAdjustsScrollViewInsets=YES et set self.edgesForExtendedLayout = UIRectEdgeNone fonctionnent pour moi lorsque je ne souhaite pas le chevauchement et que j'ai un tableviewcontroller.

1
Liangjun

Si vous voulez que "Utiliser Autolayout" soit activé à tout prix, placez le code suivant dans viewdidload.

if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7) 
{
        self.edgesForExtendedLayout = UIRectEdgeNone;
        self.extendedLayoutIncludesOpaqueBars = NO;
        self.automaticallyAdjustsScrollViewInsets = NO;
}
0
Ali Shahid

Ma barre d'état et ma barre de navigation se chevauchent après le retour de la vue paysage de YTPlayer. Voici ma solution après avoir essayé la version de @comonitos mais ne fonctionne pas sur mon iOS 8

- (void)fixNavigationBarPosition {
    if (self.navigationController) {
        CGRect frame = self.navigationController.navigationBar.frame;
        if (frame.Origin.y != 20.f) {
            frame.Origin.y = 20.f;
            self.navigationController.navigationBar.frame = frame;
        }
    }
}

Appelez cette fonction chaque fois que vous souhaitez corriger la position de la barre de navigation. J'ai appelé sur le playerView:didChangeToState: de YTPlayerViewDelegate

- (void)playerView:(YTPlayerView *)playerView didChangeToState:(YTPlayerState)state {
    switch (state) {
        case kYTPlayerStatePaused:
        case kYTPlayerStateEnded:
            [self fixNavigationBarPosition];
            break;
        default:
    }
}
0
John Pang