I have an app that uses a UITabBarController with 7 Tabs. Each tab is a UIViewController subclass (each embedded in a UINavigationController) that simply has a different background color in the view set in the storyboard. The TabItems are labeled Tab 1 through Tab 7 and the Title set in each NavBar is simply the Tab number. I've added some static Quick Actions in my Info.plist that allow me to jump to Tab 2, Tab 3, Tab 6 and Tab 7.
The problem I run into is when I set the selected Tab when handling the quick action in the AppDelegate all works fine for the first 4 tabs. If I select one of the Tabs listed in the More... list the app opens up only selecting the first tab in my UITabBarController. However if the app had already been running and I go to the home screen and try the Quick Action again then it is able to select any of the tabs from the More list. Any ideas?
Here is my AppDelegate code:
// AppDelegate.swift
import UIKit
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate
{
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
// handle quick actions
if let shortcutItem =
launchOptions?[UIApplicationLaunchOptionsKey.shortcutItem]
as? UIApplicationShortcutItem {
let _ = handleShortcut(shortcutItem: shortcutItem)
return false
}
return true
}
func application(_ application: UIApplication, performActionFor shortcutItem: UIApplicationShortcutItem, completionHandler: @escaping (Bool) -> Void) {
completionHandler(handleShortcut(shortcutItem: shortcutItem))
}
private func handleShortcut(shortcutItem: UIApplicationShortcutItem) -> Bool {
let shortcutType = shortcutItem.type
guard let shortcutIdentifier = ShortcutIdentifier(fullIdentifier: shortcutType) else {
return false
}
switch shortcutIdentifier {
case ShortcutIdentifier.OpenTab2: fallthrough
case ShortcutIdentifier.OpenTab3: fallthrough
case ShortcutIdentifier.OpenTab6: fallthrough
case ShortcutIdentifier.OpenTab7:
return selectTabBarItem(forIdentifier: shortcutIdentifier)
}
}
private func selectTabBarItem(forIdentifier identifier: ShortcutIdentifier) -> Bool {
if let tabBarController = self.window?.rootViewController as? CustomTabBarController
{
switch (identifier)
{
case .OpenTab2:
tabBarController.selectedIndex = tabDictionary["OpenTab2"]!
case .OpenTab3:
tabBarController.selectedIndex = tabDictionary["OpenTab3"]!
case .OpenTab6:
tabBarController.selectedIndex = tabDictionary["OpenTab6"]!
case .OpenTab7:
tabBarController.selectedIndex = tabDictionary["OpenTab7"]!
}
}
return true
}
// Integer in dictionary denotes tab number (zero based)
private let tabDictionary = ["OpenTab2": 1, "OpenTab3": 2, "OpenTab6": 5, "OpenTab7": 6]
enum ShortcutIdentifier: String {
case OpenTab2
case OpenTab3
case OpenTab6
case OpenTab7
init?(fullIdentifier: String) {
guard let shortIdentifier = fullIdentifier.components(separatedBy: ".").last else {
return nil
}
self.init(rawValue: shortIdentifier)
}
}
}
I found the following link (http://jakzaprogramowac.pl/pytanie/18417,select-index-greater-than-3-for-uitabbarcontroller-at-app-launch-not-working) that seemed to answer my question. I hope this helps others.
I added the following code to the beginning of AppDelegate DidFinishLaunchingWithOptions to initially select the first tab and call layoutIfNeeded() on the tabBarController's View: