3

I have the following issue. When I run my app on my phone, 3d touch the icon and select the quick action it launches the app presenting the correct view controller but when I put the app in background and try to invoke the quick action it just opens the app where I have left it. So to make it work I have to kill my app every time. Here is my code:

func application(application: UIApplication, performActionForShortcutItem shortcutItem: UIApplicationShortcutItem, completionHandler: (Bool) -> Void) {
    if shortcutItem.type == "com.traning.Search" {

        let sb = UIStoryboard(name: "Main", bundle: nil)

        let searchVC = sb.instantiateViewControllerWithIdentifier("searchVC") as! UINavigationController

        let root = UIApplication.sharedApplication().keyWindow?.rootViewController
        root?.presentViewController(searchVC, animated: false, completion: { () -> Void in
            completionHandler(true)
        })

    }
}

Thanks in advance.

martin petrov
  • 123
  • 3
  • 13
  • 1
    Does it call performActionForShortcutItem? Is root = nil? – beyowulf Dec 02 '15 at 18:16
  • Where does it have to call the performActionForShortcutItem? – martin petrov Dec 02 '15 at 18:33
  • 1
    I mean just try printing something in performActionForShortcutItem to ensure it's being called. Perhaps print(root) that why you can check if performActionForShortcutItem is called and check to make sure root is not nil. – beyowulf Dec 02 '15 at 18:37
  • The problem is that it calls the method only once after I launch the app then if I put it in the background and try to call the method nothing happens. – martin petrov Dec 02 '15 at 18:42
  • 1
    Do you know for a fact it's not calling it? Or might it get called but not do anything? Doing what I suggested will help us determine which it is. Do you do so? What was the result? – beyowulf Dec 02 '15 at 18:44
  • root is: Optional() – martin petrov Dec 02 '15 at 18:45
  • So it calls it everytime but does not transfer to the correct view controller. – martin petrov Dec 02 '15 at 18:46
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/96826/discussion-between-martin-petrov-and-beyowulf). – martin petrov Dec 02 '15 at 18:51

1 Answers1

4

I'm guessing you're trying to present a view controller from a view controller that's not visible. You can use extensions like:

    extension UIViewController {
    func topMostViewController() -> UIViewController {
        if self.presentedViewController == nil {
            return self
        }
        if let navigation = self.presentedViewController as? UINavigationController {
            return navigation.visibleViewController.topMostViewController()
        }
        if let tab = self.presentedViewController as? UITabBarController {
            if let selectedTab = tab.selectedViewController {
                return selectedTab.topMostViewController()
            }
            return tab.topMostViewController()
        }
        return self.presentedViewController!.topMostViewController()
    }
}

extension UIApplication {
    func topMostViewController() -> UIViewController? {
        return self.keyWindow?.rootViewController?.topMostViewController()
    }
}

You can place both of these in your app delegate.swift, above your app delegate class, to get the currently visible view controller.enter image description here Then present the search view controller on that. For example:

func application(application: UIApplication, performActionForShortcutItem shortcutItem: UIApplicationShortcutItem, completionHandler: (Bool) -> Void) {
    if shortcutItem.type == "com.traning.Search" {

        let sb = UIStoryboard(name: "Main", bundle: nil)

        let searchVC = sb.instantiateViewControllerWithIdentifier("searchVC") as! UINavigationController

        let topViewController = UIApplication.sharedApplication.topMostViewController()
        topViewController.presentViewController(searchVC, animated: false, completion: { () -> Void in
            completionHandler(true)
        })

    }
}
beyowulf
  • 15,101
  • 2
  • 34
  • 40