I am working on a project that is a tabbed application. I have a button on my home page that goes to the second tabbed page but when it loads it gets rid of the tabs at the bottom.
How do I prevent this from happening? my code:
func manageButtonPressed() {
let NVC:SecondViewController = SecondViewController()
self.presentViewController(NVC, animated: true, completion: nil)
}
Replace:
self.presentViewController(NVC, animated: true, completion: nil)
With:
self.tabBarController?.selectedIndex = 1
This is assuming that your home page button is at index 0 on the first tab button of Tab bar, while second VC is on second tab at index 1. You may change the index based on the position of your tab bar.
You want to use showViewController method off of a uinavigationcontroller.
So in the main storyboard of the view where you call the presentViewController you need to add a UINavigationController. Then you can call in the view
self.navigationController.showViewController(NVC, sender: self)
Then it will add the view onto the top of the navigation stack and will be underneath the tab bar
Related
Here I am using swrevealViewController to display side menu and here I am having tab bar for five view controllers and in this every view controller need to have bar button and which will be having action for side menu and here if I select any of the bar buttons in tab bar which will opens side menu and will have access to another view controllers in side menu after going to any view controller then when I press the back button action was working fine and when I move to another to another view controller in tab bar after coming back from view controller then also it works fine whenever I move to previous tab bar view controller and click side menu view controllers then the view controller was moving in the previous navigation controller and in the navigation frontNVC the last accessed new view controller was saving in navigation stack can anyone help me how to resolve this ?
here is the code which used for moving side menu
if cell.titleCellLabel.text! == "Account"
{
var controller: UIViewController? = nil
let storyboard = UIStoryboard(name: "Main", bundle: nil)
controller = storyboard.instantiateViewController(withIdentifier: controllers[indexPath.row])
print(frontNVC?.viewControllers)
if controller != nil
{
// Prevent stacking the same controller multiple times
print(frontNVC)
_ = frontNVC?.popViewController(animated: false)
frontNVC?.viewControllers.removeAll()
// Prevent pushing twice FrontTableViewController
if !(controller is SWRevealViewController) {
// Show the controller with the front view controller's navigation controller
print(frontNVC)
frontNVC!.pushViewController(controller!, animated: false)
}
// Set front view controller's position to left
revealViewController().setFrontViewPosition(.left, animated: true)
}
}
here is the code used for back button action used in side menu view controllers
#IBAction func backButtonAction(_ sender: Any) {
let nc = revealViewController().rearViewController as? UINavigationController
let frontNVC = (nc?.topViewController as? LeftSideViewController)?.frontNVC
_ = frontNVC?.popViewController(animated: true)
}
Here is my story board layout image shown below
I have two view controllers, I added navigation bar to second view controller with two bar button items Back and Item as shown below
But when I do a push segue from first view controller, it is replaced by navigation item <Category, which is title of navigation item in my first view controller as shown below
How do I keep my navigation bar intact avoiding the default navigation item <Category, which is being added automatically while maintaining push segue functionality.
I tried to do maually without using stoyboard as follows
#IBAction func plusAction(_ sender: Any) {
let secondViewController = self.storyboard?.instantiateViewController(withIdentifier: "SVC") as? SecondViewController
self.navigationController?.pushViewController(secondViewController!, animated: true)
}
but it still doesnt work.
You want to display two bar button items Back and Item by added UINavigationBar to second view controller, you are doing it in the wrong way!!!
In your storyboard, drag a UINavigationItem to your second ViewController.
If the UINavigationItem does not display on your storyboard, you must select second view controller, choose Opaque Navigation Bar or Translucent Navigation Bar (not important)
After that, you can drag UIBarButtonItem where you want on your ViewController
Have you tried changing the kind of segue through segue inspector (click the particular segue and check its attributes in the inspector) like this,
But you should know each one of it is not similar, has it's own definition in how it appears - check https://developer.apple.com/library/content/featuredarticles/ViewControllerPGforiPhoneOS/UsingSegues.html
Also, alternatively using code,
if let viewController = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "storyboardId") as? TargetViewController {
self.present(viewController, animated: false, completion: nil)
}
I have created a simple tab bar with three views in storyboard. The tab bar works well, but when I try to show another view controller from a button within a tab, the new view is placed over the whole screen and also over the tab bar.
This is how I present the view so far when a button is pressed:
#IBAction func buttonPressed(_ sender: UIButton) {
let newVC = self.storyboard?.instantiateViewController(withIdentifier: "extraVC")
self.present(newVC!, animated: true, completion: nil)
}
The other idea I had was this:
self.tabBarController?.present(vc!, animated: true, completion: nil)
But this didn't work either.
So how can I present another view controller within the tab bar (so that the bottom bar is still shown)?
When you present a view controller modally, its presentation style will be "Full Screen" by default. What you want to do is have it do in this case is just cover part of the screen (the part where the presenting view controller is drawn.
One way to accomplish this is to:
Set the modalPresentationStyle for the presented view controller to be .currentContext or .overCurrentContext
In the view controller that will be presenting the modal, set its definesContext property to true.
These steps can be done either in Interface Builder by setting attributes on the segue and the view controller, or you can modify your code to include the following:
#IBAction func buttonPressed(_ sender: UIButton) {
let newVC = self.storyboard?.instantiateViewController(withIdentifier: "extraVC")
self.definesPresentationContext = true
newVC?.modalPresentationStyle = .overCurrentContext
self.present(newVC!, animated: true, completion: nil)
}
What this combination of properties does is:
Indicate for the presented view controller that you want it to be presented in a non-full screen context (some specific section of the screen)
Indicate that the presenting view controller is in the section of the screen / the context you want the modal to be drawn according to.
More details can be found in the Apple Documentation
When you are using present method, the ViewController is presented modally and covers your UITabBarConntroller. Instead of showing your view modally you can embed every first view controller in your TabBar into UINavigationController and then use method pushViewController to push it onto stack. You will have your TabBar visible and nice looking animation for free.
In Xcode, I created a new project using the Tabbed App template to illustrate the solution above. This will create a project with a tabbar controller and two view controllers. I added a button with the title "view page" to the first view controller and embedded a navigation controller from the storyboard.
The storyboard will look like this after making the above changes:
In the FirstViewController.swift file, I created an IBAction for the button with the following code that will create another view controller called DetailViewController, with the title Favorites and a background color of orange. I used the navigation controller to present it by pushing it onto the navigation controller stack.
#IBAction func viewPageButtonTapped(_ sender: UIButton) {
print("viewPageButtonTapped")
let pinkViewController = DetailViewController()
pinkViewController.title = "Favorites"
pinkViewController.view.backgroundColor = UIColor.orange
navigationController?.pushViewController(pinkViewController, animated: true)
}
When I run the project on the simulator, I got the desired result. Hope this helps give you some ideas.
In your viewController do:
self.tabBarController?.present(nextViewController, animated: true/false, completion: {})
I'm opening a navigation controller from a button click of my main view controller.
I programatically created a left bar button item on the navigation controller which I want to dismiss the nav controller and go back to my main controller.
I'm essentially going back on the root view controller of the navigation controller.
I've tried
navigationController?.dismissViewControllerAnimated(true, completion: nil)
and
self.dismissViewControllerAnimated(true, completion: nil)
and get an NSException on both.
Please advise.
Swift 3:
self.view.window!.rootViewController?.dismiss(animated: false, completion: nil)
It will dismiss all the presented view controllers and remain root view controller.
If you are pushing your ViewController, you should use pop to remove that ViewController from Navigation Stack and land on the previous ViewController. Try this...
self.navigationController?.popViewControllerAnimated(true);
SWIFT 3
_ = navigationController?.popViewController(animated: true);
dismissViewController works when you are showing a viewController using presentViewController, that maybe the root view controller of a navigation stack, or a stand alone view controller.
self.presentingViewController?.presentingViewController?.dismissViewControllerAnimated(true, completion: nil)
Try this :)
A year later.. The exception indicates that there is something wrong with the selector that you provide to the action param, when adding the left bar button.
Something like this should work:
creating bar button item:
let backBarButton = UIBarButtonItem.init(barButtonSystemItem: UIBarButtonSystemItem.stop, target: self, action: #selector(dismissView))
dismiss root view controller:
func dismissView() {
self.dismiss(animated: true, completion: nil)
}
Apple Dev already provides very simple code which is
self.navigationController?.popToRootViewController(animated: false)
I'm new to swift and IOS development. I'm working on a tabbed application(3 views). For example, FirstView, SecondView and ThirdView. FirstView has a button that opens a addNewSession view and the addNewSession view has a Back button that back to the FirstView. The problem is Tab bar disappears after back from the addNewSession view
FirstView to addNewSession view.
#IBAction func toAddNew(sender: AnyObject) {
let addNewSession = self.storyboard?.instantiateViewControllerWithIdentifier("addNewSession") as addNew
self.presentViewController(addNewSession, animated: true, completion: nil)
}
addNewSession view to FirstView
#IBAction func backToPrev(sender: AnyObject) {
println("test1")
let FirstView = self.storyboard?.instantiateViewControllerWithIdentifier("FirstView") as FirstViewController
self.presentViewController(FirstView, animated: true, completion: nil)
}
The problem is your backToPrev method is instantiating a new FirstViewController, which is not the same instance you came from. You are not really going back to the original one, you are showing a new one. This is not what you want.
The proper way to do this is to embed the FirstViewController in a navigation controller, then push the addNew controller onto it. When you use a nav controller, you get the Back behavior for free.
Hopefully you are using a storyboard? Select your FirstViewController, go to the Editor menu and choose Embed in Navigation Controller.
In your toAddNew, instead of presentViewController use self.navigationController.pushViewController to push your addNew controller.
There's an even easier way to do this last step, using segues. You control drag in the storyboard from your button in FirstViewController to the addNew controller and create a Show segue. This will automatically show your addNew controller when the button is touched. With this approach, you will want to remove your toAddNew IBAction and the connection since it's redundant.