简体   繁体   中英

Swift - Setting up Dependency Injection in AppDelegate.swift

I am a self-taught newcomer to iOS programming and have worked through one beginner textbook. I'm trying to publish my first mobile application so I am going back through and cleaning up my code. The textbook I used stressed 'Dependency Injection' but I've struggled adapting their simple example to a more complex application.

The app operates as a shell and retrieves/parses txt files to populate. I successfully connected my model, which retrieves/parses the data, and the TableViewController that needs populated using the following code:

MyTableViewController {
    var data: Data!
}

AppDelegate {
    var window: UIWindow?
    let data = Data()

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

        let navCon = window!.rootViewController as! MyNavigationController
        let tableVC = navCon.topViewController as! MyTableViewController
        tableVC.data = data

        return true
}

I then embedded that NavigationController within a TabBarController because the app will have other tabs. I tried the same process of setting the rootViewController and then drilling down until I could set my data variable, but I can't find the correct way to layer the ViewControllers and keep getting the error;

'fatal error: unexpectedly found nil while unwrapping an Optional value'

I tried two different approaches:

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

        let tabBarCon = window!.rootViewController as! MyTabBarController
        let navCon = tabBarCon.presentedViewController as! MyNavigationController
        let tableVC = navCon.topViewController as! MyTableViewController
        tableVC.data = data

        return true
}

and

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

        let tabBarCon = window!.rootViewController as! MyTabBarController
        let navCon = MyNavigationController()
        tabBarCon.viewControllers = [navCon]

        let tableVC = navCon.topViewController as! MyTableViewController
        tableVC.data = data

        return true
}

Is there a solution to correct this error or am I going about this process wrong? Again, I have a file that pulls in a txt file and then creates a dictionary. I need a separate TableViewController to be able to access that dictionary to populate itself, but I want to achieve this in the most efficient and apple promoted manner, not all in the same file as I did in my first design.

Thanks for the help!

For Dependency Injection I do recommend you use Typhoon . From mine experience it's one of the best tool. This will help you to achive app asembly like:

/* 
 * This is the definition for our AppDelegate. Typhoon will inject the specified properties 
 * at application startup. 
 */
public dynamic func appDelegate() -> AnyObject {
    return TyphoonDefinition.withClass(AppDelegate.self) {
        (definition) in

        definition.injectProperty("cityDao", with: self.coreComponents.cityDao())
        definition.injectProperty("rootViewController", with: self.rootViewController())
    }
}

I found the solution through this thread;

Aassigning a value to a view controller from AppDelegate.swift

The result can be achieved by reconfiguring the second solution I attempted;

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

    let tabBarCon = window!.rootViewController as! MyTabBarController
    let tabBarRootVCs: Array = tabBarCon.viewControllers!

    let navCon = tabBarRootVCs[0] as! MyNavigationController

    let tableVC = navCon.topViewController as! MyTableViewController
    tableVC.data = data

    return true
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM