Search code examples
iosswiftuinavigationcontrolleruinavigationbar

Navigation controller with searchBar jump


I have a navigation controller in my main View where it includes a searchBar. Then when it goes to second View (without searchBar) there is a little jump on the screen, and same thing happens when I go back to first View.

Here is my Navigation controller code for first viewController:

func configureNavBar() {
    navigationController?.navigationBar.isTranslucent = false
    navigationController?.navigationBar.barTintColor = .mainPink()
    navigationController?.navigationBar.barStyle = .black

    searchBar = UISearchBar()
    searchBar.delegate = self
    searchBar.tintColor = .white
    navigationItem.titleView = searchBar
    searchBar.showsCancelButton = true
}

Second:

navigationController?.navigationBar.isTranslucent = false
navigationController?.navigationBar.barTintColor = .mainPink()
navigationController?.navigationBar.barStyle = .black

Is there any way to eliminate this 'jump' ?


Solution

  • This question actually contains two different issues:

    1- In case of "Large Navigation Bar" suddenly collapsed when navigating to another View Controller:

    The TableView scrolling is the main reason, Try the following:

    self.tableView.contentInsetAdjustmentBehavior = .never
    

    You can set it from "Size Inspector" in storyboard also.

    It adjusts its scroll position corresponding to the SafeArea.


    2- The case of "Default Navigation Bar" that contains SearchBar in its Navigation Item's title view:

    The main reason is that the search bar is added with height "56" by default

    • Regarding a black line that appears under the navigation bar of the pushed view controller, So you can fix it with the following:

      // Inside ViewDidLoad of the Pushed View Controller
      
      self.extendedLayoutIncludesOpaqueBars = true
      

    OR

    override func viewWillDisappear(_ animated: Bool) {
        super.viewWillDisappear(animated)
        navigationController?.view.setNeedsLayout() 
        navigationController?.view.layoutIfNeeded()
     }
    
    • For preventing the NavigationBar to be extended at all when putting the SearchBar like this:

    You need to create a custom view with a fixed height frame and add this search bar inside it, check the following:

    class SearchBarViewHolder: UIView {

    let searchBar: UISearchBar  
    
    init(customSearchBar: UISearchBar) {  
        searchBar = customSearchBar  
        super.init(frame: CGRect.zero)  
    
        addSubview(searchBar)  
    }
    
    override convenience init(frame: CGRect) {  
        self.init(customSearchBar: UISearchBar())  
        self.frame = frame  
    }  
    
    required init?(coder aDecoder: NSCoder) {  
        fatalError("init(coder:) has not been implemented")  
    }  
    
    override func layoutSubviews() {  
        super.layoutSubviews()  
        searchBar.frame = bounds  
    }  
    }
    

    // Adding Search bar

    let searchBarViewHolder = SearchBarViewHolder(customSearchBar: searchBar)  
    searchBarViewHolder.frame = CGRect(x: 0, y: 0, width: view.frame.width, height: 44)  
    navigationItem.titleView = searchBarViewHolder