Отрегулируйте положение элемента кнопки панели при использовании больших заголовков с iOS 11

Я использую большой заголовок navbar с iOS 11, но когда я добавляю элемент кнопки панели, он выглядит странно расположенным в том же месте, что и исходный навигационный заголовок. Я хотел бы переместить элемент кнопки панели вниз, когда заголовок большой, и переместить его обратно в исходное положение, когда навигационная панель уже не большая. Каким будет лучший способ сделать это?

Это изображение, показывающее странное положение элемента кнопки панели

largeTitleNavbar

Я могу получить высоту навигатора динамически с помощью viewWillLayoutSubviews(), но я не могу изменить положение элемента кнопки панели с помощью setTitlePositionAdjustment

override func viewWillLayoutSubviews() {
    guard let navbarHeight = self.navigationController?.navigationBar.frame.height else{ return }
}

Ответ 1

Чтобы решить мою собственную проблему, я просто добавил кнопку в качестве подсмотра навигационной панели и установил права и нижние ограничения на навигационную панель. Теперь кнопка перемещается вверх и вниз, когда навигационная панель меняет размер. Однако для этого требуется, чтобы кнопка была удалена в любых контроллерах представлений, которые вы показываете segue с этого контроллера представления. Таким образом, я добавил тег 1 к кнопке и удалил его из своего супервизора с другого контроллера представления. Это самый простой способ его решения, и я нашел его самым легким методом.

Чтобы настроить правую кнопку:

func setupNavBar() {

    self.title = "Home"
    self.navigationController?.navigationBar.prefersLargeTitles = true
    self.navigationController?.navigationBar.isTranslucent = false

    let searchController = UISearchController(searchResultsController: nil)
    self.navigationItem.searchController = searchController

    let rightButton = UIButton()
    rightButton.setTitle("Right Button", for: .normal)
    rightButton.setTitleColor(.purple, for: .normal)
    rightButton.addTarget(self, action: #selector(rightButtonTapped(_:)), for: .touchUpInside)
    navigationController?.navigationBar.addSubview(rightButton)
    rightButton.tag = 1
    rightButton.frame = CGRect(x: self.view.frame.width, y: 0, width: 120, height: 20)

    let targetView = self.navigationController?.navigationBar

    let trailingContraint = NSLayoutConstraint(item: rightButton, attribute:
        .trailingMargin, relatedBy: .equal, toItem: targetView,
                         attribute: .trailingMargin, multiplier: 1.0, constant: -16)
    let bottomConstraint = NSLayoutConstraint(item: rightButton, attribute: .bottom, relatedBy: .equal,
                                    toItem: targetView, attribute: .bottom, multiplier: 1.0, constant: -6)
    rightButton.translatesAutoresizingMaskIntoConstraints = false
    NSLayoutConstraint.activate([trailingContraint, bottomConstraint])

}

Чтобы удалить его из любых отображаемых контроллеров просмотра:

func removeRightButton(){
    guard let subviews = self.navigationController?.navigationBar.subviews else{return}
    for view in subviews{
        if view.tag != 0{
            view.removeFromSuperview()
        }
    }
} 

Обе функции вызываются в функции viewWillAppear

Ответ 2

Что вы хотите сделать, это установить настройки позиции заголовка BarButtonItem. Добавьте в строку viewWillAppear следующую строку. Играйте с параметрами vertical и horizontal, чтобы получить layout ур..

navigationItem.rightBarButtonItem?.setTitlePositionAdjustment(.init(horizontal: 10, vertical: 20), for: UIBarMetrics.default)

https://developer.apple.com/documentation/uikit/uibarbuttonitem/1617149-settitlepositionadjustment

Ответ 3

Хороший способ - вы можете настроить заголовок навигации, если его большой, чтобы ваша панель кнопка автоматически настроится. Вот код. Также iOS-почта приложение делает то же самое для вашей справки.

func adjustsTitle() {
 guard let font = UIFont(name: "Helvetica-Medium", size: 16) else { return }
 let label = UILabel(frame: CGRect(x: 0, y: 0, width: 100, height: 20))
 label.textColor = UIColor.black
 label.textAlignment = .center
 label.text = navigationItem.title
 label.adjustsFontSizeToFitWidth = true
 navigationItem.titleView = label
}

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

//Hide back button. Since you are going to have custom button
navigationItem.hidesBackButton = true
//Increase the height based on your view intrinsic content size
navigationController?.navigationBar.frame.size.height = 100
guard let yourCustomView = UINib(nibName: "yourCustomXib", bundle: nil).instantiate(withOwner: nil, options: nil).first as? YourCustomView else {
 fatalError("Missing yourCustomXib")
}
navigationController?.navigationBar.addSubview(yourCustomView)