现在不推荐使用旧的UISearchDisplayController类,而是必须使用新的UISearchController。曾经有一个名为“SearchResultsTableView”的旧类中的属性,但它已从新类中删除。
我使用数据填充表格,所有工作都按预期进行 - 包括将每行的详细信息转换为另一个场景。我在那里抛出一个搜索栏(以编程方式 - 使用新的searchController),它成功地重新加载原始表与任何找到的结果。 然而,当在搜索之后触摸选定的行时,传递的segue是原始表行的恰好位于与现在触摸的行相同的位置! (即如果我选择当前搜索的第二行,下一个场景将会删除原始表格第二行的详细信息!)这是因为尽管行中的数据正在成功地重新填充搜索数据,但索引编号仍然是那些旧数据。
它曾经是旧类型,我们会这样检查:
if (self.resultSearchController.active) {
let indexPath = self.searchDisplayController!.searchResultsTableView.indexPathForSelectedRow()
} else {
let indexPath = self.tableView.indexPathForSelectedRow()
所以我认为使用旧的UISearchDisplayController类实际上有一个新表,而使用新的SearchController类只能在旧表中获得新行?这完全没有意义!
以下是每个请求的完整代码:
import UIKit
import Foundation
class secondTableViewController: UITableViewController, UITableViewDelegate, UITableViewDataSource, UISearchResultsUpdating {
var filteredTableData = [String]()
var resultSearchController = UISearchController()
//these 2 are standard for the title and subtitle
var TableTitle:Array< String > = Array < String >()
var TableSub:Array< String > = Array < String >()
//the following are for my seque to next scene
var the_fname:Array< String > = Array < String >()
var the_basics:Array< String > = Array < String >()
var the_p_method:Array< String > = Array < String >()
var the_seats:Array< String > = Array < String >()
var the_notes:Array< String > = Array < String >()
var the_tableData:Array< String > = Array < String >()
override func viewDidLoad() {
tableView.delegate = self
tableView.dataSource = self
self.title = currentBus
super.viewDidLoad()
self.resultSearchController = ({
let controller = UISearchController(searchResultsController: nil)
controller.searchResultsUpdater = self
controller.dimsBackgroundDuringPresentation = false
controller.searchBar.sizeToFit()
self.tableView.tableHeaderView = controller.searchBar
return controller
})()
// Reload the table
self.tableView.reloadData()
var url = "http://the_path_to_my_json_file"
get_data_from_url(url)
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
// MARK: - Table view data source
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
// #warning Potentially incomplete method implementation.
// Return the number of sections.
return 1
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
// 2
if (self.resultSearchController.active) {
return self.filteredTableData.count
}
else {
return TableTitle.count
}
}
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = self.tableView.dequeueReusableCellWithIdentifier("secondtableCell", forIndexPath: indexPath) as! UITableViewCell
// Configure the cell...
if (self.resultSearchController.active) {
cell.textLabel?.text = filteredTableData[indexPath.row]
//cell.detailTextLabel?.text = TableSub[indexPath.row]
}else{
cell.textLabel?.text = TableTitle[indexPath.row]
cell.detailTextLabel?.text = TableSub[indexPath.row]
}
return cell
}
func get_data_from_url(url:String)
{
let httpMethod = "GET"
let timeout = 15
let url = NSURL(string: url)
let urlRequest = NSMutableURLRequest(URL: url!,
cachePolicy: .ReloadIgnoringLocalAndRemoteCacheData,
timeoutInterval: 15.0)
let queue = NSOperationQueue()
NSURLConnection.sendAsynchronousRequest(
urlRequest,
queue: queue,
completionHandler: {(response: NSURLResponse!,
data: NSData!,
error: NSError!) in
if data.length > 0 && error == nil{
let json = NSString(data: data, encoding: NSASCIIStringEncoding)
self.extract_json(json!)
}else if data.length == 0 && error == nil{
println("Nothing was downloaded")
} else if error != nil{
println("Error happened = \(error)")
}
}
)
}
func extract_json(data:NSString)
{
var parseError: NSError?
let jsonData:NSData = data.dataUsingEncoding(NSASCIIStringEncoding)!
let json: AnyObject? = NSJSONSerialization.JSONObjectWithData(jsonData, options: nil, error: &parseError)
if (parseError == nil)
{
if let my_pass_list = json as? NSArray
{
for (var i = 0; i < my_pass_list.count ; i++ )
{
if let each_pass = my_pass_list[i] as? NSDictionary
{
if let fname = each_pass["fname"] as? String
{
if let lname = each_pass["lname"] as? String
{
if let numofseats = each_pass["numofseats"] as? String
{
if let showed_up = each_pass["showed_up"] as? String
{
if let res_id = each_pass["resnum"] as? String
{
if let res_notes = each_pass["res_notes"] as? String
{
if let payment_description = each_pass["payment_description"] as? String
{
// the_tableData.append(fname)
the_fname.append(fname)
the_basics.append(fname + " " + lname)
the_p_method.append(payment_description)
the_seats.append(numofseats)
the_notes.append(res_notes)
TableTitle.append(fname + " " + lname)
TableSub.append("Seats Reserved: " + numofseats + ". Showed Up: " + showed_up + ". Notes:" + res_notes)
the_tableData = TableTitle
}
}
}
}
}
}
}
}
}
}
}
do_table_refresh();
}
func do_table_refresh()
{
dispatch_async(dispatch_get_main_queue(), {
self.tableView.reloadData()
return
})
}
// MARK: - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
// Get the new view controller using [segue destinationViewController].
var thirdScene = segue.destinationViewController as! customer_details_View_Controller
if let indexPath = self.tableView.indexPathForSelectedRow() {
/*
so what I'm missing is to be able to check
if (self.resultSearchController.active) {
and if yes have indexPath be the self.resultSearchController.resultSearchTableView.indexPathForSelectedRow() {
or something of that nature
*/
thirdScene.dotrav = todayString
thirdScene.from = currentBus
thirdScene.basics = the_basics[indexPath.row]
thirdScene.p_method = the_basics[indexPath.row]
thirdScene.seats = the_tableData[indexPath.row]
thirdScene.notes = the_notes[indexPath.row]
}
// Pass the selected object to the new view controller.
}
func updateSearchResultsForSearchController(searchController: UISearchController)
{
filteredTableData.removeAll(keepCapacity: false)
let searchPredicate = NSPredicate(format: "SELF CONTAINS[c] %@", searchController.searchBar.text)
let array = (the_tableData as NSArray).filteredArrayUsingPredicate(searchPredicate)
filteredTableData = array as! [String]
self.tableView.reloadData()
}
}
答案 0 :(得分:0)
您需要根据搜索结果说明您将在tableView中拥有不同的数据。您仍然可以使用self.tableView.indexPathForSelectedRow
。
我所做的是保留对我的基础数据的引用,然后保留对我的过滤数据的引用,并始终在tableView
中显示我的过滤数据。如果我的searchBar没有文本,那么我的过滤数据就等于我的基础数据。
示例:
class MyTableViewController: UITableViewController, UISearchResultsUpdating {
var data: [String] = ["One", "Two", "Three", "Four", "Five"]
var filteredData: [String]!
var searchController: UISearchController!
override func viewDidLoad() {
super.viewDidLoad()
setUpSearchController()
setFilteredDataForCurrentSearch()
}
private func setUpSearchController() {
searchController = UISearchController(searchResultsController: nil)
searchController.searchResultsUpdater = self
self.tableView.tableHeaderView = searchController.searchBar
}
private func setFilteredDataForCurrentSearch() {
if let searchString = searchController.searchBar.text where !searchString.isEmpty {
filteredData = data.filter({ (string: String) -> Bool in
return searchString.rangeOfString(string, options: NSStringCompareOptions.CaseInsensitiveSearch) != nil
})
} else {
filteredData = data
}
}
func updateSearchResultsForSearchController(searchController: UISearchController) {
setFilteredDataForCurrentSearch()
}
}
现在,您可以使用UITableViewDataSource
实现所有UITableViewDelegate
和filteredData
方法。
在prepareForSegue
中,您可以检索正确的选定对象,如:
let indexPath = tableView.indexPathForSelectedRow()
let selectedObject = filteredData[indexPath.row]