Reputation: 131
Im new to the swift, I am trying to filter name from an array using the search bar in console am getting what I entered in the search bar but filtering with predicate im not getting filtered name...please can anyone help in this issue
var caseListOfBooker:[CaseDetails]=[]
var searchString:String=""
var filteredString = [String]()
func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) {
print("searchText \(searchText)")
searchString = searchText
updateSearchResults()
tableview.reloadData()
}
func updateSearchResults(){
filteredString.removeAll(keepingCapacity: false)
let searchPredicate = NSPredicate(format: "SELF CONTAINS[c] %@", searchString)
let array = self.caseListOfBooker.filter{$0.person_of_interest.contains(searchString)}
print(array)
if let list=array as? [String]{
filteredString=list
}
print(filteredString)
tableview.reloadData()
}
extension SearchPOIVC : UITableViewDelegate, UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
if filteredString != []{
return filteredString.count
}
else
{
if searchString != "[]" {
return caseListOfBooker.count
}else {
return 0
}
}
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 80.00
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell:POIProfileDetailsCell = tableview.dequeueReusableCell(withIdentifier: "POIProfileDetailsCell", for: indexPath) as! POIProfileDetailsCell
if filteredString != []{
cell.poiName.text = filteredString[indexPath.row]
return cell
}else{
if searchString != "[]"{
cell.poiName.text = self.caseListOfBooker[indexPath.row].person_of_interest
}
return cell
}
}
Upvotes: 3
Views: 829
Reputation: 545
var searchPredicate = NSPredicate()
searchPredicate = NSPredicate(format: "self CONTAINS[C] %@", your_searching_text)
let Final_Search_array = (Your_Array).filtered(using: searchPredicate)
Upvotes: 0
Reputation: 285069
The most efficient way to filter custom classes is to use the same type for the data source array and the filtered array
var caseListOfBooker = [CaseDetails]()
var filteredBooker = [CaseDetails]()
Add a property isFiltering
which is set to true when the search text is not empty
var isFiltering = false
and delete searchString
and filteredString
var searchString:String=""
var filteredString = [String]()
In updateSearchResults
filter the data source array (with native Swift functions), set isFiltering
accordingly and reload the table view
func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) {
print("searchText \(searchText)")
updateSearchResults(searchText: searchText)
}
func updateSearchResults(searchText: String) {
if searchText.isEmpty {
filteredBooker.removeAll()
isFiltering = false
} else {
filteredBooker = caseListOfBooker.filter{$0.person_of_interest.range(of: searchText, options: .caseInsensitive) != nil }
isFiltering = true
}
tableview.reloadData()
}
In the table view data source methods display the data depending on isFiltering
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return isFiltering ? filteredBooker.count : caseListOfBooker.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableview.dequeueReusableCell(withIdentifier: "POIProfileDetailsCell", for: indexPath) as! POIProfileDetailsCell
let booker = isFiltering ? filteredBooker[indexPath.row] : caseListOfBooker[indexPath.row]
cell.poiName.text = booker.person_of_interest
}
Upvotes: 3
Reputation: 15748
let array = self.caseListOfBooker.filter{$0.person_of_interest.contains(searchString)}
You are getting array of CaseDetails
objects and trying to cast to array of String
It fails. You need to get string values from the CaseDetails
object and join them
Use
filteredString = array.map { $0.person_of_interest }
Or
for caseDetail in array {
filteredString.append(caseDetail.person_of_interest)
}
Instead of
if let list = array as? [String]{
filteredString=list
}
Upvotes: 1