I need to assign data source to a view controller segued by press a button in appdelegate.swift. How can I find the view controller by a segue identifier. I know I can find in a navigation controller by
let navigationController = window!.rootViewController as! UINavigationController
let controller = navigationController.viewControllers[0] as! ListViewController
like this. Is there a way to find a view controller when only the segue is connected with the previous view controller?
In other words, how to identify any vc in a project? Is storyboard ID used for this?
let viewController = segue.destinationViewController as! ListViewController
Related
I have inherited a storyboard that launched directly to a UITabBarController. In the AppDelegate.swift file in the didFinishLaunchingWithOptions method there is the following code:
//let loginScreen = window!.rootViewController
let tabController = window!.rootViewController as! UITabBarController
let navController = tabController.viewControllers![0] as! UINavigationController
let salaryController = navController.topViewController as! SalaryTableViewController
let nav2Controller = tabController.viewControllers![1] as! UINavigationController
let employeeController = nav2Controller.topViewController as! EmployeeTableViewController
I am trying to change the code so the login screen is the rootViewController but when I remove the rootViewController from the tabController assignment I get an error that casting a UITableViewController to UITabBarController always fails. Does anyone know why casting a UITableViewController to a UITabBarController always fails unless the UITableViewController is the rootViewController? Is there a way to change the launch screen to a different controller without changing the rootViewController assignment? Here is the storyboard for visual:
enter image description here
UITabBarController is a subclass of UIViewController. You cannot cast superclass to subclass. (Viceversa is possible)
To implement your idea, you should remove initialing your root view controller from storyboard and do it programmatically. Because now, the Xcode think your initial view controller is UITabBarController and the only way is that you instantiate your class programmatically and then make it root view controller.
Why don't you present your login VC as a modal view controller? That way you didn't need to change anything on the view hierarchy.
How to dismiss any View Controller without using Storyboard ? and do I have to use UINavigationController to achieve this ? if not how then ?
if someone is still struggling to dissmiss on swipe (left,right,bottom,top)
i came across a very elegant and decent cocapod panslip
with a very simple usage
just call this method in viewDidLoad()
For viewController embedded in navigation Controller
let viewControllerVC = self.navigationController
viewControllerVC!.ps.enable(slipDirection: .leftToRight){
//anything you want to do after dissming
}
For Simple View Controller
let viewControllerVC = self
viewControllerVC!.ps.enable(slipDirection: .leftToRight){
//anything you want to do after dissming
}
For TableView embedded in View Controller
let viewControllerVC = self.YourTableview.parentContainerViewController()
viewControllerVC!.ps.enable(slipDirection: .leftToRight){
//anything you want to do after dissminn
}
The way to dismiss a view controller is to call a dismiss method on the presenting view controller. If you presented your child controller from a parent by calling self.present(_:animated:) then you can call self.dismiss(animated:). If you used a navigationController and called navigationController.push(_:animated:) then you need to tell the navigation controller to dismiss with navigationController.popViewController(animated:)
Method names might not be exact, but you should be able to figure it our with autocomplete.
If you want to swipe right is not a dismiss, but I think that what you want it to embed the UIViewController inside a UINavigationController.
For example:
if let vc = UIStoryboard(name: "YourStoryboard", bundle: nil).instantiateViewController(withIdentifier: "YourViewController") as? YourViewController {
let navigation = UINavigationController(rootViewController: vc)
navigationController?.pushViewController(vc, animated: true)
}
I can swap from one UIViewController to another within a UITabBarController using tabBarController?.selectedIndex = targetIndex. I would like to know how to trigger a segue after the switch.
I have tried doing if let vc = tabBarController?.viewControllers?[0] as MyViewController {} and calling vc.performSegue() but it errors out, complaining that it's a UINavigationController. (I couldn't even get vc.prepare() to work but I can't work out how to create a UIStoryBoardSegue, which it requires as the first argument, from scratch using the segue identifier.) I think this is because all of my UIViewControllers in the UITabBarController are within Navigation Controllers.
How do I switch from index 0 to 1 in the tab bar controller, and then trigger a segue in the view controller embedded in the navigation controller? Note, I need to pass in a copy of the calling object (my UIViewController) or a payload for contextual purposes to the UIViewController being segued to.
Well like you said the viewController which is presented at the index is a UINavigationController. You should get the rootViewController of the UINavigationController and perform the Segue on the RootViewController.
Below code should work:
self.tabBarController?.selectedIndex = 1
guard let vc = self.tabBarController?.viewControllers?[1] as? UINavigationController else {
return
}
guard let rootVC = vc.viewControllers.first as? SecondViewController else {
return
}
rootVC.vc = self
rootVC.performSegue(withIdentifier: "test", sender: self)
I have 2 view controller ,and I disabled the initial view controller of first view controller ,and enabled the second view controller,but when start the project,the initial view controller is still the first view controller ,what should I do? Thanks!
Tap the second view controller, and select "Is initial View Controller" in Attributes inspector.
Alternatively you can do this with code too.
In your AppDelegate class's didFinishLaunchingWithOptions method you can write
let storyBoard = UIStoryboard(name: "Main", bundle: nil)
let secondVC = storyBoard.instantiateViewControllerWithIdentifier("SecondViewController") as! SecondViewController
self.window?.rootViewController = secondVC
Edit Swift 3.0
let storyBoard = UIStoryboard(name: "Main", bundle: nil)
let secondVC = storyBoard.instantiateViewController(withIdentifier: "SecondViewController") as! SecondViewController
self.window?.rootViewController = secondVC
Assuming that your storyboard name is Main.Storyboard and your SecondViewController Storyboard ID and Restoration ID is also set in Identity Inspector and use Storyboard ID is checked.
If you are starter like me ( both iOS and OSX mechine ) and you wanted to change the entry point within same storyboard, then,
-> long press on the entry point arrow.
-> drag it to the view controller you wish to make the starting point, the arrow will now move to your new screen.
I am trying to add both a Navigation Bar Controller and a Tab Bar Controller to my application.
"First View Controller" is my first View Controller at index 0.
However, I cannot embed a Navigation Controller into First VC without incurring an error:
Could not cast value of type 'UINavigationController' (0x1a0a21fb8) to 'project.FirstViewController' (0x1000ae228).
Here's the code in my App Delegate:
let TabBarController = self.window!.rootViewController as! UITabBarController
let controller = TabBarController.viewControllers![0] as! FirstViewController
controller.managedObjectContext = self.managedObjectContext
I realize that there is no Navigation Controller object in my code. Should the Tab Bar Controller NOT be behind the login page?
Obviously I plan on using both a Navigation Controller and Tab Bar Controller post-login.
But how do I instantiate a Navigation Controller to have a Navigation Bar in my First VC?
Thank you
Your Storyboard should look like this image
add navigation controller
this may help
You are actually almost there. From what I can read, the error states that it is unable to cast FirstViewController into UINavigationController. Assuming that your storyboard looks like the one in #PKT's answer, your codes should look like this.
let TabBarController = self.window!.rootViewController as! UITabBarController
let navigationController = TabBarController.viewControllers![0] as! UINavigationController
let controller = navigationController.topViewController as! FirstViewController
controller.managedObjectContext = self.managedObjectContext
The NavigationController is important if you want to NavigationBar. though.