I have a very simple View controller below. The UI is literally just a single button with the tab bar at the bottom.
import UIKit
class ImageAdderViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
#IBAction func ButtonPressed(sender: AnyObject) {
let imagePicker = UIImagePickerController()
imagePicker.allowsEditing = false
imagePicker.sourceType = .PhotoLibrary
self.presentViewController(imagePicker, animated: true, completion: nil)
}
}
Once the select image from photo library is selected, if I click cancel or select an image it returns to the view. But the view is now empty except for the tab view.
Here is where my confusion begins:
This code works on an empty project with just one controller.
This code works when I segue to this controller from a different controller that has no tab bar at the bottom. At this point the UI with the button that we have segued to also has no tab bar.
This code does not work when I segue to the controller via a controller that has the tab bar.
All segues are push Show (e.g. Push) segues.
In short the same UIViewController works when segued to by one view but not when segued to by a different view.
EDIT 1 Specific Questions
How do I make the view controller work even when segued to by a view controller with a tab bar? Could the tab bar interfere with the presentViewController code?
My Guess
Somehow something from the previous controller with the tab bar is messing up the code on the viewcontroller with the load button, and that something seems to be entering with the tab bar when the Show occurs. How do I prevent this?
EDIT 2 More clarification
When I click cancel or select an image, the view controller that it returns me too is now empty. The button is missing. When I add labels to the view, all added those disappear as well, and it is just white, except the tab bar at the bottom. This does not occur if I segue to the load image view controller from a view without the tab bar.
EDIT 3
The View that does not bring the tab bar with it when segued from, is not segued to via a navigation controller.
The View that does bring the tab bar with it when segued from, is segued to via a navigation controller.
The Former view functionality does not cause the error. But it does not bring the tab bar
The Latter functionality has brings the tab bar and I want that.
EDIT 4
Changing the segue to a modal present on the UI which has the tab eliminates the tab bar but does not solve to UI deletion problem. This means that merely the presence of the tab bar is not causing the problem.
EDIT 5
If I completely delete the navigation controller in the storyboard it all works, but the tab bar is gone. How can I make it work with the navigation controller?
Related
I am facing a strange issue with Tab bar controller. I have a tab bar controller in main.storyboard working fine. I have 5 different storyboard references for each item and I could see all 5 tabs and tab bar is working fine in the simulator.
On selecting the 3rd tab, there is a button in 1st view controller that pushes to second view controller, here I am hiding the tab bar in viewWillAppear. Then when I push to 3rd view controller, I am showing the tab bar again in viewWillAppear.
Now when I select some other tab item from 3rd view controller and come back to 3rd tab, tab bar is not visible even though i have written below code:
override func viewWillAppear(_ animated: Bool) {
tabBarController?.tabBar.isHidden = false
}
Finally figured out the issue. One of my view controller in storyboard had hide tab bar on push view controller enabled causing the tab bar to hide in my expected view controller. On unchecking it and handling all hide/show tab bar in source code itself, i am able to fix the issue.
I have read multiple answers regarding this issue. The main thing indicated is to set hidesBottomBarWhenPushed to true, which i have done and is still not working for me.
So this is my storyboard layout.
So i present a TableViewController from my TabBarController, the view i present is the bottom left on the storyboard. With hidesBottomBarWhenPushed set to true, i expect the bottom bar to be hidden but this is not the case. It actually adds a new bottom bar and upon navigating back to the tab view a new tab bar is overlapping the original one. You can see this in the screenshots below.
So firstly the tab bar, we then select the filter icon on the top right, which triggers the segue to the next controller.
So now the next controller loads in. As you can see the tab bar is displayed even though i have set hidesBottomBarWhenPushed on the storyboard.
And now when we navigate back there is a new tab bar overlapping the original.
I don't have much experience with tab bar controllers, have i done something wrong with my storyboard hierarchy maybe. Perhaps each tab should have its own navigation controller. However my tab bar also needs a navigation controller.
Any help or suggestions is greatly appreciated.
In viewDidLoad of tableVC
self.tabBarController?.tabBar.isHidden = true
In viewWillAppear of the VC before the tableVC
self.tabBarController?.tabBar.isHidden = false
I have being trying different things and looking around for a while without finding an answer to my problem. Maybe I'm doing something fundamentally wrong.
The sample application consists of:
A first view controller that displays a second view controller using a segue. This works fine.
A second view controller, in which I have simulated the display of a third view programmatically, which contains a bar item button (named "Done") that I would like to display.
The bar item button in the third view controller is not displayed at runtime but is displayed in IntefaceBuidler at design time.
This third view controller needs to be displayed modal.
What I'm doing wrong to display this bar item button?
A sample project illustrating the problem is available here.
Below a screen capture of the bar item button at design time:
Below a screen capture of the bar item button not showing at design time:
PS:
Please disregard the "Unknown class ThirdViewControlller in Interface Builder file.", since the ThirdViewController is displayed fine at runtime. Also, the "Done" button in the middle of the view works fine.
In SecondViewController you need to push the third onto the navigation controller stack like so:
self.navigationController?.pushViewController(thirdViewController, animated: true)
You are currently presenting it as a modal. Also, you've unnecessarily added a second UINavigationController to your storyboard (for the third view controller)
If you want to present a modal, then you'd need to embed the controller in a navigation controller:
let navController = UINavigationController(rootViewController: thirdViewController)
self.present(navController, animated: false)
If you prefer to keep this within the storyboard, then you need to provide a identifier for the UINavigationController and insatiate that in your function.
The above button is a navigation bar item that will only be displayed on the navigation bar . For achieving your desired result , you first have to embed the navigation controller at least in your second viewcontroller and then you should do a push segue rather than modal . Navigation controller can be added by
whith your second viewcontroller selected go to Editor\Embed In\Navigation Controller
for pushing the viewcontroller programatically onto user navigation controller's stack use
self.navigationController?.pushViewController(nextViewController, animated: true)
I made one button on the navigation bar. I made it to modal view. But the problem is I can't bring this modal view on the top of the tab bar. What should I do?
In addition, I have used storyboard's segue to present the modal view.
Enter to see storyboard image
Enter to see simulator image
It's hard to tell from the screenshots, but it seems like what you want is for the tab bar to become greyed out just like the background of the view inside the UITabBarController?
Where are you presenting the modal view from? If view controller A is inside your tab bar controller, then presenting the modal view from A will result in the tab bar not getting grayed out. If you present from the tab bar controller, it should do what you want.
In the presenting view controller's code, instead of
present(modalViewController, animated: true, completion: completion)
try using
tabBarController?.present(modalViewController, animated: true, completion: completion)
(Where modalViewController and completion are whatever you mean to use for these arguments, of course.)
If you are using a segue to present the modal controller, then the same concept applies. Move the segue to the tab bar controller and then perform it on the tab bar controller from the presenting view controller.
tabBarController?.performSegue(withIdentifier: "yourSegueIdentifier", sender: tabBarController)
You can simply use the modalPresentationStyle of your view controller and set it to fullScreen or overFullScreen and this will automatically hide the tab bar, whether the view controller is presented from the tab bar or not.
Swift 4 example:
presentedVC.modalPresentationStyle = .overFullScreen
You can check the documentation for more information: UIModalPresentationStyle
This is the current layout for my application. As you can see, I have a ViewController that is embedded in a TabBarViewController. You can see I have two tab bars in both of those bottom view controllers but only the first one shows up. In the second view controller after the push segue, the tab bar disappears. Why is this?
I added the properties for the First view controller and it is not set to hide the bottom bar during the segue so I am confused as to why it would disappear after the segue. Any ideas?
You'll need to wrap your tabBar's root viewControllers in a UINavigationController. So your UITabBarController would actually be pointed at the Navigation Controller. Then as you move around in that navigation controller, the tab bar will stay in place.
To fix this in your application, select your view controller in storyboard, then click "Editor" -> "Embed In" -> "Navigation Controller".
Here's a visual representation I just threw together for anyone else who comes across this problem. If you remove the "NavigationController" in the storyboard shown below, the tab will disappear when you click the button in "First View". With the navigation controller, you will maintain the tab bar. Hope this helps.
Try set self.tabBarController.tabBar.translucent = NO; in viewWillAppear
You could also try to dismiss the views by adding an outlet/action. For example, I experienced an issue where I had a TabBar view controller and needed to segue between 2 different views (ImageViews) on one of the tabs and as soon as I did a traditional segue, the whole tab bar disappeared. I had created the following "Back button" to clear the view:
#IBAction func backBtnPressed(_ sender: AnyObject) {
dismiss(animated: true, completion: nil)
}
Note: It is an important practice to clear views out as they will stack up overtime and will reduce the performance of your app.
Technical Info:
https://developer.apple.com/reference/uikit/uiviewcontroller/1621505-dismiss
Not sure if this helps but worth mentioning!