how can I move a data array between tab bar viewControllers when I have navigationControllers involved - swift

I have a tab bar controller and 3 viewControllers connected to it and when I move data between the viewControllers I use the following code, which works perfect:
let secondTab = tabBarController?.viewControllers![1] as! ImageViewController
secondTab.imageArray = images
Now I added navigation to the second viewController with EDITOR->Embed In....so, there is now a navigationController between my ImageViewController and the tabBarController. How can I still get the data to the ImageViewController?

You can try
if let nav = tabBarController?.viewControllers![1] as? UINavigationController {
if let let secondTab = nav.topViewController as? ImageViewController
secondTab.imageArray = images
}
}

Related

How can I present inside a tab of a UITabBarViewController?

I want to be able to create a TabBarViewController with some tabs and then push into the given tabs
let tabBarViewController = UITabBarController()
let redVc = UIViewController()
redVc.view.backgroundColor = .red
let blueVc = UIViewController()
blueVc.view.backgroundColor = .blue
tabBarViewController.viewControllers = [redVc, blueVc]
This created a tabBarViewController with a red and a blue tab. Now I want to push a yellow VC to the red tab so that I have a yellow and a blue tab.
let yellowVc = UIViewController()
yellowVc.view.backgroundColor = .yellow
tabBarViewController.modalPresentationStyle = .fullScreen
// this doesn't work
viewController.present(tabBarViewController, animated: true)
// must use this
tabBarViewController.viewControllers![0] = yellowVc
What should I do to be able to present in a given tab?
You can setup your UITabbarController in such a way, that each of it's child is a UINavigationController.
All together, you then have the following hierarchy:
UITabbarController
child1 (UINavigationController)
first content ViewController
child2 (UINavigationController)
second content ViewController
Now from within each contentViewController, you can use navigationcontroller.push to push a new viewController to the stack and it will stay inside the tabbar.

How to embed a view controller into a navigation view controller programmatically

I am trying to embed my view controller into a navigation view controller so i get the navigation bar and all the other stuff like back buttons. I want to do it programmatically.
It is done like this:
// example ViewController
let myVC = UIViewController()
// create the NavigationController with my VC as root
let navCon = UINavigationController(rootViewController: myVC)

Tab bar disappeared when back to initial view controller

i have 2 view controllers then tab bar controller connected to 3 navigation controller , each navigation connected to multiple views .
The point that from one of these views that is connected to one of navigation controllers , i want to back again to the start screen , it good by this 2 lines :
let loginViewController = self.storyboard?.instantiateViewController(withIdentifier: "LoginViewController")
UIApplication.shared.keyWindow?.rootViewController = loginViewController
but after i do this and want to navigate again to the tab bar its disappeared from the view . I used this to navigate to tab bar :
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let viewTabController = self.storyboard?.instantiateViewController(withIdentifier :"MainTabBarController") as! MainTabBarController
viewTabController.selectedIndex = 1
appDelegate.window?.rootViewController = viewTabController
Thanks in advance.
When you use instantiateViewController you are making new instances of view controllers in memory while there is no need in your case , you have created them before. so you can dissmis your tabBar and go back to first screen like this (initial viewcontroller must be embeded into a navigation controller) :
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let navigationController = appDelegate.window?.rootViewController as! UINavigationController
navigationController.dismiss(animated: true, completion: nil)
for bringing back tabBar you can either save its instance in your app delegate and present it or use a storyboard segue to present it modally
:)

Navigation bar not showing with MMDrawerController

I am new to swift and iOS development.
In my project i am loading slidein menu with MMDrawerController, it works fine for slide ,but after initializing MMDrawerController in AppDelegate, by top navigation bar [navigation controller] is not getting displayed. commenting MMDrawer initialization shows the navigation bar and click events are firing proper , following is the navigation initialization code ,
func buildNavigationDrawer()
{
// Instantiate Main.storyboard
let mainStoryBoard:UIStoryboard = UIStoryboard(name:"Main", bundle:nil)
// Create View Controllers
let mainPage:TabBarViewController = mainStoryBoard.instantiateViewControllerWithIdentifier("TabBarViewController") as! TabBarViewController
let leftSideMenu:LeftSideViewController = mainStoryBoard.instantiateViewControllerWithIdentifier("LeftSideViewController") as! LeftSideViewController
let rightSideMenu:RightSideViewController = mainStoryBoard.instantiateViewControllerWithIdentifier("RightSideViewController") as! RightSideViewController
// Wrap into Navigation controllers
let leftSideMenuNav = UINavigationController(rootViewController:leftSideMenu)
let rightSideMenuNav = UINavigationController(rootViewController:rightSideMenu)
// Cerate MMDrawerController
drawerContainer = MMDrawerController(centerViewController: mainPage, leftDrawerViewController: leftSideMenuNav, rightDrawerViewController: rightSideMenuNav)
drawerContainer!.openDrawerGestureModeMask = MMOpenDrawerGestureMode.PanningCenterView
drawerContainer!.closeDrawerGestureModeMask = MMCloseDrawerGestureMode.PanningCenterView
// Assign MMDrawerController to our window's root ViewController
window?.rootViewController = drawerContainer
}
In one of the examples about the MMDrawerController there is this code:
self.drawerController = [[MMDrawerController alloc]
initWithCenterViewController:navigationController....
Try to change your mainPage with a UINavigationController with the rootViewController linked to the TabBarViewController and you should be solve the issue.
DETAIL:
// Wrap into Navigation controllers
let leftSideMenuNav = UINavigationController(rootViewController:leftSideMenu)
let rightSideMenuNav = UINavigationController(rootViewController:rightSideMenu)
let centerMenuNav = UINavigationController(rootViewController: mainPage)
// Cerate MMDrawerController
drawerContainer = MMDrawerController(centerViewController: centerMenuNav, leftDrawerViewController: leftSideMenuNav, rightDrawerViewController: rightSideMenuNav)

UISplitview: access UITabBarController from appDelegate

I need to access the UITabBarController, and the second of its subviews from the appDelegate.
This is what I have tried in applicationDidEnterBackground:
let splitViewController = self.window!.rootViewController as! UISplitViewController
let leftNavController = splitViewController.viewControllers.first as! UINavigationController
let tabController = leftNavController.tabBarController! as UITabBarController
let controllers : Array = tabController.viewControllers!
print("viewcontrollers \(controllers)")
The app crashes, complaining that tabController is nil. If i remove the UINavigation controller from storyboard, the UITabBarController is accessed easily with:
let tabController = splitViewController.viewControllers.first as! UITabBarController
What is the correct way to access the childcontrollers of the UITabBarController, where a UISplitView is the root?
Finally I found a solution. I had to use "childViewControllers" of the navigation controller like this:
let splitViewController = self.window!.rootViewController as! UISplitViewController
let leftNavController = splitViewController.viewControllers.first as! UINavigationController
let tabController = leftNavController.childViewControllers.first as! UITabBarController
let viewControllers : Array = tabController.viewControllers!
print("viewControllers \(viewControllers)")
Now I can easily access any of the viewControllers and run their methods from appDelegate :-)
Rather than embedding your tab bar controller in a navigation controller, you should embed the child view controllers in their own navigation controllers, like this:
Split View -> Tab Bar -> Navigation Controller #1 -> View Controller
-> Navigation Controller #2 -> View Controller
This is the correct way to use a tab bar in conjunction with a navigation controller.