Push TabBarController to a View - objective-c

How can i push a TabBarController to a View?
The App is View-Based. In the App I have a XIB with a TabBarController and I want to push the TabBar to the display. I have done everything, and now I don't know what I'm doing wrong.
Here is the code that should push the TabBarController:
- (void)showTabBar {
TabBar *tbc = [[TabBar alloc] initWithNibName:#"TabBar" bundle:nil];
[self presentModalViewController:tbc animated:YES];
[tbc release];
}
At this moment there is an empty view in the XIB. So the display is white when I run this code. There is also the TabBarController, which I want to see on the display.
Thanks for your help.
UPDATE:
I should say that these are two different classes. The class where the function "showTabBar" is based should push the TabBarController. The second class is TabBar. TabBar is the delegate of the TabBarController.
So I have modified the answer like this, but I have tried both:
[self presentModalViewController:tbc.tabBarController.view animated:YES];
The error now looks like this:
Incompatible Objective-C types 'struct UIView *', expected 'struct UIViewController *' when passing argument 1 of 'presentModalViewController:animated:' from distinct Objective-C type
UPDATE:
Hey the error has gone away. Cool. ;)
But the app is terminating. I've seen this behavior before, but I didn't know what to do.
The debugger console says this:
2011-01-27 15:49:32.629 Touch[3657:207] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Application tried to present a nil modal view controller on target <StartUp: 0x9300f20>.'

Because the UITabBarController class inherits from the UIViewController class, tab bar controllers have their own view that is accessible through the view property. When deploying a tab bar interface, you must install this view as the root of your window. Unlike other view controllers, a tab bar interface should never be installed as a child of another view controller.
http://developer.apple.com/library/ios/#documentation/uikit/reference/UITabBarController_Class/Reference/Reference.html
What this mean is, this is not "allowed" and Apple can or may in the future reject your application. UITabBarController is intended to be added to the root view(window) in your application delegate. If you want a tabbar to be pushed on later you need to use the UIToolBar with e.g. uisegmentedcontrol or the toolbar buttons.
Even though some apps does this(e.g Wordpress app) you will later find out that you will run onto some issues in the console when presenting viewcontrollers modally.(A warning will be given).

Related

Scene is unreachable due to lack of entry points... Custom Button

I'm new to programming on xCode. I've made a login screen in a snapchat format. Currently, I started with two view controllers one for login and then signup but I changed it so I start with an intial view controller that has two custom buttons I made. View the picture. I want it to be that so when you clean the login button it takes you to the login screen and when you click the sign up button it takes you to the sign up screen.
I'm not sure what I'm doing wrong. I want![enter image description here][1]
My app delegate has the following:
http://i.stack.imgur.com/8fWT4.png
http://i.stack.imgur.com/b9mfN.png
I just don't understand as to why I keep getting the following error: Scene is unreachable due to lack of entry points and does not have an identifier for runtime access via -instantiateViewControllerWithIdentifier:.
Unless your segueing to the view in question, you would need to give it a storyboard identifier to connect the nib with the related class. Go into the storyboard and ensure you've set the class and storyboard id. If you're segueing to the class, ensure you give your segue an identifier. But if not, you can then do something like:
YourViewController *vc = (YourViewController*)[self.storyboard instantiateViewControllerWithIndentifier:#"YourStoryboardIdentifier"];
[self presentViewController:vc animated:YES completion:^{}];// Or however you want to present it. ie pushing onto the navigation stack
You can use this code:
WaitingRoomVC *ivc=[self.storyboard instantiateViewControllerWithIdentifier:#"waiting"];
[self.navigationController pushViewController:ivc animated:YES];

How to access a IBAction from a SKView?

I am making a little game with few mini games. On the 1.VC I have UIButtons inside a scrollView to choose the mini game. When the miniGame is loaded (a UIVC) it loads a SKView with the chosen SKScene game.
This is my App view Setup:
1.
UIViewController -> 1.1. ScrollView -> 1.1.1. UIButton -> 1.1.1.1. UIViewController -> 1.1.1.1.1. SKView -> 1.1.1.1.1.1. SKScene (the 1. mini game).
In the 1.1.1.1. VC I have a backButton (UIButton) which returns me back to the 1.VC.
Since I added the backButton in 1.1.1.1.VC I can always return at any moment in the first mini game to 1.VC.
PROBLEM:
The only way to go back from 1.1.1.1. (or any deeper) to 1. is by clicking the UIButton. I want to go back programmatically. When the endGameVC (a SKScene) is presented I want it to "seque" or "present" back to the 1.VC automatically (using a NSTimer).
So far I have tried:
1.
[self.view removeFromSuperview];
Result:
Black Screen - cant do anything from here
2.
[self.view presentScene:nil];
Result:Gray screen - I removed the skview and could go back with the button click
3.
[self.view removeFromSuperview];
[self.view addSubview:[[WBMGamesDataManager sharedInstance] tempy]];
Result:
-[WBMMainVC superview]: unrecognized selector sent to instance 0x9ac4c30
2014-04-04 11:54:06.317 KinderApp[1940:60b] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[WBMMainVC superview]: unrecognized selector sent to instance 0x9ac4c30'
... other stuff that I tried didn't get me anywhere.
Any idea or solution is welcome. If you know what I am doing wrong, or if the whole approach is fishy I am open for comments/critics. Thank you :).
I am assuming you are using segues on way of doing this is by popping the current view controller
[self.navigationController popViewControllerAnimated:YES];
but for this to work you need to call it from the UIViewController that hosts the SKView so depending on where you need to go back programatically, pass a reference of the UIViewController to that desired view, and create a method that will simply invoke the above line
/////in UIViewController
-(void)popIt{
[self.navigationController popViewControllerAnimated:YES];
}
////in the view where you want to simulate the back method
[referenceToVC popIt];
hope this helps, feel free to ask if you anything is unclear.
Found the solution:
In my:
#implementation MiniGameConcept
which is a SKScene I have put the following line of code at the place where I used my timer/counter where I needed the game to end:
[self.view.window.rootViewController dismissViewControllerAnimated:YES completion:nil];
This leads me to the 1. VC which is my main screen where the player can choose the mini game set.
It worked for me. I also found a way to go one step back, but this basically gets me to the rootVC. Console output with NSLog shows the VC name.

Container view is expected to be populated at this point

i have a simple ios implementation. There is a tableviewcontroller embedded in a navigationcontroller and a qlviewcontroller in this implementation, navigationcontroller is embedded in a tabbarcontroller too.
Actual tab lists a lot of image files, if a cell is selected in the tableviewcontroller, a qlpreviewcontroller will be instantiated and image file will be shown. another tab shows only settings of app.
i have subclassed the qlpreviewcontroller. The instance of this subclass will be created with the following code part;
XYQLPreviewController *qlpvc = [[XYQLPreviewController alloc] init];
qlpvc.hidesBottomBarWhenPushed = YES;
[self.navigationController pushViewController:qlpvc animated:YES];
i want to hide tabbar in the preview controller so that there is enough place to preview.
these all work very well with ios 6 and below but with ios 7 i have the following problems;
Back button of navigation bar in qlpreviewcontroller doesnt respond, its not clickable.
if i back navigate with this new cool slide transition of ios 7, ta ta my tabbar got lost, i see only a white layer at the tabbar not my cool tabbar.
i see the following log message in log screen,if i select an image file and instantiate the subclass of previewcontroller.
"Container view is expected to be populated at this point"
what a problem can it be , i have no idea.
Please help.
PS:i have only a xib file not the storyboard.
If you want to hide the tab bar, I would say your best bet is to present the preview controller as a modal instead of pushing it onto the stack. Then when the user closes it (instead of hits back), it will bring them back to the tab bar view.
[self.navigationController presentViewController:qlpvc animated:YES completion:nil];

How to present a modal view controller outside of a view controller using presentModalViewController:animated?

Let's say you have an application in which you know for sure that there's always a UINavigationController displayed, and that I need to display another view controller modally from outside this controller (for example : because I use the Command pattern and I don't want to give a reference to a view controller to it).
Is there a safe way to get the "root" navigation controller, and call its presentModalViewController:animated method ?
I tried to use [UIApplication sharedApplication].keyWindow.rootViewController but I figured out that it was nil during an alert.
Are you using a storyboard or separate xibs?
If you're using separate xibs then you will be setting up the UINavigationController in applicationDidFinishLaunching.
You can make the navigation controller a property of the app delegate.
Then you can access the UINavigationController from anywhere by getting the singleton app delegate and getting the navigation controller property from it.

How to get Push Segues, Containment controllers, and storyboards to work together

I'm building an app with the following page flows (it's a big complex so I will try to be as clear as possible):
Login -> MainViewController
Now, MainViewController uses controller containment in iOS 5 to host two views/controllers:
MainViewController
/ \
FirstController SecondController --> DetailsController
From SecondController, I want to segue to a separate View Controller (you can think of it as "details" if you think of MainViewController as "master").
From SecondController, I can segue using "modal" segue to DetailsController. But when I "pop" back, iOS reloads MainViewController. I don't want it to do that.
If I use "push" segue, I get a runtime error saying there are no UINavigationControllers on the stack. Fine.
So what I tried next was I tried to make MainViewController the root controller of a new UINavigationController:
Login --> UINavigationController --> DetailsController (but "initiated" by Second)
|
MainViewController
/ \
FirstController SecondController
And then from SecondController, I tell UINavigationController to perform the "push" segue. But I still get the same runtime error - no UINavigationController found.
I must not understand how the navigation stack works - it's probably not checking the caller, because I'm sure I'm calling performSegueWithIdentifier: from the UINavigationController.
I was using the "Your second iOS app" as a guide, and they prescribe this method (modal segue). But I really do not want to re-load the MainViewController if at all possible (it's doing some expensive things). I would prefer iOS to "cache" my view/controller/data. I could of course write code to cache my data when I load the details page, and reload the cache instead of re-computing the data when I pop back, but I was hoping the "push" segue would do this for me automatically.
If you guys have any ideas, I would be grateful. Thank you.
in order for the push to work, you need to select the view in IB that will make the call and embed it in a navigation controller from the editor menu.
editor > embed in> navigation controller