Показывать панель поиска на панели навигации без прокрутки на iOS 11

80

Я прикрепляю UISearchController к navigationItem.searchControllerсвойству UITableViewController в iOS 11. Это отлично работает: я могу использовать красивую панель поиска в стиле iOS 11.

Однако я бы хотел, чтобы панель поиска была видна при запуске. По умолчанию пользователь должен прокрутить таблицу вверх, чтобы увидеть панель поиска. Кто-нибудь знает, как такое возможно?

введите описание изображения здесь введите описание изображения здесь

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

Я уже обнаружил, что панель поиска можно сделать видимой, установив для свойства hidesSearchBarWhenScrollingмоего элемента навигации значение false. Однако это приводит к тому, что панель поиска всегда видна - даже при прокрутке вниз - а это не то, что мне нужно.

Джонатан
источник
где вы добавили кодhidesSearchBarWhenScrolling
Anbu.Karthik
1
как насчет того, чтобы установить его как s firstResponder?
Милан Носань
2
Выбранный ниже ответ работает для меня при загрузке, но я также хотел бы повторно отобразить контроллер поиска при программной прокрутке вверх с помощью scrollView.setContentOffset(_:animated). У кого-нибудь есть предложение?
Джастин Валлели
@Jonathan hidesSearchBarWhenScrolling = falseпомещает строку поиска над большим заголовком в iOS 13. Есть идеи, могу ли я как-нибудь обновить это?
Bonnke

Ответы:

187

Следующее делает панель поиска сначала видимой, а затем позволяет ей скрыться при прокрутке:

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    if #available(iOS 11.0, *) {
        navigationItem.hidesSearchBarWhenScrolling = false
    }
}

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    if #available(iOS 11.0, *) {
        navigationItem.hidesSearchBarWhenScrolling = true
    }
}

Использование isActiveне сделало того, что я хотел, оно делает панель поиска активной (показывает кнопку отмены и т. Д.), Когда все, что мне нужно, это чтобы она была видна.

Джордан Вуд
источник
Спасибо, у меня сработало. Интересное решение :)
Mikrasya
9
Это решение работает, но есть побочные эффекты, если вы также отображаете панель навигации, если она была ранее скрыта (например, при нажатии этого представления с панелью поиска в стек навигации). Панель поиска будет отображаться статично на месте во время анимации панели навигации. Выглядит ужасно :(
Мэтью Креншоу
12
Нет, если вы поставите первую часть viewDidLoadвместоviewWillAppear
Марк-Александр Берубе
1
Может кто-нибудь уточнить, почему это работает и почему searchController.searchBar.isHidden = falseво viewDidLoad нет? Последнее кажется мне гораздо более логичным
pho_pho
5
Это вызывает визуальную ошибку в iOS 13 при возврате с дочернего экрана.
nemissm
5

Вы можете установить для свойства isActiveзначение trueпосле добавления searchController в navigationItem.

Именно так:

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    searchController.isActive = true
}
txaidw
источник
Нет метода установки setIsActive:
Николай Краснов
Ты прав, @NikolayKrasnov. isActiveявляется логическим только для чтения. searchController.active = trueВместо этого вы захотите использовать .
Марк Йешке
2

Для меня это сработало после добавления следующих строк в viewDidLoad()метод:

navigationController?.navigationBar.prefersLargeTitles = true
navigationController!.navigationBar.sizeToFit()
Рохит
источник
0

На iOS 13 ответ @Jordan Wood не сработал. Вместо этого я сделал:

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    UIView.performWithoutAnimation {
        searchController.isActive = true
        searchController.isActive = false
    }
}
GaétanZ
источник