如何对UINavigationController和UISearchController进行子类化以注入依赖项?

时间:2019-06-29 14:36:20

标签: swift dependency-injection uinavigationcontroller tdd uisearchcontroller

有人可以解释为什么我必须在UINavigationControllerUISearchController上都覆盖init(nibName,bundle)吗?

import UIKit

class DashboardNav: UINavigationController {

    var dashboard: UIViewController?

    init(dashboard: UIViewController) {
        self.dashboard = dashboard
        super.init(rootViewController: dashboard)
        self.tabBarItem = UITabBarItem(title: "Dashboard", image: #imageLiteral(resourceName: "vectorEq"), tag: 1)
    }

    //FIXME: Why does this get called after init
    override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: Bundle?) {
        super.init(nibName: nil, bundle: nil)
    }

    required init?(coder aDecoder: NSCoder) { fatalError("IMPOSSIBLE")}
}

此代码将编译,但将取消我的仪表板引用,迫使我在构造后设置它,这是我不希望的。自定义init首先运行,然后再运行init(nibName,bundle)。这是构建代码的解决方法。

let dashBoard = UIViewController()
let dashboardNav = DashboardNav(dashboard: dashboardScreen)
dashboardNav.dashboard = dashBoard //FIXME: this is bad

如果我删除init(nibName,bundle),则由于异常,应用崩溃

我在UISearchController子类中观察到了相同的行为。这是显示解决方案的结构。

let sortToolBar = SortToolbar()
let search = Search(Database: database, sortToolBar: sortToolBar)
search.sortToolBar = foodSortToolBar //FIXME: =0
search.searchBar.inputAccessoryView = foodSortToolBar //FIXME: =0
search.foodDatabase = foodDatabase //FIXME: init(nibName) seems to be reinitializing

这是UISearchController子类。

import UIKit

class Search: UISearchController {

    var foodDatabase: FoodDatabase? //FIXME: ? var is here because init(nib) complains it's not
    var foodSortToolBar: FoodSortToolbar? //FIXME: =0

    init(database: Database, sortToolBar: SortToolbar) {
        self.foodDatabase = foodDatabase    //FIXME: Still have to attach it post construction
        self.foodSortToolBar = foodSortToolBar
        super.init(searchResultsController: nil) //FIXME: Calls init(nibName, bundle)


        //FIXME: Inject the search bar...couldn't get it to work
        self.searchBar.delegate = self
        self.searchBar.scopeButtonTitles = ["Totality", "Frequency", "Recency"]
        self.searchBar.showsScopeBar = true
        self.searchBar.placeholder = "Food Search"
        self.searchBar.showsCancelButton = true
        self.searchBar.showsSearchResultsButton = false
        self.searchBar.searchBarStyle = .minimal

    }

    //FIXME: Why does this get called after init
    override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: Bundle?) {
        super.init(nibName: nil, bundle: nil)
    }

    required init?(coder aDecoder: NSCoder) { fatalError("init(coder:) has not been implemented") }
}

有人知道该机制的原因吗? 请指教。 谢谢。

亚伦

0 个答案:

没有答案