I want to remove the text from the back button, but I want to keep the icon. I have tried
let backButton = UIBarButtonItem(title: \"\", style: UIBarButtonIt
The method of @rmd2 is almost right, but instead you should select the navigation bar of the controller to which back button will point to and type " "
in the Back Button field.
1. Create custom class of the UINavigationController
import UIKit
class NavigationController: UINavigationController {
override func viewDidLoad() {
super.viewDidLoad()
delegate = self
}
}
extension NavigationController: UINavigationControllerDelegate {
func navigationController(_ navigationController: UINavigationController, willShow viewController: UIViewController, animated: Bool) {
if viewController.navigationItemBackButtonTextIsHidden {
viewController.navigationItem.backBarButtonItem = UIBarButtonItem(title: "", style: .plain, target: nil, action: nil)
}
}
}
2. Add UIViewController extension
import UIKit
extension UIViewController {
@objc var navigationItemBackButtonTextIsHidden: Bool { return false }
}
3. Update your ViewController class
import UIKit
class ViewController: UIViewController {
override var navigationItemBackButtonTextIsHidden: Bool { return true }
}
import UIKit
// MARK: - ViewController
class ViewController: UIViewController {
var screenCounter = 1
override func viewDidLoad() {
super.viewDidLoad()
setupNavigationItem()
}
override var navigationItemBackButtonTextIsHidden: Bool { return (screenCounter % 2) == 0 }
}
extension ViewController {
private func setupNavigationItem() {
navigationItem.title = "VC \(screenCounter)"
navigationItem.rightBarButtonItem = UIBarButtonItem(title: "push", style: .plain, target: self, action: #selector(pushBarButtonTouchedUpInside))
}
@objc func pushBarButtonTouchedUpInside(button: UIBarButtonItem) {
guard let navigationController = navigationController else { return }
let viewController = ViewController()
viewController.screenCounter = screenCounter + 1
viewController.view.backgroundColor = .white
navigationController.pushViewController(viewController, animated: true)
}
}
// MARK: - NavigationController
class NavigationController: UINavigationController {
override func viewDidLoad() {
super.viewDidLoad()
delegate = self
}
}
extension NavigationController: UINavigationControllerDelegate {
func navigationController(_ navigationController: UINavigationController, willShow viewController: UIViewController, animated: Bool) {
if viewController.navigationItemBackButtonTextIsHidden {
viewController.navigationItem.backBarButtonItem = UIBarButtonItem(title: "", style: .plain, target: nil, action: nil)
}
}
}
// MARK: - UIViewController extension
extension UIViewController {
@objc var navigationItemBackButtonTextIsHidden: Bool { return false }
}
For me this did the trick:
override func viewWillDisappear(_ animated: Bool) {
super.viewWillDisappear(true)
self.navigationItem.title = " "
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
self.navigationItem.title = "my amazing title"
navigationItem.backBarButtonItem = UIBarButtonItem(title: " ", style: .plain, target: nil, action: nil)
}
Notice that if you only set the title without modifying the backBarButtonItem it will appear to work. But if you try to go back using a gesture and than cancel and stay on the pushed view controller, the back title will come back.
Working in Swift 4
After Searching a lot I found best and simple solution, this will affect all the viewControllers written in Swift 4.2 and also working in Swift 5
extension UIViewController {
open override func awakeFromNib() {
navigationItem.backBarButtonItem = UIBarButtonItem(title: "", style: .plain, target: nil, action: nil)
}
}
I solved this problem by adding a " " on the StoryBoard Title of the previous ViewController. Just a space, not empty ;D
I've tried a couple of answers and I can't get them to work in all cases. So this is a workaround to not affect the title of the navigation bar if it's set.
guard let items = viewController.navigationController?.navigationBar.items else { return }
for item in items {
if item.title == nil {
item.title = ""
}
}