This question already has answers here:
Tab Bar controller disappearing when moving to another view (iOS SDK, Using storyboards)
(2 answers)
Closed 2 years ago.
I have a tab bar controller, then a navigation controller, then a first view controller. This view controller has a tab bar as expected. However, when I segue from this view I lose the tab bar. I want it to retain its position on the other VC's stemming from this first view. Here is my IB:
I want the tab bar to also appear on the left VC after it is loaded via segue from the right VC,
How is this achieved as currently it disappears regardless of me setting the tab section at the bottom of the VC as shown above.
From storyboard you establish a segue from starting view controller to Tab Bar Root View Controller. Then you use segue to pass the data to the specific item view controller
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let vc = segue.destination as! TabBarRootViewController
let vc1 = vc.viewControllers?[0] as! specificItemViewController
vc1.destinationVariable = self.startingControllerVariable
Related
I have a popover view which is simply a stack of UIButtons.
The popover is presented from a view controller (Records) which is itself inside a NavigationController.
I need the buttons in popover view to be able to push other views on top of the navigation stack.
Here's how I prepare the segue for the popover in the Records view controller:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "popoverSegue" {
let dest = segue.destination as! PopoverViewController
dest.navController = navigationController
dest.modalPresentationStyle = .popover
dest.popoverPresentationController?.barButtonItem = addButton
dest.popoverPresentationController?.delegate = self
}
}
Then inside the popoverViewController I got a bunch of IBAction functions where I need to push other views on top of the navController that was set above.
let editor = EditorViewController(nibName: "EditorViewController", bundle: nil)
navController?.pushViewController(editor, animated: true)
This kina works and the editor view shows up with a nav bar and all, but as soon as I tap on the view or try to scroll, it just gets dismissed.
How can I prevent that dismiss thing? I did try setting isModalInPresentation. It didn't work for me.
Answering, as per OP's comments...
The proper approach is to have your "popover" controller tell the presenting controller to push a new VC onto the navigation stack.
This can be done in a few different ways, but most commonly by using either the protocol/delegate pattern or with closures.
Currently I have a VC1 of type UITableViewController that is embedded in UINavigationController. When the user selects a cell, it performs a push segue to VC2 also of type UITableViewController. That is fine because the navigation bar is still present.
However in VC1, there is a UIBarButtonItem in the navigation bar, that upon tapped, also segues to VC2 and performs different things, but it uses all the same menu layout.
Using the UIBarButtonItem to segue to VC2, I like to perform a modal segue to distinguish between the two actions.
I know that modal segues encompasses the whole screen, and any top bars will be removed.
I followed this question: Modal segue, navigation bar dissapears
One of the answers provided shows how to embed a UINavigationController in prepareForSegue, so I followed it and implemented:
override func prepare(for segue: UIStoryboardSegue, sender: Any?)
{
if segue.identifier == "AddSegue"
{
let navigationController: UINavigationController = segue.destination as! UINavigationController
var addVC: VC2 = VC2()
addVC = navigationController.viewControllers[0] as! VC2
}
}
However, I get the error:
Could not cast value of type 'VC2' to
'UINavigationController'
How can I properly embed a UINavigationController in prepareForSegue because I need to pass data between different view controllers.
Here's my storyboard:
The segue you're intersecting is to your VC2, not a navigation controller. You're going to need to update the "AddSegue" segue to point to a navigation controller, then link your VC2 as the root view controller of the navigation controller.
If you post your storyboard, I can give you more details on how to do this.
EDIT: Here's how you should set up your storyboard. It might get a bit weird, since VC2 has two parent navigation controllers, but it should be fine.
I am developing an iOS app in Swift 2.3, XCode 8.0. My app has 4 tabs and to each of the tabs - 4 different View Controllers are connected. Inside the 4 View Controllers I have embedded Navigation controllers.
My requirement is that when a user selects tab 1 -> goes to ViewController 1 -> Next the user can go to 2nd View Controller as there is a navigation controller.
But when the user selects the second tab and then comes back to the first tab, instead of showing the first View Controller that is directly attached to tab 1, the View Controller that was last opened with the back button is shown.
How can I move directly move to the View Controller attached to the first tab?
The embedded navigation controller should automatically keep track of the stack for you regardless of which tab the user is in with the tab bar controller. Make sure each tab has its own navigation controller embedded into it instead of having the entire tab bar controller embedded in one navigation controller.
For example, if you implemented this programmatically:
let viewController1 = UIViewController()
let navigationController1 = UINavigationController()
navigationController1.setViewControllers([viewController1], animated: true)
let viewController2 = UIViewController()
let tabBarController1 = UITabBarController()
tabBarController1.setViewControllers([navigationController1, viewController2], animated: true)
Here the navigationController1 will keep track of which viewController is on top of the stack regardless of where the user is in the tab bar controller.
Thanks, I found the solution -
This works for me -
In my main tab bar viewController, I made it a delegate of both UITabBarController, UITabBarControllerDelegate and then implemented the didSelectViewController method of UITabBarControllerDelegate as below -
func tabBarController(tabBarController: UITabBarController, didSelectViewController viewController: UIViewController) {
let index : Int = (tabBarController.viewControllers?.indexOf(viewController))!
let navigationController = viewController as? UINavigationController
navigationController?.popToRootViewControllerAnimated(false)
}
I have two view controllers and a Navigation contoller in a storyboard. In the first view controller I have two buttons.
Both buttons segue to the second view which contains a map and opens the map with different info. They are both of the kind show.
The first button when clicked opens the map with the navigation bar at the top (it loads from the side).
The second button loads the map without the navigation bar (it loads from the bottom).
I want both buttons to load the map with the navigation bar.
I am using xcode 7.3 swift and storyboards
Also using prepare for segue
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
if(segue.identifier == "lav"){
let DestViewController = segue.destinationViewController as! MapView
DestViewController.type = typeLav
}
if(segue.identifier == "cam"){
let DestViewController = segue.destinationViewController as! MapView
DestViewController.type = typeCam
}
}
Set the segue action
Present Modally
Show Up from bottom, and without navigation controller, so there is no navbar too.
Push
Push the view controller to current navigation stack, so the navigation bar is shown
btw, method prepareForSegue was used to setup data transfered between view controllers;
I have a set of view controllers linked to a tab controller.
When a image is selected on one of these tabbed views a segue is executed and a detail viewocntroller not linked to the tab controlled is opened.
Pronblem is when I navigate back to the tabbed view controller via segue from the detail view, the tabs are no longer visible.
Before segue executed on tabbed vc:
Same vc with no tab after segue from vc not linked to tab controller
Question is how to ensure tab will be visible on vc when called via the non tabbed vc?
Just to add the tabbed view connected to tab controller is a collection view, the detail view segue is excited when user sects an image:
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
println(segue.identifier)
println(sender)
println("SEGUE SELECTED: \(segue.identifier)");
if(segue.identifier == "segueToDetailScrollView"){
// pass the cell
let cell = sender as CollectionViewCell;
let indexPath = collectionView?.indexPathForCell(cell);
let vc = segue.destinationViewController as ScrollView;
var image = arrayOfIUmages[indexPath!.row];
var imageTitle = titles[indexPath!.row];
println("Image to segue name : \(image) and the title : \(imageTitle)");
println("The vew controller \(vc)");
vc.currImage = UIImage(named: arrayOfIUmages[indexPath!.row]);
vc.textHeading = self.titles[indexPath!.row];
}
}
You will need to create a segue to the tabcontroller and let tab controllers set the inner view. Onload you can check for a shared default or something similar to find which tab should be shown.
Need to use unwind method in target view controller to allow navigation back to the same instance navigated from, good example here http://www.raywenderlich.com/81880/storyboards-tutorial-swift-part-2