PushViewController and Popview Controller on uinavigation bar from initial view controller - iphone

I am new to iphone. I have a small confusion on uinavigation controllers that is I want a navigation bar in initial view controller in that view controller there is a button in navigation bar when we click on that it will push the another view controller(second view controller) from that there is a back button if we click on that i want to pop that view controller and come back to initial view controller.If any body know this please help me .If you explain with some code it will better to understand us.
The following code i have written so,far here present modal view controller and dismiss model view controller is working but pushview controller and popview controller is not working
In appDelegate i have written like this
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
//create a window
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
//biblePlayerController is an instance of BiblePlayerViewController class and then set the biblePlayerController as a rootViewController to the window
self.biblePlayerController = [[BiblePlayerViewController alloc] initWithNibName:#"BiblePlayerViewController" bundle:nil];
navigationController = [[UINavigationController alloc]initWithRootViewController:self.biblePlayerController];
// self.window.rootViewController = self.biblePlayerController;
[self.window addSubview:navigationController.view];
//make the window visible
[self.window makeKeyAndVisible];
return YES;
}
//In initial View controller there is a navigation on that there is a download button code for that is
//BiblePlayerViewController.m
UIBarButtonItem *downloadButton = [[UIBarButtonItem alloc] initWithTitle:#"Download" style:UIBarButtonItemStylePlain target:self action:#selector(gotoProgressViewController:)];
self.navigationItem.rightBarButtonItem = downloadButton;
- (IBAction)gotoProgressViewController:(id)sender {
#try {
//ShowProgressViewCont is initialized with the nibName
showProgressViewController = [[ShowProgressViewCont alloc]initWithNibName:#"ShowProgressViewCont" bundle:nil];
//UINavigationController is initialized with the rootViewController showProgressViewController
navigationController = [[UINavigationController alloc]initWithRootViewController:showProgressViewController];
//The transition style of the navigationController is set to UIModalTransitionStyleCrossDissolve
navigationController.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;
//Presents a modal view managed by the given view controller to the user.Here navigation Controller that manages the modal view.
[self presentModalViewController:navigationController animated:YES];
// [navigationController pushViewController:showProgressViewController animated:YES];
}
#catch(NSException * e){NSLog(#"Exception At10: %s %d %s %s %#",__FILE__,__LINE__,__PRETTY_FUNCTION__,__FUNCTION__,e);}#finally{}
}
In the above code presentModalViewController is working but pushViewController is not working why. If any body know this please help me..

Suppose you are in ParentViewController and by pressing Child Btn you want to go to ChildViewController.
- (void) childBtnPressed : (id) sender
{
ChildViewController *makeNewObject = [[ChildViewController alloc] initWithNibName:#"ChildViewController" bundle:nil];
[self.navigationController pushViewController:makeNewObject animated:YES];
[makeNewObject release];
}
Now in your ChildViewController.m file, write this on the Back Btn action to go back to the Parent View Controller.
- (void) backBtnPressed : (id) sender
{
[self.navigationController popViewControllerAnimated:YES];
}

On clicking the button in the Navigationbar, Push nextview
- (IBAction)NextViewAction:(id) sender
{
NextViewController *NxtView = [[NextViewController alloc] initWithNibName:#"NextViewController" bundle:nil];
[self.navigationController pushViewController:NxtView animated:YES];
[NxtView release];
}
To Pop from NextViewController
[self.navigationController popViewControllerAnimated:YES];

Related

How do I push root view controller?

I want to push root view controller. Why doesn't this code work?
RootController *rootController = [[RootController alloc]initWithStyle:UITableViewStylePlain];
[self.navigationController pushViewController:rootController animated:YES];
[rootController release];
I used addSubview like this before.
- (void)cancel {
[self.navigationController popViewControllerAnimated:YES];
}
- (void)viewDidLoad { // this is root view controller
[super viewDidLoad];
UIBarButtonItem *cancelButton = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemCancel target:self action:#selector(cancel)];
self.navigationItem.leftBarButtonItem = cancelButton;
[cancelButton release];
}
RootController *rootController = [[RootController alloc]initWithStyle:UITableViewStylePlain];
UINavigationController *aNavigationController = [[UINavigationController alloc]initWithRootViewController:rootController];
self.naviController = aNavigationController;
[aNavigationController release];
[rootController release];
[self.view addSubview:[naviController view]];
And I added cancel button in navigation bar to go back to previous view. It doesn't work.
So, I want to push instead of add.
You set the root controller in a UINavigationController using the
initWithRootViewController:
method. So, the way you are doing is correct. I would suggest you to inspect self.view and ensure that it is not nil.
EDIT: after your comment
You need to define a root view controller for your UINavigationController to work properly; from the UINavigationController reference:
Every navigation stack must have at least one view controller to act as the root.
So you cannot remove the root view controller. Possibly, to make things work as you like you should create an additional view controller to use as root view controller that you do not alter, then push your RootViewController on the navigation stack, then popping would work:
UIViewController *baseController = [[UIViewController alloc] initWithStyle:UITableViewStylePlain];
UINavigationController *aNavigationController = [[UINavigationController alloc] initWithRootViewController:baseController];
self.naviController = aNavigationController;
[aNavigationController release];
[baseController release];
[self.view addSubview:[naviController view]];
RootController *rootController = [[RootController alloc] initWithStyle:UITableViewStylePlain];
[self.navigationController pushViewController:rootController animated:YES];
[rootController release];
Notice that I first defined a simple UIViewController as root view controller, then pushed your controller on to it.
Once you do this, if you add the cancel button like you do, it will work popping the rootViewController from the navigation stack.
AFTER LAST COMMENT:
If I understand you right, when clicking on the cancel button, you want to get rid of the UINavigationController altogether.
In this case, use the following code for cancel:
- (void)cancel {
[self.navigationController.view removeFromSuperview];
}
If this guess is right, keep in mind that since you are not keeping any reference to the navigation controller, it will be deallocated and with it all the view controllers you instantiated.
If instead of removing the UINavigationController altogether, you would simpy hide the navigation bar, then after popping rootController, call:
setNavigationBarHidden:animated

Presenting Modal View Controller before window is visible

I would like to present a view controller modally before calling -makeKeyAndVisible on the application's window. However, this code only shows the mainNav view controller:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
MainViewController *main = [[MainViewController alloc] init];
UINavigationController *mainNav = [[UINavigationController alloc] initWithRootViewController:main];
if ([[NSUserDefaults standardUserDefaults] boolForKey:#"Restore"])
{
DetailViewController *detail = [[DetailViewController alloc] init];
UINavigationController *detailNav = [[UINavigationController alloc] initWithRootViewController:detail];
// changing main to mainNav does not help
[main presentModalViewController:learnNav animated:NO];
[detailNav release]; [detail release];
}
self.window.rootViewController = mainNav;
[main release]; [mainNav release];
[self.window makeKeyAndVisible];
return YES;
}
What am I missing?
You should better make the window appear and then present the modal view with animated=NO. What's the point of presenting the modal view before everything else is instantiated and displayed?
Edit
To try to make your code work, here are a couple of hints. Try this:
[mainNav presentModalViewController:learnNav animated:NO];
or this:
[main.navigationController presentModalViewController:learnNav animated:NO];
I'd say that these two methods work best if they're put after the makeKeyAndVisible call.

How to set up a navigationController by UINavigationController?

I am working with push notifications. i am trying to create and push a DetailView in the navigationController when action button in notification is clicked. but navigationController is nil. how can i put that DetailView in the navigationController? I want to push RootViewController in the navigationController and then the DetailView. how can i do that?
in AppDelegate:
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo {
RootViewController *controller = [[RootViewController alloc] init];
//getting warnings here.(Unused variable navigationController)
UINavigationController *navigationController = [[UINavigationController alloc] initWithRootViewController:controller];
[controller doStuff];
[controller release];
}
in RootViewController:
-(void)doStuff{
[[self stories] removeAllObjects];
[self startParsing];
[self.tableView reloadData];
DetailViewController *detail = [[DetailViewController alloc] init];
//custom code
[self.navigationController pushViewController:detail animated:YES];
[detail release];
this is the code i m using right now. and plz notice that i have
[self.tableView reloadData];
Okay, now I am pretty sure I understand the issue. The problem is, you never manually set the navigationController property on a UIViewController. The navigationController property is nil if the view controller is not under a navigation controller and if it is, then the property points to it.
What you need to do, is when you display your root view controller, instead of directly displaying its view, add it to a navigation controller, then display the navigation controller's view. Like so:
RootViewController *controller = [[RootViewController alloc] init];
UINavigationController *navigationController = [[UINavigationController alloc] initWithRootViewController:controller];
//Here you would display navigationController.view somehow
So, after you have your root view controller in a navigation controller, in a method in root view controller you can do this:
DetailViewController *detail = [[DetailViewController alloc] init];
//Do whatever you need to do to set values on the detail view controller
[self.navigationController pushViewController:detail animated:YES];
The key thing is this: you need to put the root view controller into a navigation controller before you can access a navigation controller from within root view controller.
If your nav controller is nil, it needs creating and then you place things into it.
Try this:
UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:rootViewController];
[navController pushViewController:detailViewController animated:NO]; // or YES
If you start out with no UINavigationController and want to display it with more than one view controller in its stack, after initing the navigation controller you can set the viewControllers property to an array with the various view controllers you want.
edit: some example code:
UINavigationController *navController = [[UINavigationController alloc] init];
NSArray *viewControllers = [NSArray arrayWithObjects:viewController1, viewController2, nil];
[navController setViewControllers:viewControllers animated:NO];
After doing that, your navigation controller will have viewController2 on top and viewController1 behind it.
Alternately, you could do it this way:
UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:viewController1];
[navController pushViewController:viewController2 animated:NO];

Navigation Controller and Table Views

I am creating an application which I want to have a view controller with buttons as the first view controller with no navigation bar, and then when the user selects a button a table view controller appears managed by a navigation controller.
At the moment I am setting up the navigation controller in the app delegate and setting the top view controller as the table view controller I want to start the navigation bar on. So far I can see the navigation bar but that is it when I transition from the first view controller to the table view controller.
Any help would be much appreciated as I have confused myself with this issue.
I'm not totally clear on what you are asking, so I might have it wrong, but here goes.
The top navigation bar is can be displayed or hidden by calling:
self.navigationController.navigationBarHidden = NO;
In the viewWillAppear method of your viewController. So set it to YES or NO depending on whether or not you want it to be displayed.
#Disco, you would do something like so:
// In the App delegate
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
CustomViewController *viewController = [[CustomViewController alloc] init];
[window addSubview:viewController.view];
[window makeKeyAndVisible];
return YES;
}
// In your button method
- (IBAction)loadUpTableViewController:(id)sender {
CustomTableViewController *tvc = [[CustomTableViewController alloc] init];
UINavigationController *navigationController = [[UINavigationController alloc] initWithRootViewController:tvc];
[self presentModalViewController:navigationController animated:YES];
[navigationController release];
[tvc release];
}

Help with navigation Controller, windows & subviews!

my first xib contains a ScrollView with a springboard like interface in MainWindow.xib:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
navController = [[UINavigationController alloc] init];
[navController setNavigationBarHidden:YES];
[window addSubview:navController.view];
[window sendSubviewToBack:navController.view]; }
When a button is clicked the FirstViewController appears with a tableview and a navigation controller:
- (void) buttonPushed:(id)sender {
FirstViewController *firstViewController = [[FirstViewController alloc] init];
[navController pushViewController:firstViewController animated:YES];
[firstViewController release];
[window addSubview:navController.view]; }
When I click the back button in Navigation Controller to go back to springboard, I get the springboard xib, but unresponsive to touches with a Navigation Bar on top!
- (void)goHome:(id) sender {
[self.view removeFromSuperview];
How can I go back to springboard screen (mainwindow.xib) without having the navigation bar stacked on top, and be responsive to touches ?
Why don't you set the springboard view to be the root view controller of your navigation controller and get rid of any UI in the window?
I think that the window shouldn't have any UI elements accept view of view controllers that are added to it (by navigation controller or by tab bar controller).
This way you won't have to reinvent the wheel for the first view to load from the springboard view and the back button will work properly.
You can set the navigationBarHidden property to false in the viewDidLoad method of the root view controller (the view controller of the springboard view).
Did you try calling [navController setNavigationBarHidden:YES]; in your mainview viewWillAppear callback ?
- (void)applicationDidFinishLaunching:(UIApplication *)application
{
UIViewController *rootController = [[MyRootViewController alloc] init];
navigationController = [[UINavigationController alloc]
initWithRootViewController:rootController];
[rootController release];
window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
[window addSubview:navigationController.view];
[window makeKeyAndVisible];
}