iosswiftuitabbarcontroller

Present a View Controller modally from a tab bar controller


I want to build a view with a camera. Something just like Instagram where there is a button in the middle that the user can click and the camera view shows up. I implemented a code for the TabViewController in the AppDelegate but nothing happens, no animation or Presentation of the new ViewController.

Here is my AppDelegate:

import UIKit


class AppDelegate: UIResponder, UIApplicationDelegate, UITabBarControllerDelegate {
    var window: UIWindow?
    func tabBarController(_ tabBarController: UITabBarController, shouldSelect viewController: ViewController) -> Bool {
    if viewController is ViewController {
        let storyboard = UIStoryboard(name: "Main.storyboard", bundle: nil)
        if let controller = storyboard.instantiateViewController(withIdentifier: "cameraVC") as? ViewController {
            controller.modalPresentationStyle = .fullScreen
            tabBarController.present(controller, animated: true, completion: nil)
        }
        return false
    }
    return true
}

Here is my Storyboard:

Main.storyboard

Any ideas?


Solution

  • I suggest to create a custom class for your TabBarController, then assign the delegate to that.

    You can either assign and check the restorationIdentifier of the view controller, or do a type check. I usually use storyboard identifier as the restoration identifier of the view controller(s).

    class TabBarController: UITabBarController, UITabBarControllerDelegate {
    
        override func viewDidLoad() {
            super.viewDidLoad()
    
            self.delegate = self
        }
    
        func tabBarController(_ tabBarController: UITabBarController, shouldSelect viewController: UIViewController) -> Bool {
            if let identifier = viewController.restorationIdentifier, identifier == "cameraVC" {
                let vc = self.storyboard?.instantiateViewController(withIdentifier: "cameraVC") as! CameraViewController
                present(vc, animated: true, completion: nil)
                return false
            }
    
            return true
        }
    }
    

    Here's a sample you can play with: https://gist.github.com/emrekyv/3343aa40c24d7e54244dc09ba0cd95df