3

This question has been asked before, but I am not able to get a clear explanation about this issue. I have a simple application with a tableview and a search function. In viewDidLoad(), I call setUpSearchView() which is defined like this

  let searchController = UISearchController(searchResultsController: nil)
  searchController.searchResultsUpdater = self
  searchController.hidesNavigationBarDuringPresentation = true
  searchController.dimsBackgroundDuringPresentation = false
  self.tableView.tableHeaderView = searchController.searchBar

This code doesn't not work properly. On the console, I can see this error

Attempting to load the view of a view controller while it is deallocating is not allowed and may result in undefined behavior

Moreover, the searchcontroller does not animate properly and does not call updateSearchResultsForSearchController delegate when I type on the searchbar.

But, all these issues are easily fixed by making a minor change to the searchController initialization function. Rather than declaring the searchController as a local variable in the function, If I declare it an instance variable outside the method like this var searchController:UISearchController!, everything works, although I have no idea why.

Now the code will look like this

var searchController:UISearchController!

In setUpSearchView()

 searchController = UISearchController(searchResultsController: nil)
 searchController.searchResultsUpdater = self
 searchController.hidesNavigationBarDuringPresentation = true
 searchController.dimsBackgroundDuringPresentation = false
 self.tableView.tableHeaderView = searchController.searchBar

Here is a link to the viewController on github: https://github.com/tmsbn/marvel_heroes/blob/master/avengers/HeroesListController.swift

Can someone explain why this happens? Is this a bug with swift? Or it is something in iOS that I don't know about.

TMS
  • 1,201
  • 1
  • 13
  • 20
  • see this once it helps you http://stackoverflow.com/questions/32282401/attempting-to-load-the-view-of-a-view-controller-while-it-is-deallocating-uis – Anbu.Karthik Apr 15 '16 at 08:01

1 Answers1

3

If you are creating a variable in a function (viewDidLoad) it's lifetime is the same as that functions lifetime. In this case you are trying to set the table header view as a searchController that is being deallocated (it's lifetime is the same as viewDidLoads)

When you create the variable outside of viewDidLoad and instantiate it later, the variable has the same lifespan as the viewController/class

Olivier Wilkinson
  • 2,836
  • 15
  • 17
  • Sorry, but I don't quite understand. Why is the searchController being deallocated before it is being set as the table header view? Is setting table header view an asynchronous function. – TMS Apr 15 '16 at 08:24
  • I think that on running the code, the compiler sees that the variable will be deallocated at the end of viewDidLoad, so setting it as the table header flags up that error. This is because while the table header is now set, all the pointers to that object are gone, which is why the delegate methods don't work etc. – Olivier Wilkinson Apr 15 '16 at 08:30
  • I see.. that makes sense. Thank you for the explanation! – TMS Apr 15 '16 at 08:32
  • No problem! Glad I could be of help! – Olivier Wilkinson Apr 15 '16 at 08:32