If I set the displaysSearchBarInNavigationBar = YES in viewDidLoad, the search bar will be in navigation bar when the view show up. But I want to s
I have just refactored Nick's answer to make it the POP way in Swift 4.
protocol SearchViewAnimateble : class{ }
extension SearchViewAnimateble where Self: UIViewController{
func showSearchBar(searchBar : UISearchBar) {
searchBar.alpha = 0
navigationItem.titleView = searchBar
navigationItem.setRightBarButton(nil, animated: true)
UIView.animate(withDuration: 0.5, animations: {
searchBar.alpha = 1
}, completion: { finished in
searchBar.becomeFirstResponder()
})
}
func hideSearchBar( searchBarButtonItem : UIBarButtonItem, titleView : UIView) {
navigationItem.setRightBarButton(searchBarButtonItem, animated: true)
titleView.alpha = 0
UIView.animate(withDuration: 0.3, animations: {
self.navigationItem.titleView = titleView
titleView.alpha = 1
}, completion: { finished in
})
}
}
Then you can use it like this
class ViewController : UIViewController, UISearchBarDelegate, SearchViewAnimateble {
var searchBar = UISearchBar()
var searchBarButtonItem: UIBarButtonItem?
var logoImageView : UIImageView!
override func viewDidLoad() {
super.viewDidLoad()
// Can replace logoImageView for titleLabel of navbar
let logoImage = UIImage(named: "logo-navbar")!
logoImageView = UIImageView(frame: CGRect(x: 0, y: 0, width: logoImage.size.width, height: logoImage.size.height))
logoImageView.image = logoImage
navigationItem.titleView = logoImageView
searchBar.delegate = self
searchBar.searchBarStyle = .minimal
searchBar.showsCancelButton = true
searchBarButtonItem = navigationItem.rightBarButtonItem
}
@IBAction func searchButtonPressed(sender: AnyObject) {
showSearchBar(searchBar: searchBar)
}
//MARK: UISearchBarDelegate
func searchBarCancelButtonClicked(searchBar: UISearchBar) {
hideSearchBar( searchBarButtonItem : searchBarButton!, titleView : logoImageView)
}
}