How to add a searchBar with scopebar inside of a N

2019-08-19 03:11发布

I read all questions on stackoverflow but none of them could solve my problem. I created a UICollectionView and and anchored a searchBar inside of the navigationBar without using Storyboards!

   class UserSearchController: UICollectionViewController ,.. {..
    lazy var  searchBar: UISearchBar = {
    let sb = UISearchBar()
    sb.placeholder = "Enter username"
    sb.barTintColor = UIColor.gray
    UITextField.appearance(whenContainedInInstancesOf: [UISearchBar.self]).backgroundColor = UIColor.rgb(red: 230, green: 230, blue: 230)
    sb.delegate = self
    sb.showsCancelButton = true
    return sb
}()  .... 

  // adding the searchBar to the collectionView as subView and      
    anchoring it  to the navigationBar

enter image description here

The searchbar is shown inside of the navigationBar and everything works fine. The problem occurs when I try to add a scopebar to my searchbar. I added the following properties to my searchbar

      sb.showsScopeBar = true
      sb.scopeButtonTitles = ["Username", "Hashtag"]

The scopeBar is hide behind the navigationBar and the navBar is not automatically increasing its height. You just see a gray background.

enter image description here

Adding my code to a simple UiViewController everything works fine

This code works inside a normal VIewController where the searchBar is added as subView and anchored to the view.

    lazy var  searchBar: UISearchBar = {

    let sb = UISearchBar()
    sb.placeholder = "Enter username"
    sb.barTintColor = UIColor.gray
    UITextField.appearance(whenContainedInInstancesOf: [UISearchBar.self]).backgroundColor = UIColor.rgb(red: 230, green: 230, blue: 230)
    sb.delegate = self
    sb.scopeButtonTitles = ["Username", "Hashtag"]
    sb.tintColor = UIColor.black
    sb.barTintColor = UIColor.lightGray


    return sb
}()

public func searchBarShouldBeginEditing(_ searchBar: UISearchBar) -> Bool {
    searchBar.showsScopeBar = true
    searchBar.sizeToFit()
    searchBar.setShowsCancelButton(true, animated: true)

    return true
}



func searchBarCancelButtonClicked(_ searchBar: UISearchBar) {
    searchBar.showsScopeBar = false
    searchBar.endEditing(true)
}

My searchBar looks like the following. If you start typing the scopeBar appears and if you click cancel it disappears. I want the same but only inside of the navBar :

enter image description here enter image description here

How is it possible to add a searchBar with scopeBar inside of the navigationBar without Storyboards. Isn't there any easy way. Please can you refer to my code and use my code to show me how this works. I also tried to increase the size of the navigationBar but it should work automatically and I don't know if this is the right approach.

1条回答
Bombasti
2楼-- · 2019-08-19 03:36

I think this is the sort of implementation you are looking for:

Your segment controller

// ( Declare Globaly )
var yourSegmentController = UISegmentedControl()
yourSegmentController.addTarget(self, action: #selector(ParentClass.filterChanged(_:)), for: .touchUpInside)

Then you will have to register your custom UICollectionViewCell classes with your UICollectionView. Do this in your viewDidLoad or whatever initializer method is used in the module you have the UICollectionView inside of:

self.yourCollectionView.register(YourCustomUserCellClassHere.self, forCellWithReuseIdentifier: NSStringFromClass(YourCustomUserCellClassHere))

self.yourCollectionView.register(YourCustomHashtagCellClassHere.self, forCellWithReuseIdentifier: NSStringFromClass(YourCustomHashtagCellClassHere))

Lastly, in your cellForItemAt delegate method, do the following to see which filter is selected and return the cells accordingly:

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {

    var cellToReturn = UICollectionViewCell()

    // USERS
    if yourSegmentController.selectedSegmentIndex == 0 {

        let customUserCell = self.yourCollectionView.dequeueReusableCell( withReuseIdentifier: NSStringFromClass(YourCustomUserCellClassHere), for: indexPath) as? YourCustomUserCellClassHere

        // Do what you want with your custom cell here...


        cellToReturn = customUserCell
    }
    // HASHTAGS
    else if yourSegmentController.selectedSegmentIndex == 1 {

        let customHashtagCell = self.yourCollectionView.dequeueReusableCell( withReuseIdentifier: NSStringFromClass(YourCustomHashtagCellClassHere), for: indexPath) as? YourCustomHashtagCellClassHere

        // Do what you want with your custom cell here...


        cellToReturn = customHashtagCell

    }

    return cellToReturn

}

This will check to see what filter is selected and then return the cell that suits the filter.

Also keep in mind every time the user changes your segment filter you will have to refresh the UICollectionView.

Refresh it like this:

// Put this method at the same level where your cellForItemAt function is but not inside

func filterChanged (_ sender:UISegmentedControl) {
    self.yourCollectionView.reloadData()
} 
查看更多
登录 后发表回答