使用SearchController搜索时使用标签栏获取黑屏 [英] Getting black screen on using tab bar while searching using SearchController

查看:116
本文介绍了使用SearchController搜索时使用标签栏获取黑屏的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个应用程序,其中一个标签栏控制器嵌入在导航控制器中。该应用程序有2个选项卡,第一个(搜索)有一个使用UISearchController实现的搜索栏。如果我在搜索时从这个标签切换到另一个标签(下载),则会发生另外两个标签 -




  • 第二个标签中的导航栏(下载)消失

  • 当我回到第一个标签(搜索)时,它显示黑屏





我已经使用故事板完成了所有这些工作。



这是我的SearchViewController

  import UIKit 
import Alamofire
import SwiftyJSON

class ViewController:UIViewController,UITableViewDelegate,UITableViewDataSource,UISearchResultsUpdating,UISearchBarDelegate {

// MARK:变量
var papers = [Paper ]()
var filteredPapers = [Paper]()
let searchController = UISearchController(searchResultsController:nil)

// MARK:Outlets
@IBOutlet weak var activityIndi​​cator :UIActivityIndi​​catorView!
@IBOutlet var table:UITableView!
@IBOutlet weak var loadingMessageLabel:UILabel!
@IBOutlet weak var retryButton:UIButton!

// MARK:行动
@IBAction func retryButton(发件人:UIButton){
self.loadingMessageLabel.hidden = false
self.loadingMessageLabel.text =while卫星移动到位...
self.activityIndi​​cator.hidden = false
self.activityIndi​​cator.startAnimating()
self.retryButton.hidden = true
self.getPapersData( )

}

// MARK:表格视图

func tableView(tableView:UITableView,numberOfRowsInSection section:Int) - > Int {
//如果在搜索模式下,则返回结果数,否则返回总数
//如果searchController.active&& searchController.searchBar.text!={
if searchController.active {
return filteredPapers.count
}
return papers.count
}

func tableView(tableView:UITableView,cellForRowAtIndexPath indexPath:NSIndexPath) - > UITableViewCell {

let paper:Paper

//如果searchController.active&& searchController.searchBar.text!={
if searchController.active {
paper = filteredPapers [indexPath.row]
} else {
paper = papers [indexPath.row]
}

如果让cell = self.table.dequeueReusableCellWithIdentifier(Cell)为? PapersTableCell {

cell.initCell(paper.name,detail:paper.detail)
print(cell)
return cell
}

return PapersTableCell()

}

func tableView(tableView:UITableView,didSelectRowAtIndexPath indexPath:NSIndexPath){
}

func tableView (tableView:UITableView,editActionsForRowAtIndexPath indexPath:NSIndexPath) - > [UITableViewRowAction]? {


let downloadButton = UITableViewRowAction(style:.Normal,title:Download){action,index in

var url = String(self.papers [indexPath.row] .url)
url = url.stringByReplacingOccurrencesOfString(,withString:%20)
print(url)
let destination = Alamofire.Request.suggestedDownloadDestination(directory :.DocumentDirectory,domain:.UserDomainMask)

//单元格中的微调器

// var selectCell = self.table.cellForRowAtIndexPath(indexPath)as? PapersTableCell
// selectCell!.downloadSpinner.hidden = false

//关闭下载按钮
self.table.editing = false

Alamofire。下载(.GET,url,目的地:目的地).response {_,_,_,错误在
如果让错误=错误{
print(失败错误:\(错误))
} else {
print(已成功下载文件)
}
// selectCell?.downloadSpinner.hidden = true
}

}

downloadButton.backgroundColor = UIColor(红色:0.30,绿色:0.85,蓝色:0.39,alpha:1.0)


返回[downloadButton]

}

func tableView(tableView:UITableView,canEditRowAtIndexPath indexPath:NSIndexPath) - > Bool {
//你希望动作显示的单元格需要编辑
返回true
}

func tableView(tableView:UITableView,commitEditingStyle editingStyle: UITableViewCellEditingStyle,forRowAtIndexPath indexPath:NSIndexPath){
//你也需要实现这个方法,否则你不能滑动显示动作
}

// MARK:搜索

func filterContentForSearchText(searchText:String,scope:String =All){
filteredPapers = papers.filter {paper in
let categoryMatch =(scope ==All) || (paper.exam == scope)
返回categoryMatch&& paper.name.lowercaseString.containsString(searchText.lowercaseString)
}

table.reloadData()
}

func updateSearchResultsForSearchController(searchController:UISearchController) {
让searchBar = searchController.searchBar
让scope = searchBar.scopeButtonTitles![searchBar.selectedScopeButtonIndex]
filterContentForSearchText(searchController.searchBar.text!,scope:scope)

}

func searchBar(searchBar:UISearchBar,selectedScopeButtonIndexDidChange selectedScope:Int){
filterContentForSearchText(searchBar.text !, scope:searchBar.scopeButtonTitles![selectedScope])
}

// MARK:默认值

覆盖func viewDidLoad(){
super.viewDidLoad()

self.getPapersData()

searchController.searchResultsUpdater = self
searchController.dimsBackgroundDuringPresentation = false
definesPresentationContext = true
table.tableHeaderView = searchController.searchBar
searchController.searchBar.scopeButtonTitles = [All,ST1,ST2,PUT,UT]
searchController.searchBar.delegate = self
activityIndi​​cator.startAnimating()


}

覆盖func viewWillDisappear(动画:Bool){
//如果searchController.active {
self.searchController.resignFirstResponder()
//}
}





覆盖func didReceiveMemoryWarning(){
super.didReceiveMemoryWarning()
//处置可以重新创建的任何资源。
}

// MARK:API调用

func getPapersData(){
Alamofire.request(.GET,http:// silive。在/ bytepad / rest / api / paper / getallpapers?query =)
.responseJSON {

self.activityIndi​​cator.stopAnimating()
self.activityIndi​​cator.hidden = true

//如果网络工作正常
如果response.result.isFailure!= true {

self.loadingMessageLabel.hidden = true
self .table.hidden = false
//print(response.result)//响应序列化的结果

让json = JSON(response.result.value!)
$ b json中的项目$ b $ {
//分割标题。删除扩展
let title = item.1 [Title]。string!.characters.split(。)。map(String.init)[0]
let category = item。 1 [ExamCategory]。string
let url = item.1 [URL]。string
let detail = item.1 [PaperCategory]。string

let paper = Paper(name:title,exam:category!,url:url!,detail:detail!)
self.papers.append(paper)

}
self .table.reloadData()

}
//如果网络失败
else {
self.retryButton.hidden = false
self.loadingMessageLabel。 text =检查您的互联网连接
}

}
}


}

这是我的DownloadViewController

  import UIKit 
import QuickLook

class DownloadViewController:UIViewController,UITableViewDataSource,UITableViewDelegate,QLPreviewControllerDataSource {

var items = [(name:String,url:String)]()

@IBOutlet weak var downloadsTable:UITableView!

func tableView(tableView:UITableView,numberOfRowsInSection section:Int) - > Int {
return items.count
}

func tableView(tableView:UITableView,didSelectRowAtIndexPath indexPath:NSIndexPath){

print(items [indexPath。 row] .url)

// performSegueWithIdentifier(DocumentViewSegue,sender:items [indexPath.row] .url)

let previewQL = QLPreviewController()// 4
previewQL.dataSource = self // 5
previewQL.currentPreviewItemIndex = indexPath.row // 6
showViewController(previewQL,sender:nil)// 7

}

func tableView(tableView:UITableView,cellForRowAtIndexPath indexPath:NSIndexPath) - > UITableViewCell {

如果让cell = self.downloadsTable.dequeueReusableCellWithIdentifier(Download Cell)为? DownloadsTableCell {

cell.initCell(items [indexPath.row] .name,detail:,fileURL:items [indexPath.row] .url)

return cell
}

返回DownloadsTableCell()

}

func tableView(tableView:UITableView,commitEditingStyle editingStyle:UITableViewCellEditingStyle,forRowAtIndexPath indexPath:NSIndexPath) {
if editingStyle == UITableViewCellEditingStyle.Delete {

// let fileManager = NSFileManager.defaultManager()
//
// //删除'hello.swift 'file
//
// do {
// try fileManager.removeItemAtPath(String(items [indexPath.row] .url))
//}
//抓住错误,因为NSError {
// print(哎呀!出错了:\(错误))
//}

items.removeAtIndex(indexPath .row)
表View.deleteRowsAtIndexPaths([indexPath],withRowAnimation:UITableViewRowAnimation.Automatic)
}
}


覆盖func viewDidAppear(动画:Bool){

items.removeAll()

let documentsUrl = NSFileManager.defaultManager()。URLsForDirectory(.DocumentDirectory,inDomains:.UserDomainMask).first!

//现在让我们获取目录内容(包括文件夹)
do {
let directoryContents = try NSFileManager.defaultManager()。contentsOfDirectoryAtURL(documentsUrl,includingPropertiesForKeys:nil,options: NSDirectoryEnumerationOptions())
// print(directoryContents)

目录中的var文件内容{
print(file.lastPathComponent)
print(file.absoluteURL)

//将列表中的数据保存为元组
self.items.append((file.lastPathComponent!,file.absoluteString))
}

}捕捉错误为NSError {
print(error.localizedDescription)
}

downloadsTable.reloadData()
}

/ / MARK:预览

func numberOfPreviewItemsInPreviewController(controller:QLPreviewController) - > Int {
return items.count
}

func previewController(controller:QLPreviewController,previewItemAtIndex index:Int) - > QLPreviewItem {
返回NSURL(字符串:items [index] .url)!
}

覆盖func viewDidLoad(){
super.viewDidLoad()


//加载视图后进行任何其他设置。


}

覆盖func viewWillAppear(动画:Bool){
//做点什么

super.viewWillAppear( true)


}

覆盖func didReceiveMemoryWarning(){
super.didReceiveMemoryWarning()
//处置任何可以使用的资源被重建。
}


/ *
// MARK: - 导航

//在基于故事板的应用程序中,您经常需要在导航之前做一点准备
覆盖func prepareForSegue(segue:UIStoryboardSegue,sender:AnyObject?){
//使用segue.destinationViewController获取新的视图控制器。
//将所选对象传递给新视图控制器。
}
* /


}


解决方案

看起来附加了 UISearchController 的视图将从视图层次结构中删除。您可以将 UISearchController 视为在开始搜索时以模态方式呈现,而 definesPresentationContext 属性指示哪个 UIViewController 将是一个呈现它的人(



而不是(我怀疑你现在拥有的):



如果你想解雇 UISearchController 选项卡切换,将此覆盖添加到 ViewController

 覆盖func viewWillDisappear(animated:Bool){
super.viewWillDisappear(animated)
searchController.active = false
}


I have an app with a tab bar controller embedded in a navigation controller. The app has 2 tabs, the first one(search) has a search bar implemented using the UISearchController. If I switch from this tab to the other tab(downloads) while I'm searching, to the other tab two things happen -

  • The navigation bar in the second tab(downloads) disappears
  • When i come back to the first tab(search), it shows a black screen

I have done all this using the storyboard.

this is my SearchViewController

import UIKit
import Alamofire
import SwiftyJSON

class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource, UISearchResultsUpdating, UISearchBarDelegate{

    //MARK: Variables
    var papers = [Paper]()
    var filteredPapers = [Paper]()
    let searchController = UISearchController(searchResultsController: nil)

    // MARK: Outlets
    @IBOutlet weak var activityIndicator: UIActivityIndicatorView!
    @IBOutlet var table: UITableView!
    @IBOutlet weak var loadingMessageLabel: UILabel!
    @IBOutlet weak var retryButton: UIButton!

    //MARK: Actions
    @IBAction func retryButton(sender: UIButton) {
        self.loadingMessageLabel.hidden = false
        self.loadingMessageLabel.text = "While the satellite moves into position..."
        self.activityIndicator.hidden = false
        self.activityIndicator.startAnimating()
        self.retryButton.hidden = true
        self.getPapersData()

    }

    // MARK: Table View

    func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        // If in searching mode, then return the number of results else return the total number
//        if searchController.active && searchController.searchBar.text != "" {
        if searchController.active {
            return filteredPapers.count
        }
        return papers.count
    }

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {

        let paper: Paper

//        if searchController.active && searchController.searchBar.text != "" {
        if searchController.active {
            paper = filteredPapers[indexPath.row]
        } else {
            paper = papers[indexPath.row]
        }

        if let cell = self.table.dequeueReusableCellWithIdentifier("Cell") as? PapersTableCell {

            cell.initCell(paper.name, detail: paper.detail)
            print(cell)
            return cell
        }

        return PapersTableCell()

    }

    func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
    }

    func tableView(tableView: UITableView, editActionsForRowAtIndexPath indexPath: NSIndexPath) -> [UITableViewRowAction]? {


        let downloadButton = UITableViewRowAction(style: .Normal, title: "Download") { action, index in

            var url = String(self.papers[indexPath.row].url)
            url = url.stringByReplacingOccurrencesOfString(" ", withString: "%20")
            print(url)
            let destination = Alamofire.Request.suggestedDownloadDestination(directory: .DocumentDirectory, domain: .UserDomainMask)

            // Spinner in cell

            //            var selectCell = self.table.cellForRowAtIndexPath(indexPath) as? PapersTableCell
            //            selectCell!.downloadSpinner.hidden = false

            // Dismiss the download button
            self.table.editing = false

            Alamofire.download(.GET, url, destination: destination).response { _, _, _, error in
                if let error = error {
                    print("Failed with error: \(error)")
                } else {
                    print("Downloaded file successfully")
                }
                //                selectCell?.downloadSpinner.hidden = true
            }

        }

        downloadButton.backgroundColor = UIColor(red:0.30, green:0.85, blue:0.39, alpha:1.0)


        return [downloadButton]

    }

    func tableView(tableView: UITableView, canEditRowAtIndexPath indexPath: NSIndexPath) -> Bool {
        // the cells you would like the actions to appear needs to be editable
        return true
    }

    func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath) {
        // you need to implement this method too or you can't swipe to display the actions
    }

    // MARK: Search

    func filterContentForSearchText(searchText: String, scope: String = "All") {
        filteredPapers = papers.filter { paper in
            let categoryMatch = (scope == "All") || (paper.exam == scope)
            return  categoryMatch && paper.name.lowercaseString.containsString(searchText.lowercaseString)
        }

        table.reloadData()
    }

    func updateSearchResultsForSearchController(searchController: UISearchController) {
        let searchBar = searchController.searchBar
        let scope = searchBar.scopeButtonTitles![searchBar.selectedScopeButtonIndex]
        filterContentForSearchText(searchController.searchBar.text!, scope: scope)

    }

    func searchBar(searchBar: UISearchBar, selectedScopeButtonIndexDidChange selectedScope: Int) {
        filterContentForSearchText(searchBar.text!, scope: searchBar.scopeButtonTitles![selectedScope])
    }

    // MARK: Defaults

    override func viewDidLoad() {
        super.viewDidLoad()

        self.getPapersData()

        searchController.searchResultsUpdater = self
        searchController.dimsBackgroundDuringPresentation = false
        definesPresentationContext = true
        table.tableHeaderView = searchController.searchBar
        searchController.searchBar.scopeButtonTitles = ["All", "ST1", "ST2", "PUT", "UT"]
        searchController.searchBar.delegate = self
        activityIndicator.startAnimating()


    }

    override func viewWillDisappear(animated: Bool) {
//        if searchController.active {
            self.searchController.resignFirstResponder()
//        }
    }





    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    // MARK: API call

    func getPapersData(){
        Alamofire.request(.GET, "http://silive.in/bytepad/rest/api/paper/getallpapers?query=")
            .responseJSON { response in

                self.activityIndicator.stopAnimating()
                self.activityIndicator.hidden = true

                // If the network works fine
                if response.result.isFailure != true {

                    self.loadingMessageLabel.hidden = true
                    self.table.hidden = false
                    //print(response.result)   // result of response serialization

                    let json = JSON(response.result.value!)

                    for item in json {
                        // Split the title on the . to remove the extention
                        let title = item.1["Title"].string!.characters.split(".").map(String.init)[0]
                        let category = item.1["ExamCategory"].string
                        let url = item.1["URL"].string
                        let detail = item.1["PaperCategory"].string

                        let paper = Paper(name: title, exam: category!, url: url!, detail: detail!)
                        self.papers.append(paper)

                    }
                    self.table.reloadData()

                }
                    // If the network fails
                else {
                    self.retryButton.hidden = false
                    self.loadingMessageLabel.text = "Check your internet connectivity"
                }

        }
    }


}

And this is my DownloadViewController

import UIKit
import QuickLook

class DownloadViewController: UIViewController, UITableViewDataSource, UITableViewDelegate, QLPreviewControllerDataSource {

    var items = [(name:String, url:String)]()

    @IBOutlet weak var downloadsTable: UITableView!

    func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return items.count
    }

    func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {

        print(items[indexPath.row].url)

//        performSegueWithIdentifier("DocumentViewSegue", sender: items[indexPath.row].url)

        let previewQL = QLPreviewController() // 4
        previewQL.dataSource = self // 5
        previewQL.currentPreviewItemIndex = indexPath.row // 6
        showViewController(previewQL, sender: nil) // 7

    }

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {

        if let cell = self.downloadsTable.dequeueReusableCellWithIdentifier("Download Cell") as? DownloadsTableCell {

            cell.initCell(items[indexPath.row].name, detail: "", fileURL: items[indexPath.row].url)

            return cell
        }

        return DownloadsTableCell()

    }

    func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath) {
        if editingStyle == UITableViewCellEditingStyle.Delete {

//            let fileManager = NSFileManager.defaultManager()
//            
//            // Delete 'hello.swift' file
//            
//            do {
//                try fileManager.removeItemAtPath(String(items[indexPath.row].url))
//            }
//            catch let error as NSError {
//                print("Ooops! Something went wrong: \(error)")
//            }

            items.removeAtIndex(indexPath.row)
            tableView.deleteRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
        }
    }


    override func viewDidAppear(animated: Bool) {

        items.removeAll()

        let documentsUrl =  NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask).first!

        // now lets get the directory contents (including folders)
        do {
            let directoryContents = try NSFileManager.defaultManager().contentsOfDirectoryAtURL(documentsUrl, includingPropertiesForKeys: nil, options: NSDirectoryEnumerationOptions())
//            print(directoryContents)

            for var file in directoryContents {
                print(file.lastPathComponent)
                print(file.absoluteURL)

                // Save the data in the list as a tuple
                self.items.append((file.lastPathComponent!, file.absoluteString))
            }

        } catch let error as NSError {
            print(error.localizedDescription)
        }

        downloadsTable.reloadData()
    }

    // MARK: Preview

    func numberOfPreviewItemsInPreviewController(controller: QLPreviewController) -> Int {
        return items.count
    }

    func previewController(controller: QLPreviewController, previewItemAtIndex index: Int) -> QLPreviewItem {
        return NSURL(string: items[index].url)!
    }

    override func viewDidLoad() {
        super.viewDidLoad()


        // Do any additional setup after loading the view.


    }

    override func viewWillAppear(animated: Bool) {
        //do something

        super.viewWillAppear(true)


    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }


    /*
    // 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.
        // Pass the selected object to the new view controller.
    }
    */


}

解决方案

Looks like the view that your UISearchController is attached to gets removed from the view hierarchy. You can think of the UISearchController as being presented modally when you start searching, and the definesPresentationContext property indicates which UIViewController would be the one to present it (more on this).

One of the ways to fix this would be reconfiguring your storyboard so that each tab has its own UINavigationController (in case you need it for both):

Instead of (what I suspect you have now):

And if you want to dismiss UISearchController when the tab switches, add this override to the ViewController:

override func viewWillDisappear(animated: Bool) {
    super.viewWillDisappear(animated)
    searchController.active = false
}

这篇关于使用SearchController搜索时使用标签栏获取黑屏的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆