I have a view controller reference to a storyboard of a given identifier. I'm adding a bunch of buttons to it, then trying to display it via a segue.
My problem is that when the segue fires, it creates a difference instance of the view controller with the same segue identifier, and thus it's blank.
What's the best practice to addSubView() to a storyboard, then getting that SAME storyboard object to display?
CLARIFICATION
Here's the flow I'm using:
Central VC -> Create SubVC using centralized Storyboard Object -> Adding SubViews to that SubVC in a factory class -> Queue Segue from SubVC back to the Central VC for segue using its identifier -> [it creates a NEW VC without my additions]
If you're using segues, then the Storyboard creates the destination viewController. If you want to customize the destination viewController, then you do that in prepareForSegue.
You can instantiate a view by code, and pushing in to you navigation controller, it's a clean approach and dont mess the Storyboard with unnecessary segues.
Just instantiate the next view (you must first give this view an StoryBoard ID), call it by code, and push it in the navigation controller.
Objective-C
UIStoryboard* storyboard = [UIStoryboard storyboardWithName:#"storyBoard_Name" bundle:nil];
UIViewController* controller = [storyboard instantiateViewControllerWithIdentifier:#"ViewController_ID"];
[self.navigationController pushViewController:viewControllerName animated:YES];
Swift
let storyboard = UIStoryboard(name: "storyBoard_Name", bundle: nil)
let vc = storyboard.instantiateViewControllerWithIdentifier("ViewController_ID") as! UIViewController
self.presentViewController(vc, animated: true, completion: nil)
Related
I have a view controller (PhotoViewController) which has a child view controller (CameraViewController). In CameraViewController, there is a button that sets off a chain of segueing through other programmatically created view controllers. On the last of these view controllers, I want to unwind to the original PhotoViewController. All examples I have found require you to have view controllers in the storyboard, which I don't have. How can I do this?
You have not understood what an unwind segue is. It is merely a way of reversing the calls that created the current view controller and got it into the view controller hierarchy, in the special case where you want to trigger this through a segue in a storyboard.
For example, if you (or the storyboard) called pushViewController (for a pushed view controller), an unwind segue is just a way of calling popViewController.
Or, if you called (or the storyboard) called present (for a modally presented view controller), an unwind segue is just a way of calling dismiss.
If you don't have your view controllers in a storyboard, you don't need an unwind segue; you just do one of those two things, directly, in code.
Remember, we all got along for years just fine without unwind segues. In fact, we all got along for years without storyboards! And so can you.
If your original PhotoViewController is created on a storyboard and you want to segue back to it from a programmatically made VC you have present it rather than unwinding because unwindSegues are for storyboards only.
To present your PhotoViewController here is one of the ways to do so.
func presentPhotoViewController() {
let storyboard = UIStoryboard(name: "YourStoryBoardName", bundle: nil)
if let photoViewController = storyboard.instantiateViewController(withIdentifier: "PhotoViewControllerUniqueId") as? PhotoViewController {
// Pass any data you have (Optional)
self.present(photoViewController, animated: true, completion: nil)
// If your PhotoViewController is embeded in a navigation Controller do the following.
//let navController = UINavigationController(rootViewController: photoViewController)
//self.present(navController, animated: true, completion: nil)
}
}
I have designed in a storyboard a login/password Controller. The textfields are linked to the controller with the famous ctrl+drag.
Is there a way to reuse storyboard + controller somewhere else in the App. For instance I want to give the user the ability to change his login from a setting menu and I do not want to have to create a new class and to clone its storyboard representation.
What is the best practice in this case to reuse what I have already done?
This is what view controller's identifiers are used for.
In your storyboard, set an identifier for LoginViewController, after that, you'll only need to present your LoginViewController or push it to your navigation stack. Your code should look something like this:
let storyboard = UIStoryboard(name: "yourStoryboardName", bundle: nil)
let loginViewController = storyboard.instantiateViewController(withIdentifier: "loginViewController") as! LoginViewController
// If you are in a navigation controller:
self.navigationController?.pushViewController(loginViewController, animated: true)
// If you just want to present a new view:
self.present(loginViewController, animated: true, completion: nil)
This way, you'll push/present a new view controller that has the layout specified in storyboard for the identifier "loginViewController".
All text fields and buttons in that view controller should be handled in the class specified for the view controller which, in your case, should be LoginViewController.
Ofcourse you can. I'm using this code.
Try:
OBJECTIVE-C:
UIStoryboard *storyBoard = [UIStoryboard storyboardWithName:storyBoardName bundle:nil];
UIViewController *upcomingViewController = [storyBoard instantiateViewControllerWithIdentifier: storyBoardID];
UINavigationController *controller = [[UINavigationController alloc] initWithRootViewController:upcomingViewController];
I am new in swift.I want to move one screen to another but problem is when I go to another screen,old screen overrides in new screen.
here is my code
dispatch_async(dispatch_get_main_queue()) {
let appsDelegate = UIApplication.sharedApplication().delegate
appsDelegate?.window!!.rootViewController = nil
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
let nextViewController = storyBoard.instantiateViewControllerWithIdentifier("launcherEntry") as! UINavigationController
appsDelegate?.window!!.rootViewController = nextViewController
}
If you use UINavigationController, you should push the second view(screen) onto the first one. Check out the offical guide.
According to your code old screen overrides because you have not a push a UIViewController into navigation controller.
Here you destroyee the exiting controller then set a new controller. So that previos controller is move from the memory.
Please show Apple docs for the UINavigationController.
Update:
Please use following code for set a root view controller then you can push view controller easily.
let navigationController:UINavigationController = storyboard.instantiateInitialViewController() as! UINavigationController
let rootViewController:UIViewController = storyboard.instantiateViewControllerWithIdentifier("ID_LoginVC") as! LoginVC
navigationController.viewControllers = [rootViewController]
self.window?.rootViewController = navigationController
As you are new , i will explain what will happen when your code will be executed.
App delegate will hold the current instance of our application. Setting root view controller is setting Main view controller of your application.
SO basically your code will replace the previous view controller with next one.
Now what you have to do,
We have Navigation controller to manage our navigation stack, that allow us to go back from where have initiated.
If you are Using storyboard , add your view controller into NavigationController, if you already know then ignore or follow this
SELECT your first view controller GOTO Editor in Xcode menu > Select EMBED IN option > NAVIGATION CONTROLLER. this will add your first view into navigation controller.
Now when you want to display next view controller, There are two ways to do so,
1)Using segue from Storyboard
Right click from view/button from where you want to show next view.
drag it to the next view controller and release the right click.
Select push
2)Programatically
you don't have to set root view controller, just push the next view controller in navigation controller you have
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
let nextViewController = storyBoard.instantiateViewControllerWithIdentifier("launcherEntry") as! UINavigationController
Above line will intimate the textview controller, now we have to push this view controller, we can achieve this with
self.navigationController?.pushViewController(nextViewController, animated: true)
I want to switch between different view controllers, here is my codes,
let sb = UIStoryboard(name:"Main", bundle: nil)
let vc = sb.instantiateViewControllerWithIdentifier("tabBarController") as ViewController
self.presentViewController(vc, animated: true, completion: nil)
'tabBarController' is the storyboad ID I had wrote in the identifier inspector.but I got some error at this line.
let vc = sb.instantiateViewControllerWithIdentifier("tabBarController") as ViewController
and here is the screenshot,
What's the problem?
And I have another question, here is the screenshot after the sb was initialized, the storyboardFileName is "Main.storyboardc", shouldn't it be "Main.storyboard"?
Thanks very much!!!!
The error is saying that the view controller returned by instantiateViewControllerWithIdentifier cannot be cast to a ViewController.
This is probably because you did not set the Custom Class property of your view controller in the storyboard to ViewController.
Go to your storyboard, select your view controller, then open the Identity inspector and look for the Custom Class property. Set it to ViewController and tab out of the field to make sure it takes. Then run again.
I'm having trouble with a simple Xamarin Studio Storyboards concept. See screenshots below for visuals and see the downloadable source code here.
Let's say I have a NavigationController with MainViewController on it. This is visible in my storyboard. I want a button which, when pressed, brings up a new NavigationController with RedViewController. I also want RedViewController on the same storyboard as the MainViewController. In this project, I tried to do that but for some reason when I do a:
var myStoryboard = AppDelegate.Storyboard;
// Instatiating View Controller with Storyboard ID 'StuffViewController'
RedViewController = myStoryboard.InstantiateViewController ("RedViewController") as RedViewController;
RedViewController.ModalTransitionStyle = UIModalTransitionStyle.CoverVertical;
this.PresentViewController(RedViewController, true, null);
the RedViewController doesn't have it's Navigation controller with it. When presented RedViewController's Navigation Controller is null! What am I doing wrong there?
Now when I created a NavigationController & BlueViewController in a totally seperate storyboard it works fine. When I press the Blue Button it goes to the BlueViewController and correctly shows it's NavigationController. Why is this one working but the other one not? The only difference that I can see is that they are on separate Storyboards.
UIStoryboard storyBoard = UIStoryboard.FromName ("BlueStoryboard", null);
UIViewController controller = storyBoard.InstantiateInitialViewController () as UIViewController;
controller.ModalTransitionStyle = UIModalTransitionStyle.CoverVertical;
this.PresentViewController (controller, true, null);
ViewController that can present a new NavigationController & ViewController ViewController called "Red" with a navigation bar
When you instantiate your new view controller you need to instantiate the UINavigationController, not the RedViewController.
In the case of your 'blue' code you instantiate the initialViewController - which is the navigation controller that contains the Blue controller.
You want
RedViewNavigationController = myStoryboard.InstantiateViewController ("RedViewNavigationController") as UINavigationController;
where 'RedViewNavigationController' is the identifier for the navigation controller that the Red View Controller is embedded in.
If you want to present the red controller with its navigation controller, you should instantiate the navigation controller (which, in turn, will instantiate the red controller), and present it.