I have a functioning app, and I'd like to just add a new view and have an existing button change views with an IBAction function. I've set up the following and get no response. Thanks for any help.
MainViewController.h
- (IBAction)showSettings:(UIButton *)sender;
MainViewController.m
-(void)showSettings:(UIButton*)btn{
SettingsViewController *oView = [[SettingsViewController alloc] initWithNibName:#"SettingsViewController" bundle:nil];
[self.navigationController pushViewController:oView animated:YES];
}
SettingsViewController.h (the new view) is relatively empty.
SettingsViewController.m
boilerplate
Three things to make sure:
showSettings: gets called when the button is tapped (if not then perhaps you didn't connect the button tap event to the action at all)
SettingsViewController instance gets alloc and initialised
self.navigationController is not nil (if it's nil perhaps the current view controller is not embed in a navigation controller in the first place?).
Update:
Now we see the issue is #3. To embed your first view controller to a UINavigationController so you could push the second view controller:
Select your first view controller in storyboard
Select (menu) Editor -> Embed In -> Navigation Controller
Have you wired up your button's TouchUpInside event to your showSettings: method? This is normally done in Interface Builder with a control-drag. If you set a breakpoint on the first line of showSettings:, do you hit the breakpoint when you press the button? If not this is likely your issue.
Related
Here is the scenario
Create new project Tabbed Application. Add new controller, TestViewController with XIB file, in the XIB file just add one button with text "TestViewControllerButton".
If I create a button in FirstViewController, and add an action to go to TestViewController, the button in XIB file is displaed.
TestViewController* vc = [[TestViewController alloc] init];
[self presentViewController:vc animated:YES completion:nil];
The problem is when I add TestViewController to tab controller (index 2, start from 0), it does not show the XIB (I mean, the button does not displayed).
Here are my steps. I add UIViewController in Tab Controller, then change the class to TestViewController in Identity Inspector. Then add Tab Bar Item to TestViewController and link it to Tab Bar Controller, so when the last tab is clicked, it linked to TestViewController. But the problem is, the button in the XIB is not displayed (I add the button in TestViewController.xib).
Yeah, off course I can add the button directly in Main.storyboard in my TestViewController, but the idea is I want to manage the UI in TestViewController XIB, and the main.storyboard just load the view in TestViewController image.
Ok, I add some screenshot to make understand. This screen runs well when I do programmatically, run in UIViewController (code above - self presentViewController:vc animated:YES completion:nil).
When I run from Tab
The setting I think is already correct (since it runs well in UIViewController)
Already set file owner to the TestViewController
Already bind the outlet
Thanks!
I think you are using the ViewController of size Inferred , Change it to iPhone 4 inch in Attribute Inspector (Simulated Metrics -> Size and set the button frame acc. to that .
Hope this help :)
Of course it will not show the controls. See, you are using two different view controllers at these places. In the xib, you have actually added your button and hence when an instance of your testViewController is created from the xib, it has the button and its associated action with it. However, in the case when you add a viewController in your storyboard and set its class to be that of TestViewController, all you are doing is setting the class type of the new view controller to be TestViewController. But you are not providing any information by which the storyboard can know that it has to create the new instance of testViewController from the image saved in its XIB. So it just crates a new view controller of type TestViewController, using its image from inside the storyboard (without the button in it).
So to get your view controller from the xib you will have to override initWithCoder: method inside your TestViewController implementation and return an instance of your viewController from the XIB. Something like:
- (instancetype)initWithCoder:(NSCoder *)aDecoder {
return [self initWithNibName:nil bundle:nil];
}
I am using MMDrawerController for making left slide menu in iOS. The problem is that all the view controllers I am using in this project are having slider with them i.e in each UIViewController I can slide to get left menu but I want only with the first view not with all the UIViewController.
How can I stop slider code for the other UIViewController in the project.
you can cancel panning using below method. put that method in viewWillAppear
To allow gesture add this in viewWillAppear
[self.mm_drawerController setOpenDrawerGestureModeMask:MMOpenDrawerGestureModeAll];
when you push any view cancel gesture using below code.
[self.mm_drawerController setOpenDrawerGestureModeMask:MMOpenDrawerGestureModeNone];
if you don't want side menu for a view controller, call it using segue
example issue code:
assuming you have used this code in the side menu to navigate to other view controllers
switch(item selected) ....
case number:
centerViewController = [self.storyboard instantiateViewControllerWithIdentifier:#"STORYBOARD_ID"];
instead use :
[self performSegueWithIdentifier:#"segue_identifier" sender:nil];
this will navigate to completely new context instead of adding your view controllers to the centerViewController of MMDrawerController
My problem
I have a standard UIViewController. With the press of a button, it loads a form sheet modal view controller. When dismissing this modal view with the press of a UIBarButtonItem I call a method by doing:
ViewController *main = [[ViewController alloc] initWithNibName:nil bundle:nil];
[main updateLabel];
In the method -(void)updateLabel in the main ViewController I'm setting the text of a label, but the label won't change. But I know the function gets called, because if I do a NSLog(#"Method call test); instead of label.text = #"Test" I can see the message in console.
What am I doing wrong? It must be the way I'm calling the method in the main ViewController, because I can easily change the label anywhere else.
What I want to do:
When dismissing a modal view controller, I want a method to be called in the main view controller, and in this case change the text of a label.
Thanks for your help!
You're creating a new instance of ViewController with that code, not getting a pointer to the one you already have.
If ViewController is the controller that presented the modal view, then you can get a pointer to it with,
ViewController *main = self.presentingViewController;
A better way to do this would be to use the delegate pattern.
https://developer.apple.com/library/ios/documentation/general/conceptual/DevPedia-CocoaCore/Delegation.html
The following is a design pattern suggestion
The modal view controller shouldn't know how to dismiss itself, that is the responsibility of the presenting view controller. After all, it could have been presented in many different ways (modally, popover, push navigation). Using the delegate pattern, the modal view controller would tell its delegate that it should be dismissed when the bar button item gets pressed. The delegate, which is the presenting view controller, would then dismiss the modal view and update the label mentioned in your question.
I have a button in my popover controller. I want to use it to dismiss the popover, so I am trying to access a method (dismissPopover) of the presenting view controller (the "root" view controller).
Note: the method to dismiss the popover is already set up and working, in the root VC, which is the delegate. If I call it it will dismiss the popover. I just need to access the method from the popover.
To do this I set up a property in the AppDelegate, and get an instance of the rootVC like this: self.rootController = (ViewController*)self.window.rootViewController;. Then I imported the root VC class and the AppDelegate to the popover's view controller's class, as below. Seems to give me access to the rootVC, and the methods, but the results do not fire the method. Any idea what I am missing here?
#import "ViewController.h"
#import "AppDelegate.h"
Action connected to button:
- (IBAction)dismissPopover:(id)sender {
//Checking the button works, it does:
NSLog(#"dismissPopover, from popover");
//Trying to get an instance of the rootViewController, the "presenting view controller"
ViewController *rootVC = [(AppDelegate *)[[UIApplication sharedApplication] delegate] rootController];
//trying to access the method in the rootVC that dismisses the popover
[rootVC dismissPopover];
//Tried the following code, does nothing:
//[self dismissPopoverAnimated:YES];
}
NOTE: I ended up abandoning the use of a popover for this as it became a bit over complicated. I tried loading my view controller into a UIView (so I could load the contents of a nib to a pop-up view). That also became a bit complicated. So, for now I am just building my desired interface in a UIView programatically. So far works great.
dismissPopoverAnimated: is a method of UIPopoverController class. so, you need a popover controller reference in your 'root' view controller.
MyRootViewController.myPopoverController = thePopover;
the button is in your 'root' view controller, and in it's action method:
[self.myPopoverController dismissPopoverAnimated:YES];
In iOS 8, you can dismiss the popover (if it's coming from a segue, at least) with dismissViewControllerAnimated:completion: from within the popover. Doesn't work in iOS 7 (or below), however.
Popover automatically dismissed when clicking outside it , as you order a button to dismiss it you can simply use the following code inside your dismissPopover method :
[self.popoverController dismissPopoverAnimated:YES];
you don't need all this tedious work !
[self dismissViewControllerAnimated:YES completion:nil];
is the solution;
you just need an IBoutlet or add target to your button and then call above line
I had the same problem
just do in your buttonClickMethod:
[yourPopoverController dismissPopoverAnimated:YES];
hope you help!
cheers
This is the first time I'm trying to implement navigation from a tableView cell to another tableView using UINavigationController and it doesn't work for me.
I'm NOT using nib file and I have a simple tableView that I present it in a modal dialog in my app, it works fine, now I added the disclosureInidcator to one of it's cell, to make the user enable to choose from a fixed number of options available from another list(tableView). For this purpose I have another class that makes the second tableView. the problem is now navigation from the cell(contains disclosure icon)in first tableview to second tableView doesn't do anything, no error, no nothing. I guess the way I setup the navigation controller would be wrong, the code doesn't fall in delegate, or datasource of the second class at all.
in First TableView in method : didSelectRowAtIndexPath I tried to catch that row, then call the second tableView like this:
mySecondViewController *secondVC = [[[mySecondViewController alloc] initWithStyle:UITableViewStyleGrouped ] autorelease];
UINavigationController *navCont = [[UINavigationController alloc] initWithRootViewController: self];//not sure the first controller should act as the root controller?
[navCont pushViewController:secondVC animated:YES]; //it does nothing, no error,...
the second tableViewcontroller class contains all delegate and datasource methods, and initialization method:
- (id)initWithStyle:(UITableViewStyle)style
{
if ((self = [super initWithStyle:style])) {
}
return self;
}
and declared in interface as:
#interface stockOptionViewController : UITableViewController {
}
I tried to play with viewDidLoad, but didn't help.
Please help me cause I have no clue and all sample codes found is based on using nib files.
Thank,
Kam
Your navigation controller should be the root view controller of the app delegate's window, and the first view controller should be the root view controller of the navigation controller, then you can push new controllers onto it.
Please see the documentation for UINavigationController.
At the moment, you are creating a navigation controller but not putting it anywhere, so asking it to push new view controllers is a little pointless. You have the right code, just not in the right order.
You can present view control modally without nav controller
mySecondViewController *secondVC = [[[mySecondViewController alloc] initWithStyle:UITableViewStyleGrouped ] autorelease];
[self presentModalViewController:secondVC animated:YES];
UINavigationController should be the root view controller. In the current code, navCont is not on the view stack, so it won't work. Instead of pushing myFirstViewController in your appDelegate, push the UINavigationController to the stack and add myFirstViewController as its root view controller.