I'm using SWRevealViewController with TabBar Controller as front and a VC in which I have placed TableView as a rear view for SWReveal VC.
My UI Looks like this,
Now when I click on table view and want to open first tab bar VC it hides my Tab bar from the bottom. Through this code I try to open my TabBar Controller,
var menuVCBeforeLoginArray = ["NewsVC","BookmarkVC","MessageVC"]
let vcIdentifier = menuVCBeforeLoginArray[indexPath.row]
let vc = storyboard!.instantiateViewController(withIdentifier: vcIdentifier)
let navVC = UINavigationController.init(rootViewController: vc)
self.revealViewController().pushFrontViewController(navVC, animated: true)
Now when it opens the first tab bar it looks like this with hidden bottom bar.
How can I show the bottom bar even when I open VC from side menu?
You should not push with selected viewcontroller with a navigation controller. Get the tabbar controller and change selectedIndex
//var menuVCBeforeLoginArray = ["NewsVC","BookmarkVC","MessageVC"]
//let vcIdentifier = menuVCBeforeLoginArray[indexPath.row]
//let vc = storyboard!.instantiateViewController(withIdentifier: vcIdentifier)
//let navVC = UINavigationController.init(rootViewController: vc)
//self.revealViewController().pushFrontViewController(navVC, animated: true)
if let tabBarController = self.revealViewController().frontViewController as? UITabBarController {
tabBarController.selectedIndex = indexPath.row
}
Related
So I can't use initial view controller for the tab bar controller because there is already one and this is way further along in the app. That is why I made a tab bar controller programmatically inside the first to two view controllers that I want in the tab bar controller.
Here is the VC where I add the tab bar controller to, in viewDidLoad.
let tabBarController2 = YourTabBarController()
addChild(tabBarController2)
view.addSubview(tabBarController2.view)
NSLayoutConstraint.activate([
tabBarController2.view.bottomAnchor.constraint(equalTo: mainview.bottomAnchor),
tabBarController2.view.leadingAnchor.constraint(equalTo: mainview.leadingAnchor),
tabBarController2.view.trailingAnchor.constraint(equalTo: mainview.trailingAnchor),
])
tabBarController2
.didMove(toParent: self)
below is the class of the tab bar controller
super.viewDidLoad()
let storyboard = UIStoryboard(name: "Main", bundle: nil)
let firstViewController = homepage()
let navigationController = UINavigationController(rootViewController: firstViewController)
navigationController.title = "First"
viewControllers = [navigationController]
if let secondViewController = storyboard.instantiateViewController(withIdentifier: "ranking") as? ranking {
let navgitaionController1 = UINavigationController(rootViewController: secondViewController)
navgitaionController1.title = "Second"
var array = self.viewControllers
array?.append(navgitaionController1)
self.viewControllers = array
I want to append couple of viewcontrollers in array of viewcontroller of a navigation controller, then want push third viewcontroller of the same navigation controller.
My code is as follows
let navigationController = getCurrentNavController()
let listVC = UIStoryboard.loadListViewController()
navigationController.viewControllers.append(listVC)
let detailVC = UIStoryboard.loadDetailsViewController()
navigationController.viewControllers.append(detailVC)
let thirdVC = UIStoryboard.loadThird()
navigationController.pushViewController(thirdVC, animated: true)
The thirdVC is push on the navigation controller,
the problem is when i pop thirdVC,
I don't find detailVC or listVC.
Is this possible?
if yes please help.
Don't edit the viewControllers array directly. That is why the animated parameter exists.
A solution may be to add the viewControllers in between after 0.25 seconds (the duration of the push animation) by doing:
let navigationController = getCurrentNavController()
var viewControllers = navigationController.viewControllers
let listVC = UIStoryboard.loadListViewController()
viewControllers.append(listVC)
let detailVC = UIStoryboard.loadDetailsViewController()
viewControllers.append(detailVC)
let thirdVC = UIStoryboard.loadThird()
viewControllers.append(thirdVC)
navigationController.pushViewController(thirdVC, animated: true)
DispatchQueue.main.asyncAfter(now() + 0.25) {
navigationController.setViewControllers(viewControllers, animated: false)
}
As mentioned, you do not want to modify the navigation controller's viewControllers directly.
But, you also don't need to do any explicit "pushing":
let navigationController = getCurrentNavController()
let listVC = UIStoryboard.loadListViewController()
let detailVC = UIStoryboard.loadDetailsViewController()
let thirdVC = UIStoryboard.loadThird()
var vcs = navigationController.viewControllers
vcs.append(listVC)
vcs.append(detailVC)
vcs.append(thirdVC)
navigationController.setViewControllers(viewControllers, animated: true)
This will animate thirdVC in from the current view controller, just as if you had pushed it, but it will also insert listVC and detailVC into the navigation controller's stack so the "Back" button will take you through detailVC and listVC.
When presenting my viewcontroller this way I don't get a navigationbar, even though the viewcontroller is embedded in a navigation controller in the interface builder.
if let stockVC = storyboard?.instantiateViewController(withIdentifier: "Stock") as? StockTableViewController {
stockVC.stockToDisplay = commonData.stock.filter { $0.productID.contains(product) }
// No NavigationBar with this one
navigationController?.present(stockVC, animated: true)
// No NavigationBar with this one
self.present(stockVC, animated: true)
}
I know the navigationBar works, because if I set the ViewController as initial in the storyboard, it shows.
What am I doing wrong here?
When you present a view controller, it is not part of the current navigation stack. You need to create a new navigation controller with your stockVC contained in it, and present the new navigation controller:
if let stockVC = storyboard?.instantiateViewController(withIdentifier: "Stock") as? StockTableViewController {
stockVC.stockToDisplay = commonData.stock.filter { $0.productID.contains(product) }
let stockNavigationController = UINavigationController(rootViewController: stockVC)
self.present(stockNavigationController, animated: true)
}
I am building a flow like this
FirstViewController -> SecondViewController - > Tab Bar View Controller (consists of 1. ThirdViewController and 2. FourthVIewController)
I am opening Tab Bar View Controller as a pop up form the SecondViewController. However, when I run (self.dismiss(animated: true, completion: nil)) on click of a button in ThirdViewController, it goes back to the FirstViewController.
I want to go back to the SecondViewController
Adding code.
This is how I open the tab bar view controller from my SecondViewController
let popupVC = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "tabBarVC") as! UITabBarController
self.addChildViewController(popupVC)
popupVC.view.frame = self.view.frame
self.view.addSubview(popupVC.view)
popupVC.didMove(toParentViewController: self)
And this is how I try to close the tab bar view controller form Third View Controller
self.dismiss(animated: true, completion: nil))
You added tabBarController in secondViewController as subView. So you need to remove that tabBarController view from super view.
For that, you need a tabBarController object.
self.tabBarController?.view.removeFromSuperview()
You can use a navigation controller in your flow, so when you are in ThirdViewController use this:
if let vc = self.storyboard?.instantiateViewController(withIdentifier: "second") as? SecondViewController {
self.navigationController?.popToViewController(vc, animated: true)
}
The below code was able to remove the tabview and take me back to the SecondViewController
self.tabBarController?.view.removeFromSuperview()
Switching to other item on UITabBar, where 0 insert index of UTTabBar item:
self.tabBarController?.selectedIndex = 0
I want to create an app that lets the user click on a button on V1 on the navigation bar. This will segue to V2 where they can press another button on the navigation bar on V2 and it will bring them back to V1 which has the tab bar controller at the bottom. I don't want the tab bar on V2 and I don't want V2 as a tab bar item. When I try this the tab bar disappears on V1 when I segue back to V1 from V2.
TAB BAR CONTROLLER -> TAB BAR ITEM (V1) -> V2(Via navigation bar button item on V1) -> back to V1(Via navigation bar button item on V2)
I have added [self.navigationController, popViewControllerAnimated:YES]; to my button function but it comes up with an error - expected expression in container literal.
Apart from this code I have not got any other code in my app yet.
I am using Xcode 8.0 and Swift 3.0
First create subclass of UITabBarController, Then add properties to AppDelegate
var navController: UINavigationController?
var tabController: MyTabController?
If you want to show tab bar controller on app launch then put these code in AppDelegate in didFinishLaunchingWithOptions
self.window = UIWindow(frame: UIScreen.main.bounds)
let myStoryboard = UIStoryboard(name: "Main", bundle: nil) as UIStoryboard
self.tabController = myStoryboard.instantiateViewController(withIdentifier: "MyTabController") as? MyTabController
//self.navController = UINavigationController(rootViewController: self.tabController!)
//self.window?.rootViewController = self.navController
self.window?.rootViewController = self.tabController
self.window?.makeKeyAndVisible()
return true
If you want to jump on tab bar after login or something else then , add property to that controller
var appDelegate: AppDelegate!
in viewDidLoad
appDelegate = UIApplication.shared.delegate as? AppDelegate
And method should like
func logIntoApp() {
appDelegate.tabController = self.storyboard?.instantiateViewController(withIdentifier: "MyTabController") as? MyTabController
appDelegate.window?.rootViewController = appDelegate.tabController
}
Then in your tab item view controller , create property of AppDelegate and assign delegate as above.
And methods should be like :
#IBAction func showWithTab(_sender: AnyObject) {
let DefaultVC = self.storyboard?.instantiateViewController(withIdentifier: "DefaultViewController") as! DefaultViewController
self.navigationController?.pushViewController(DefaultVC, animated: true)
}
#IBAction func showWithoutTab(_sender: AnyObject) {
let DefaultVC = self.storyboard?.instantiateViewController(withIdentifier: "DefaultViewController") as! DefaultViewController
// You can create your own animation
UIView.transition(from: (appDelegate.tabController?.view)!, to: (appDelegate.navController?.view)!, duration: 0.3, options: UIViewAnimationOptions.curveEaseIn) { (finished) in
self.appDelegate.window?.rootViewController = self.appDelegate.navController
}
// OR you can use like this way
UIView.transition(from: self.view, to: DefaultVC.view, duration: 0.3, options: UIViewAnimationOptions.curveEaseIn) { (finished) in
self.appDelegate.window?.rootViewController = self.appDelegate.navController
}
}
Why not use a simple Tab Bar?
Something like this:
and in VC1 :
override func viewWillDisappear(_ animated: Bool) {
super.viewWillDisappear(animated)
myTab.removeFromSuperview()
}
I have solved my problem after days of trying to figure out an answer. You need to add this to any view controller.
#IBAction func unwindToViewController (sender: UIStoryboardSegue){
}
Then you can add a segue from bar button item to the exit icon on the view controller.
You can view an image of the VC scene here.