I have used navigation item in my app. In the log out method I have popped to root view controller i.e. my loginViewController but while doing so the navigation bar gets removed. I have tried putting the code to load in viewWillAppear but it is still not working. Could you please help me?
Here is my code for log out:
#IBAction func btnLogOutClicked(_ sender: Any) {
let log : LoginViewController = self.storyboard?.instantiateViewController(withIdentifier: "LoginViewController") as! LoginViewController
let window:UIWindow = UIApplication.shared.keyWindow!
let navControl : UINavigationController = window.rootViewController as! UINavigationController
if (!(navControl .isEqual(log)))
{
window.rootViewController = log
}
navControl.popToRootViewController(animated: true)
}
My viewWillAppear-
override func viewWillAppear(_ animated: Bool) {
self.navigationController?.isNavigationBarHidden = false
self.navigationItem.hidesBackButton = true
self.navigationItem.title = "Select Client"
// create a new butto
let button: UIButton = UIButton(type: UIButtonType.custom)
//set image for button
button.setImage(UIImage(named: "logo-icon"), for: UIControlState.normal)
//set frame
button.frame = CGRect(x: 0, y: 0, width: 50, height: 30)
let barButton = UIBarButtonItem(customView: button)
//assign button to navigationbar
self.navigationItem.leftBarButtonItem = barButton
}
Here is my storyboard-
I am using pushViewController to reach to tab bar controller from login view controller
Try below code to change the NavigationController stack :
let oldVCs = self.navigationController?.viewControllers
let newVCs = [UIViewController]()
// Add your root VC in new array of VCs
newVCs.append(oldVCs![0])
// Add your new VC just after your root VC
let log : LoginViewController = self.storyboard?.instantiateViewController(withIdentifier: "LoginViewController") as! LoginViewController
newVCs.append(log)
self.navigationController?.setViewControllers(newVCs , animated: true)
In this the animation will be like pushing a new controller in stack.
If you want to completely leave that stack and create a new one:
let log : LoginViewController = self.storyboard?.instantiateViewController(withIdentifier: "LoginViewController") as! LoginViewController
let loginNavigationController = UINavigationController(rootViewController: log)
self.view.window?.rootViewController = loginNavigationController
Related
I have a UITabBarController which has 4 tabs. I want to show different view controllers for second tab bar item. Depending on the condition I want to show the view controllers for that tab bar item.
I wrote following code :
UITabbarController -
override func tabBar(_ tabBar: UITabBar, didSelect item: UITabBarItem) {
if item.tag == 2 {
if UserDefaults.standard.bool(forKey: "FirstTimeUser") == true {
// let vc1 = storyboard?.instantiateViewController(identifier: "CreateNewProjectViewController") as! CreateNewProjectViewController
// self.navigationController?.pushViewController(vc1, animated: true)
let vc1 = self.storyboard?.instantiateViewController(withIdentifier: "CreateNewProjectViewController") as! CreateNewProjectViewController
let window = UIApplication.shared.windows.first
window?.rootViewController = vc1
tabBarController?.tabBar.isHidden = false
}else {
// let vc2 = storyboard?.instantiateViewController(identifier: "ProjectsViewController") as! ProjectsViewController
// self.navigationController?.pushViewController(vc2, animated: true)
let vc2 = self.storyboard?.instantiateViewController(withIdentifier: "ProjectsViewController") as! ProjectsViewController
let window = UIApplication.shared.windows.first
window?.rootViewController = vc2
tabBarController?.tabBar.isHidden = false
}
}
}
I tried with navigationController but it is showing blank screen.
If I try setting the view controller with "
let vc2 = self.storyboard?.instantiateViewController(withIdentifier: "ProjectsViewController") as! ProjectsViewController
let window = UIApplication.shared.windows.first
window?.rootViewController = vc2
tabBarController?.tabBar.isHidden = false
".
It does not show the tab bar, please help me get it correctly.
Thank you!
I am relatively new to swift and iOS and can't find an answer or any help for my problem that works.
I want to create a navigation controller view when I click on a button in my previous view. My previous view is an on-boarding with a button on the last page. I successfully connected the button to my next view but I am not able to make the view act like a navigation controller. For example, when a navigation bar is displayed, I am not able to add navigation items to it.
Is there a way to set the new view I create by clicking my button in the first view to be the root controller for my navigation view?
A short version of my code:
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
let button = UIButton(frame: CGRect(x: view.frame.width / 2, y: view.frame.height / 2, width: 40, height: 40))
button.backgroundColor = .red
button.tintColor = .white
button.setTitle("Test", for: .normal)
button.addTarget(self, action: #selector(change), for: .touchUpInside)
view.addSubview(button)
}
func change () {
let otherView = SecondViewController()
self.present(otherView, animated: true, completion: nil)
}
}
class SecondViewController: UINavigationController {
override func viewDidLoad() {
super.viewDidLoad()
view.backgroundColor = .yellow
}
}
The SecondViewController gets displayed with a navigation bar but I had problems implementing navigation items, because they weren't shown.
Does the second view controller I present have to be of type UIViewController or UINavigationController?
I am aware that there are easier ways to achieve my goal with the use of the storyboard but in my opinion I understand it better by making my own references via code instead of creating them by dragging them out of the storyboard.
Edit: I have no Objective-C background and learning Swift for about 4 weeks now.
You can add UINavigationController like below :
First you have to create object of SecondViewController,
let myViewController: SecondViewController? = storyboard?.instantiateViewController(withIdentifier: "SecondViewController")
Or
let myViewController: SecondViewController? = SecondViewController(nibName: "SecondViewController", bundle: nil)
Or
let myViewController: SecondViewController? = SecondViewController()
Then add Navigation to SecondViewController
let myNavigationController = UINavigationController(rootViewController: myViewController!)
If you want to present then use :
self.present(myNavigationController, animated: true) {
}
If you want to push then use :
self.navigationController?.pushViewController(myNavigationController, animated: true)
If you want to set as root controller then use :
let appDelegate: AppDelegate = (UIApplication.shared.delegate as? AppDelegate)!
appDelegate.window?.rootViewController = myNavigationController
var objVC: UIViewController? = storyboard.instantiateViewController(withIdentifier: "ViewController")
var aObjNavi = UINavigationController(rootViewController: objVC)
Now, instead of using view controller object use navigation controller object.
here is my code at the appdelegate:
func showMainView()
{
self.window = UIWindow(frame: UIScreen.main.bounds)
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
let secondViewController = storyBoard.instantiateViewController(withIdentifier: "PRODUCT_TABBAR_VC_ID")
let nav = UINavigationController()
nav.pushViewController(secondViewController, animated: true)
self.window!.rootViewController = nav
self.window!.makeKeyAndVisible()
}
simulator output:
basicaly i want when user press back button then came back main page . i mean initial page .
i am trying with this one but it not working at least one answer for me Navigate Back to previous view controller
Note : #matt said it is imposible. so could you tell me please what should i do . i am new to iOS
Update:
when user select Man that time tabviewcontroller two page only showing list of product about Man. so if user want to see Woman then user back to main page to select Woman then he will see Woman tabviewcontroller two page.
The back button is for returning to an earlier view controller pushed onto a UINavigationController. In your code, there is no back button because there is nothing to come back to; secondViewController is the only view controller pushed onto the UINavigationController.
You should create your hierarchy like so:
----> UIViewController
----> UINavigationController ----> UIViewController ----> UITabBarController
----> UIViewController
EDIT: It will look like that:
This way it will be possible to pop UIViewControllers contained in UITabBarController.
Place following lines within didFinishLaunchingWithOptions in AppDelegate.swift
self.window = UIWindow(frame: UIScreen.main.bounds)
let nav = UINavigationController(rootViewController: FirstViewController())
self.window!.rootViewController = nav
self.window!.makeKeyAndVisible()
Create FirstViewController.swift with following:
class FirstViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
let button1 = UIButton(frame: CGRect(x: 0, y: 0, width: 200, height: 200))
button1.setTitle("Man", for: .normal)
button1.tag = 1
self.view.addSubview(button1)
button1.addTarget(self, action: #selector(showAction(sender:)), for: .touchUpInside)
let button2 = UIButton(frame: CGRect(x: 0, y: 250, width: 200, height: 200))
button2.setTitle("Woman", for: .normal)
button2.tag = 2
self.view.addSubview(button2)
button2.addTarget(self, action: #selector(showAction(sender:)), for: .touchUpInside)
}
func showAction(sender: UIButton) {
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
let secondViewController = storyBoard.instantiateViewController(withIdentifier: "PRODUCT_TABBAR_VC_ID")
if (sender.tag == 1) {
// SHOW MAN
} else if (sender.tag == 2) {
// SHOW WOMAN
}
self.navigationController?.pushViewController(secondViewController, animated: true)
}
}
in my app i am using slider so i am using this library.
https://github.com/dekatotoro/SlideMenuControllerSwift
but while using this i am confused in use of navigation bar.
in my appdelegate i write down this code
window = UIWindow(frame: UIScreen.mainScreen().bounds)
storyboard = UIStoryboard(name: "Main", bundle: nil)
let controller123 : MainViewController = (self.storyboard!.instantiateViewControllerWithIdentifier("MainViewController") as? MainViewController)!
let controllerright : drawerViewController = self.storyboard!.instantiateViewControllerWithIdentifier("drawerViewController") as! drawerViewController
let controllerleft : RightViewController = self.storyboard!.instantiateViewControllerWithIdentifier("RightViewController") as! RightViewController
let controller = SlideMenuController (mainViewController: controller123, leftMenuViewController: controllerleft, rightMenuViewController: controllerright)
navigation = UINavigationController(rootViewController: controller)
window?.rootViewController = navigation
window?.makeKeyAndVisible()
and in my mainviewcontroller i add drwer by this code
slideMenuController()?.addRightBarButtonWithImage(UIImage(named: "ic_menu_black_24dp")!)
because i want drawer on right side
and when i select one item from drawer i write this code
let controller123 : RightViewController = (self.storyboard!.instantiateViewControllerWithIdentifier("RightViewController") as? RightViewController)!
let controllerright : drawerViewController = self.storyboard!.instantiateViewControllerWithIdentifier("drawerViewController") as! drawerViewController
let controllerleft : RightViewController = self.storyboard!.instantiateViewControllerWithIdentifier("RightViewController") as! RightViewController
let controller = SlideMenuController (mainViewController: controller123, leftMenuViewController: controllerleft, rightMenuViewController: controllerright)
navigationController?.pushViewController(controller, animated: false)
but now issue is that i can not set navigation bar title or even i can not hide back button so how can i solve that?
Try something like this. Add this line in your viewDidLoad() method of drawerViewController
self.navigationItem.hidesBackButton = true
self.navigationItem.title = "Your Title"
//If you want to create a custom title View then try this
self.navigationItem.titleView = yourview
Hope this will help you.
try this code "override func viewWillAppear(animated: Bool)" in current view controller :
navigationItem.hidesBackButton = true;
navigationItem.title = "Hello";
hope this code will help you.
Try this in viewDidLoad in each ViewController that navigates from Drawer
self.navigationItem.hidesBackButton = true
self.navigationItem.title = "Title"
I'm presenting a Navigation Controller as a popover. First time a do it I can push to another View Controller with any issue. But, second time a present another controller the same way I can't perform a push because the self.navigationController of the presented Controller is nil. This is the piece of code I'm using to present the Controller
func instantiateEditController(view : UIView) -> UINavigationController
{
let popoverContent = self.storyboard?.instantiateViewControllerWithIdentifier("Edit Controller") as MCMEditController
popoverContent.preferredContentSize = CGSizeMake(320, 480)
let navController = MCMBaseNavigationController(rootViewController: popoverContent)
navController.modalPresentationStyle = UIModalPresentationStyle.Popover
navController.navigationBar.tintColor = UIColor.whiteColor()
let popover = navController.popoverPresentationController
popover?.sourceView = view
popover?.sourceRect = CGRectMake(0, 0, view.frame.size.width, view.frame.size.height)
return navController
}
Note: The Navigation Controller is always presented, but just the first time I perform pushes. And this code is for be used in iPad.
Because of the nature of Storyboards and not being able to show that here, I'm not sure where your issue is exactly.
However I successfully setup a project that works using segues. I changed your code to the following:
func instantiateEditController(view : UIView) -> UINavigationController
{
if let popoverContent = self.storyboard?.instantiateViewControllerWithIdentifier("Edit Controller") as? MCMEditController {
popoverContent.preferredContentSize = CGSizeMake(320, 480)
let navController = UINavigationController(rootViewController: popoverContent)
navController.modalPresentationStyle = UIModalPresentationStyle.Popover
navController.navigationBar.tintColor = UIColor.whiteColor()
let popover = navController.popoverPresentationController
popover?.sourceView = view
popover?.sourceRect = CGRectMake(0, 0, view.frame.size.width, view.frame.size.height)
return navController
} else {
return UINavigationController(rootViewController: self) // not recommend to keep this, I'm on Swift 1.2 and this was an easy fix to resolve the errors
}
}
To present this popover I set up this IBAction in my ViewController (sender in my case was a UIButton)
#IBAction func presentPopover(sender: AnyObject) {
if let view = sender as? UIView {
let controller = instantiateEditController(view)
let popover = UIPopoverController(contentViewController: controller)
popover.presentPopoverFromRect(view.frame, inView: self.view, permittedArrowDirections:UIPopoverArrowDirection.Any, animated: true)
}
}
The last thing that could be the issue is make sure your segues are using the segue type "show" for all the segues to make sure the transition between them use the navigation controller push:
Hope this helps!