webentwicklung-frage-antwort-db.com.de

Richtige Methode zum Ausblenden der Statusleiste unter iOS, mit Animation und Ändern der Stammansicht

Stellen Sie sich einen Ansichtscontroller vor, der die Statusleiste herausziehen (oder ausblenden) muss, wenn auf eine Schaltfläche geklickt wird.

- (void) buttonClick:(id)sender
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES
                                            withAnimation:UIStatusBarAnimationSlide];
}

Durch das Obige wird die Statusleiste effektiv ausgeblendet, die Größe der Stammansicht wird jedoch nicht ordnungsgemäß angepasst, sodass oben eine Lücke von 20 Pixeln verbleibt.

Was ich erwartet habe, ist, dass die Stammansicht den Bereich erweitert, der zuvor von der Statusleiste verwendet wurde (animiert, mit derselben Dauer wie die Statusleistenanimation).

Was ist der richtige Weg, dies zu tun?

(Ich bin mir bewusst, dass es viele ähnliche Fragen gibt, aber ich konnte nichts dazu finden, die Statusleiste bei Bedarf auszublenden, anstatt sie zu verstecken, um einen neuen View-Controller anzuzeigen)

Die "rohe Gewalt" Annäherung

Natürlich funktioniert das folgende ...

[[UIApplication sharedApplication] setStatusBarHidden:YES
                                        withAnimation:UIStatusBarAnimationSlide];
[UIView animateWithDuration:0.25 animations:^{
    CGRect frame = self.view.frame;
    frame.Origin.y -= 20;
    frame.size.height += 20;
    self.view.frame = frame;
}];

... hat aber Nachteile:

  • Hardcodes für die Dauer der Folienanimation
  • Hardcodes die Höhe der Statusleiste
  • Die Stammansicht Origin bleibt bei (0, -20). Ich mag es, wenn meine Bilder möglichst bei (0,0) beginnen.

Was ich schon probiert habe

  • Stellen Sie sicher, dass die Autoresize-Maske der Root-Ansicht UIViewAutoresizingFlexibleTopMargin und UIViewAutoresizingFlexibleHeight hat.
  • [self.view setNeedsLayout] aufgerufen, nachdem die Statusleiste ausgeblendet wurde.
  • [self.view setNeedsDisplay] aufgerufen, nachdem die Statusleiste ausgeblendet wurde.
  • Setzen Sie wantsFullScreenLayout vor und nach dem Ausblenden der Statusleiste auf YES.
32
hpique

Das funktioniert gut und hat nichts hartcodiert .

CGRect appFrame = [[UIScreen mainScreen] applicationFrame];

[[UIApplication sharedApplication] setStatusBarHidden:YES withAnimation:UIStatusBarAnimationSlide];
[UIView animateWithDuration:0.25 animations:^{
    self.navigationController.navigationBar.frame = self.navigationController.navigationBar.bounds;
    self.view.window.frame = CGRectMake(0, 0, appFrame.size.width, appFrame.size.height);
}];
16
Lefteris

Für diejenigen, die versuchen, dies mit dem Aussehen der View Controller-Statusleiste zu implementieren, müssen Sie die Methode prefersStatusBarHidden in Ihrem View Controller implementieren

 - (BOOL)prefersStatusBarHidden
{
    // If self.statusBarHidden is TRUE, return YES. If FALSE, return NO.
    return (self.statusBarHidden) ? YES : NO;
}

Und dann in Ihrer Button-Klick-Methode:

- (void) buttonClick:(id)sender
{
    // Switch BOOL value
    self.statusBarHidden = (self.statusBarHidden) ? NO : YES;

    // Update the status bar
    [UIView animateWithDuration:0.25 animations:^{
        [self setNeedsStatusBarAppearanceUpdate];
    }];
}

Um den Animationsstil festzulegen, verwenden Sie Folgendes:

-(UIStatusBarAnimation)preferredStatusBarUpdateAnimation
{
    return UIStatusBarAnimationSlide;
}

Und den Stil anpassen:

- (UIStatusBarStyle)preferredStatusBarStyle
{
    return UIStatusBarStyleLightContent;
}
23
awfulcode

Sie können den Modal-View-Controller anzeigen und wieder schließen, um die Statusleiste korrekt auszublenden

- (void)toggleStatusBar {
    BOOL isStatusBarHidden = [[UIApplication sharedApplication] isStatusBarHidden];
    [[UIApplication sharedApplication] setStatusBarHidden:!isStatusBarHidden];

    UIViewController *vc = [[UIViewController alloc] init];
    [self presentViewController:vc animated:NO completion:nil];
    [self dismissViewControllerAnimated:NO completion:nil];
    [vc release];
}

Ich habe diesen Code in der Methode "willAnimateRotationToInterfaceOrientation" für die Ausrichtung im Querformat verwendet, und alles funktioniert ordnungsgemäß. Aber ich weiß nicht, ob es mit Animationen funktioniert.

8
Exception

Statusleiste ausblenden oder anzeigen, mit der auch die Ansicht in der Größe geändert wird 

-(void)statusBar:(BOOL)status {
UIViewController *rootViewController = self.view.window.rootViewController;
UIView *view = rootViewController.view;

// Hide/Unhide the status bar
[[UIApplication sharedApplication] setStatusBarHidden:status]; // BOOL : YES or NO

// statusBar frame
CGRect statusBarFrame = [UIApplication.sharedApplication statusBarFrame];
// Establish baseline frame
CGRect newViewFrame = self.view.window.bounds;

// Check statusBar frame is worth dodging
if (!CGRectEqualToRect(statusBarFrame, CGRectZero)) {
    UIInterfaceOrientation currentOrientation = rootViewController.interfaceOrientation;
    if (UIInterfaceOrientationIsPortrait(currentOrientation)) {
        // If portrait need to shrink height
        newViewFrame.size.height -= statusBarFrame.size.height;
        if (currentOrientation == UIInterfaceOrientationPortrait) {
            // If not upside-down move down Origin
            newViewFrame.Origin.y += statusBarFrame.size.height;
        }
    } else { // Is landscape 
        // portrait shrink width
        newViewFrame.size.width -= statusBarFrame.size.width;
        if (currentOrientation == UIInterfaceOrientationLandscapeLeft) {
            // If the status bar is on the left side of the window move Origin
            newViewFrame.Origin.x += statusBarFrame.size.width;
        }
    }
}
view.frame = newViewFrame; // pass new frame 
}

aufrufmethode (Nachricht):

 if ([[UIApplication sharedApplication] isStatusBarHidden]) {
        [self statusBar:NO];
 } else {
        [self statusBar:YES];
 }
7
Shams Ahmed

Ich kenne dafür einen Umweg, aber die Nachteile liegen auch auf der Hand. Sie können self.wantsFullScreenLayout = YES; in Ihre viewDidLoad setzen und Ihre Xib-Datei so groß wie der Bildschirm einstellen (320x480 und 320x568 für iPhone5). Dies bedeutet jedoch, dass der Bereich unter der Statusleiste ebenfalls nicht sichtbar ist. Auf diese Weise wird Ihre Ansicht auch nicht erweitert, wenn Sie die Statusleiste ausblenden. Sie können dies berücksichtigen, wenn Sie im Statusleistenbereich nichts anzeigen möchten.

0
sunkehappy

Der Einfachheit halber eine Swift 4-Variante der Antwort von @ awfulcode:

var statusBarHidden = false {
    didSet {
        UIView.animate(withDuration: 0.25) {
            self.setNeedsStatusBarAppearanceUpdate()
        }
    }
}

override var preferredStatusBarStyle: UIStatusBarStyle {
    return .default
}

override var preferredStatusBarUpdateAnimation: UIStatusBarAnimation {
    return .fade
}

override var prefersStatusBarHidden: Bool {
    return statusBarHidden
}
0
pinch

Nach stundenlangem Experimentieren und Antworten suchen; besonders diese Antwort . Mit ein bisschen Tweaking habe ich es erfolgreich geschafft, jetzt ist die obere Lücke 20px zwischen dem Übergang verschwunden!

Angenommen, wir haben ein BOOL isStatusBarEnabled ivar, das angibt, ob die Statusleiste ausgeblendet werden soll oder nicht (z. B. beim Zugriff auf NSUserDefault zur Überprüfung von boolValueForKey).

Wir prüfen also zuerst, ob die Statusleiste bereits verborgen ist oder nicht, über [[UIApplication sharedApplication] isStatusBarHidden], wenn sie nicht ausgeblendet ist (== wird angezeigt), verstecken wir sie! Sonst, tu es anders!

  • Um 20px zu korrigieren, wenn der Status angezeigt wird - aber die Navigation ist nicht richtig gedrückt, fügen Sie einfach 20 Punkte zu Origin.y von self.navgigationController.navigationBar.frame hinzu.

  • Gehen Sie genauso vor, wenn Sie die Statusleiste ausblenden möchten. Entfernen Sie einfach diesen 20 Punkt auf Origin.y von self.navgigationController.navigationBar.frame, und belassen Sie ihn einfach 0.

das ist es!

@implementation SomeViewController {
    BOOL isStatusBarEnabled;
}

// ...

- (void)toggleStatusBar
{
    UINavigationBar *navBar = self.navigationController.navigationBar;

    if ([[UIApplication sharedApplication] isStatusBarHidden]) {

        // Change to regular mode
        // Show status bar
        [[UIApplication sharedApplication] setStatusBarHidden:NO
                                                withAnimation:UIStatusBarAnimationSlide];
        [UIView animateWithDuration:0.3
                         animations:^{
                             navBar.frame = CGRectMake(navBar.frame.Origin.x, 20, navBar.frame.size.width, navBar.frame.size.height);
                         } completion:nil];

    } else if (![[UIApplication sharedApplication] isStatusBarHidden]) {
        // Change to fullscreen mode
        // Hide status bar
        [[UIApplication sharedApplication] setStatusBarHidden:YES
                                                withAnimation:UIStatusBarAnimationSlide];
        [UIView animateWithDuration:0.4
                         animations:^{
                             navBar.frame = CGRectMake(navBar.frame.Origin.x, 0, navBar.frame.size.width, navBar.frame.size.height);
                         } completion:nil];
    }

}

// ...

... dann habe ich in meinem Fall eine Einstellungstaste, mit der der Benutzer die Statusleiste ein-/ausblenden kann.

// ...

- (void)onDefaultsChanged:(NSNotification*)aNotification
{

    NSUserDefaults *standardDefaults = [NSUserDefaults standardUserDefaults];
    isStatusBarEnabled = [standardDefaults boolForKey:kStatusBar];

    if (isStatusBarEnabled) {

      if ([[UIApplication sharedApplication] isStatusBarHidden]) {

          // Change to regular mode
          // Show status bar
          [self toggleStatusBar];   

    } else {

        // Change to fullscreen mode
        // Hide status bar
        [self toggleStatusBar];

  }

  // ...
}

das ist es!

0
Vinh Nguyen