SetStatusBarHidden: НЕТ после загрузки XIB UINavigationBar

Когда setStatusBarHidden:NO установлено до, загружается представление, элементы UINavigationBar и другие элементы выравниваются непосредственно ниже StatusBar, как они должны. Однако, когда setStatusBarHidden:NO установлен после, просмотр загружается, часть UINavigationBar частично покрывается.

StatusBar должен быть обнаружен после загрузки указанного представления, но как это можно сделать, не сталкиваясь с вышеупомянутой проблемой?

Ответ 1

Я нашел ручку в моем коде, хотя не могу вспомнить или найти, откуда она взялась. Хитрость состоит в том, чтобы обновить панель навигации, скрыв и перепрошив ее:

[self.navigationController setNavigationBarHidden:YES animated:NO];
[self.navigationController setNavigationBarHidden:NO animated:NO];

В моем коде функция выглядит так:

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

    [[UIApplication sharedApplication] setStatusBarHidden:NO withAnimation:UIStatusBarAnimationNone];

    [self.navigationController setNavigationBarHidden:YES animated:NO];
    [self.navigationController setNavigationBarHidden:NO animated:NO];
}

Однако BE WARNED, это взломать, и в настоящее время я борюсь с некоторыми ошибками, которые, как представляется, происходят из этого кода (элемент навигации не соответствует содержимому навигации). Но так как это работало для меня в некоторых местах, я бы подумал, что я упоминаю об этом.

Edit: Думаю, я нашел здесь начальный пост: Как я могу заставить панель навигации в UINavigationController обновлять свою позицию, когда строка состояния скрыта?

GL, Одед

Ответ 2

(Я понимаю, что это был старый вопрос, но я просто потратил полчаса, пытаясь найти ответ сам без успеха, поэтому я решил разместить его здесь для всех, кто застрял... особенно если вы пытаетесь чтобы показать строку состояния, и ваше представление заканчивается перекрытием)

Я нашел, что это работает, если вы хотите СКРЫТЬ строку состояния...

[[UIApplication sharedApplication] setStatusBarHidden:YES];
[self.view setFrame: [[UIScreen mainScreen] bounds]];

но не тогда, когда вы хотите ПОКАЗАТЬ строку состояния... в этом случае я использую это решение, которое работает, но меня беспокоит, потому что он жестко кодирует высоту строки состояния до 20... это также беспокоит меня, что мне нужно настроить вид по-разному в зависимости от ориентации. но если бы я этого не делал, у него всегда был разрыв в 20 пунктов на неправильном крае. В моем случае я хочу отключить индикатор состояния для некоторых просмотров, а затем вернуться, когда вернусь. У меня возникли особые проблемы, если я повернул устройство, когда панель была выключена. поэтому оператор switch, хотя и некрасивый (кто-то может опубликовать более чистое решение), работает.

[[UIApplication sharedApplication] setStatusBarHidden:NO];

CGRect frame = [[UIScreen mainScreen] bounds];

switch (self.interfaceOrientation) 
{
    case UIInterfaceOrientationPortrait:
        frame.origin.y = 20;
        frame.size.height -= 20;
        break;

    case UIInterfaceOrientationPortraitUpsideDown:
        frame.origin.y = 0;
        frame.size.height -= 20;
        break;

    case UIInterfaceOrientationLandscapeLeft:
        frame.origin.x = 20;
        frame.size.width -= 20;
        break;

    case UIInterfaceOrientationLandscapeRight:
        frame.origin.x = 0;
        frame.size.width -= 20;
        break;

} 

[self.view setFrame:frame];

Ответ 3

Моя догадка заключается в том, что навигационная панель загружается до отображения строки состояния, поэтому позиция навигационной панели (0,0), которая затем перекрывается со строкой состояния (0,0). Вы можете просто переместить рамку навигационной панели (или настроить блок анимации) в viewDidLoad после вызова setStatusBarHidden:NO. Попробуйте сделать navigationBar.frame = CGRectMake(0,20,320,44); Строка состояния - 320x20, поэтому просто перемещать навигационную панель на 20, чтобы разместить ее.

Ответ 4

Если у вас возникла эта проблема, потому что вы не показываете строку состояния при загрузке Default.png, а затем хотите отобразить строку состояния сразу после просмотра вашего первого контроллера просмотра, просто убедитесь, что вы положили [[UIApplication sharedApplication] setStatusBarHidden:NO]; до [self.window makeKeyAndVisible]; в AppDelegate.m. Это происходит так быстро, вы никогда не увидите панель состояния на экране заставки.

[[UIApplication sharedApplication] setStatusBarHidden:NO];
[self.window makeKeyAndVisible];

Ответ 5

Вот что я делаю в своем корневом контроллере сейчас в iOS 5 после того, как я расскажу о строке состояния для анимации. Ужасно, но, похоже, это работает.

CGRect rect;

if ( self.interfaceOrientation == UIInterfaceOrientationPortrait )
    rect = CGRectMake(0, 20, 320, 460);
else if ( self.interfaceOrientation == UIInterfaceOrientationPortraitUpsideDown )
    rect = CGRectMake(0, 0, 320, 460);
else if ( self.interfaceOrientation == UIInterfaceOrientationLandscapeLeft )
    rect = CGRectMake(20, 0, 300, 480);
else
    rect = CGRectMake(0, 0, 300, 480);

[UIView animateWithDuration:0.35 animations:^{ self.view.frame = rect; }];

Ответ 6

в iOS 7 вы можете использовать:

setNeedsStatusBarAppearanceUpdate

например:

[self.mainViewController.navigationController setNeedsStatusBarAppearanceUpdate];

apple docs:

Вызвать этот метод, если атрибуты строки состояния контроллера, такие как как скрытый/незакрытый статус или стиль, измените. Если вы вызываете этот метод в блоке анимации изменения анимируются вместе с остальной части блока анимации.

использовать его только для iOS 7.