问题:
我有一个表视图,用户可以滚动查找内容或使用搜索栏。搜索栏不是使用StoryBoard创建的。我的视图有一个UISearchController
来处理搜索栏和搜索结果更新。我遇到的问题是,由于我的SearchResultsController
被另一个控制器实例化,我无法执行另一个视图,或者至少我无法找到解决方案。除了我的搜索结果控制器和它的目的地之间的segue之外,一切都有效。
我想做什么
让我MyNavTableViewController
代表MySearchResultsController
。在搜索结果控制器中,当用户点击TableViewCell
时,它将转到另一个视图。我没有使用StoryBoard来实现这一点我很难使用segue转换到另一个视图。
如果我无法实现这一目标,我可能会这样做:
在视图之间传递信息至关重要,对我而言,我总是使用segues完成它。但是,如果这不起作用,我可能会尝试通过将视图推送到导航控制器堆栈并将数据写入共享数据库或其他内容来模态地呈现视图。我宁愿使用segue。
研究: 肯定不止这些,但我不会在网址上占用太多空间。
Creating a segue programmatically
我的设置
我会尝试尽可能简洁。代码比我显示的代码多。我只是想尝试清理它,以便我只展示重要的东西。我也改变了一些名字,因为可能有敏感的信息。这可能不是什么大问题,但我宁愿安全。
class MyNavTableViewController: UIViewController, UITableViewDataSource{
//this is
@IBOutlet weak var tableView: UITableView!
var searchController: UISearchController!
override func viewDidLoad(){
...code
tableView.registerClass(UITableViewCell.self,forCellReuseIdentifier: tblId)
let resultsController = MySearchResultsController()
resultsController.databaseFilePath = databaseFilePath()
//this is essential that I use a segue because between my views I'm passing information between them.
resultsController.photo = photo!
searchController = UISearchController(searchResultsController: resultsController)
let searchBar = searchController.searchBar
searchBar.placeholder = searchBarPlaceHolderText
searchBar.sizeToFit()
tableView.tableHeaderView = searchBar
searchController.searchResultsUpdater = resultsController
}
}
MySearchResultsController: UITableViewController, UISearchResultsUpdating {
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath){
//self.performSegueWithIdentifier(imagePrepareStoryBoardId, sender: tableView.cellForRowAtIndexPath(indexPath))
/*let imagePrepare = ImagePrepareController()
customSegue = SearchResultSegue(identifier: imagePrepareId, source: self, destination: imagePrepare)*/
//neither storyboard nor navigationController can be nil.
let destVC = self.storyboard!.instantiateViewControllerWithIdentifier(imagePrepareStoryBoardId)
//destVC.photo = photo!
//self.presentViewController(destVC, animated: false, completion: nil)
self.navigationController!.pushViewController(destVC, animated: false)
}
}
我的失败尝试
1)直接上升 - 由于MySearchResultsController不是故事板中的视图,因此无法正常工作。我所读到的一切都是segues只能在SB中创建。
2)将视图推送到导航堆栈。唯一的问题是我无法在视图之间发送数据(或至少从我读过的内容)。我也在这个断点处得到了这个错误:
let destVC = self.storyboard!.instantiateViewControllerWithIdentifier(imagePrepareStoryBoardId)
fatal error: unexpectedly found nil while unwrapping an Optional value
我仔细检查了imagePrepareStoryBoardId。这是对的。
3)使用自定义segue - 正如您从注释掉的行中可以看到的那样,这也不起作用。我总是在SB上使用segues,所以这个方法对我来说有点新鲜。我可能会把它搞乱到某个地方。
答案 0 :(得分:8)
首先创建一个协议
protocol SelectedCellProtocol {
func didSelectedCell(text: String)
}
你的UITableViewClass上的声明它
class MySearchResultsController: UITableViewController, UISearchResultsUpdating {
var delegate:SelectedCellProtocol?
}
并在选定的单元格方法上调用它:
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath){
self.delegate?.didSelectedCell(cell.textLabel?.text)
}
当您声明结果控制器时,请设置委托
let resultsController = MySearchResultsController()
resultsController.databaseFilePath = databaseFilePath()
//this is essential that I use a segue because between my views I'm passing information between them.
resultsController.photo = photo!
resultsController.delegate = self
searchController = UISearchController(searchResultsController: resultsController)
let searchBar = searchController.searchBar
searchBar.placeholder = searchBarPlaceHolderText
searchBar.sizeToFit()
tableView.tableHeaderView = searchBar
searchController.searchResultsUpdater = resultsController
然后实施协议
class MyNavTableViewController: UIViewController, UITableViewDataSource, SelectedCellProtocol{
func didSelectedCell(text: String) {
print(text)
//make your custom segue
}
}