2015-07-17 6 views
11

Я следовал этому blog post, в котором объясняется, как вы можете реализовать пользовательский UINavigationBar с повышенной высотой, если, например, вы хотели поместить дополнительные элементы ui в панель навигации под остальной частью бара содержимое, которое будет сохраняться между навигацией в стеке. Этот код работает очень хорошо в случае, когда вы всегда хотите, чтобы это была увеличенная высота.Динамически увеличивать/уменьшать высоту пользовательского UINavigationBar

В моем приложении мне нужно запустить панель навигации по умолчанию, а затем увеличить ее позже, добавив больше контента после того, как пользователь выполнит задание. Очень похоже на информацию песни и управления в Itunes магазине:

enter image description here

Так что я положил некоторые проверки на месте, чтобы ничего не изменить, если BOOLNO свойство. Когда я установил его на YES, я вызываю [self setNeedsDisplay], который будет вызывать layoutSubviews, чтобы разместить все правильно на основе этого логического значения. sizeThatFits также называется, и я возвращаю правильную высоту.

Проблема в том, что я не могу позвонить [self setTransform:CGAffineTransformMakeTranslation(0, -(NavigationBarHeightIncrease))]; в initialize. Вместо этого я называю это, в то же время меняю логическое значение на YES. Из-за этого все мои элементы перемещаются вверх по этой сумме. Но если я не звоню setTransform, элементы в навигационной панели находятся в правильном положении, но сама панель расположена слишком далеко вниз, так что пользовательский вид, который я добавил в панель, показан выше, чем вид контроллера представления - он истекает кровью, и дополнительное пространство, которое я добавил, является черным цветом фона панели навигации.

Если я вызываю setTransform в initialize, когда высота является высотой по умолчанию, элементы перемещаются вверх, когда их не должно быть.

Итак, как я могу правильно динамически изменять высоту и позиционирование подкласса UINavigationBar?

+1

Я бы не рекомендовал менять высоту UINavigationBar или ее реализацию вообще, вы никогда не знаете, что будет изменено в UINavigationBar после следующей версии iOS, Вместо этого я бы использовал пользовательский UIView с тем же фоном/стилем и приложением это в верхнем руководстве по макету, тогда вы можете легко манипулировать своими представлениями без private-apis – ogres

+0

@ogres. К сожалению, мне нужно, чтобы это пользовательское представление сохранялось между нажатиями и поп-операциями, поэтому я не могу добавить его в представление контроллера представления - ему нужно как-то привязаны к навигационному контроллеру/панели. – Joey

+0

Почему бы не создать один контроллер RootView, а затем включить в него навигационный контроллер? то вы можете поддерживать просмотры – ogres

ответ

1

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

embedded navigation controller example

+0

Я установил делегат навигационного контроллера через 'prepareForSegue' для 'self'. Я избавился от верхней панели навигационного контроллера. Но теперь, как я могу получить элементы из навигационной панели навигатора теперь скрытого навигатора в мою настраиваемую панель навигации? Только установление делегата не помогло. – Joey

+0

Вам нужно будет управлять заголовками вручную. Используя существующие данные в панели навигации, такие как 'navigationController.navigationBar.topItem.title', чтобы получить текущий заголовок, вы можете установить элементы пользовательского интерфейса в своем пользовательском навигационном представлении.Отвечает ли это на ваш вопрос? –

+0

Я могу заставить это работать, устанавливая элементы и заголовок кнопки влево/вправо в 'navigationController: willShowViewController:', но жест жестка не работает, а кнопка возврата не отображается на настраиваемой панели навигации. Кроме того, поскольку панель навигации начинается с верхнего руководства по макете, она не попадает под строку состояния, поэтому под строкой состояния есть только белый. – Joey

0

Опцион является создание UIViewController в раскадровке, который имеет только вид управления, который вы хотите показать ниже панели навигации со всем остальным прозрачным. Преимущество здесь заключается в том, что вы разрабатываете это, используя обычные инструменты. Используйте ограничения, чтобы поместить его чуть ниже навигационной панели и установить высоты, ширину и т. Д. Ваших представлений.

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

Есть два варианта для вставки извлеченного вида базы:

  1. Если добавить этот вид управления для контроллера представления в верхней части в стек навигации (что на экране), было бы когда вы нажимаете на новый контроллер. Это не то, что вы сказали, что хотите.

  2. Если вы добавите этот элемент управления в self.navigationController.view, то он будет сохраняться через нажатия и всплывающие окна. Это то, что ты сказал, что хочешь.

Я использую этот подход, чтобы предоставить всплывающие подсказки для описания того, что на экране. В зависимости от того, использую ли я вариант 1 или 2, я могу сохранить помощь в нескольких нажатиях/попках.

Я получил эту идею из этого учебника, который описывает общий подход: http://blog.typpz.com/2013/12/09/ios-sdk-create-a-pop-up-window/

Эта ссылка предоставляет полный пример кода о том, как открыть представление и удалить представление.

Это позволит вам создать его в IB, представить и отбросить его по мере необходимости и сохранить его в навигационных последовательностях.

Надеюсь, это поможет.

+0

Интересный подход. Единственная проблема, с которой я вижу, заключается в том, что она будет скрывать основные взгляды. Мне нужен контроллер (ы) просмотра, чтобы изменить их вставки содержимого, или весь вид перемещен вниз, так что новый вид не скроет их содержимое. – Joey

+0

@Joey Опция состоит в том, чтобы создать ваши таблицы как UIViewController, содержащие UITableView, а не с помощью UITableViewController. Затем вы можете привязать вершину UITableView к верхнему руководству по макету с ограничением и смещением. Когда вы хотите наложить наложение, измените ограничение в коде. Поскольку у вас есть ограничение для оверлея и таблицы, вы можете анимировать оба. Ввод оверлей за панель навигации (добавление оверлей в передний, а не в конец отображения содержимого контроллера навигации), вы увидите, что оверлейное слайд вниз из-под бар и стол скользят вместе. –

+0

@Joey Или даже проще добавить пустой столбец в верхней части таблицы, который имеет ту же высоту, что и наложение и перезагрузка 8 ^). –

Смежные вопросы