When do I need to call - [UIViewController initWithNibName: bundle:]?

In the Usage column, initWithNibName does not change anything at all , it shows two uses of the same kind of Nib view, in the first case it just calls alloc / init and the second, it indicates initWithNibName.

So, although this always works:

MyViewController *vctrlr = [[MyViewController alloc] initWithNibName:@"MyViewController" bundle:nil]; [self.navigationController pushViewController:vctrlr animated:YES]; [vctrlr release];

The following works for all view controllers that I have inherited, but not mine!

TheirViewController *vctrlr = [[TheirViewController alloc] init]; [self.navigationController pushViewController:vctrlr animated:YES]; [vctrlr release];

New to iOS programming, I have inherited some code. All View Controllers views are defined in IB, but inconsistent creation / initialization of these view controllers has been detected. I created a new View Controller and XIB, but it does not work if I do not use initWithNibName (it fails when I click the view controller on the Nav controller). I can’t say how my view controller is different from the rest ... any hints? I managed to remove the use of initNibName for all other view controllers in the application except mine.

+6
source share
2 answers

You can pass any string name to initWithNibName: You are not just limited to calling initWithNibName:@"MyClassName" when your class is called MyClassName . It could be initWithNibName:@"MyClassNameAlternateLayout" .

This becomes useful if you need to load a different icon depending on what the application should do. Although I try to simplify the development and maintenance process as much as possible, I try to use one controller for each controller for each category of devices (iPhone or iPad), I could understand if the developer wants to provide another layout or various functions from time to time.

Another important point: initWithNibName: bundle: is the designated initializer for the UIViewController . When you call -[[UIViewController alloc] init] , then initWithNibName:bundle: -[[UIViewController alloc] init] called backstage. You can check this with a symbolic breakpoint. In other words, if you just want the default behavior, it is expected that you can call -[[UIViewController alloc] init] , and the designated initializer will be invoked implicitly.

If, however, you call -[[UIViewController alloc] init] and don’t get the expected behavior, then probably your subclass of UIViewController incorrectly implemented - (id)init . The implementation should look like one of these two examples:

 - (id)init { self = [super init]; if (self) { // custom initialization } return self; } 

or

 - (id)init { NSString *aNibName = @"WhateverYouWant"; NSBundle *aBundle = [NSBundle mainBundle]; // or whatever bundle you want self = [self initWithNibName:aNibName bundle:aBundle]; if (self) { // custom initialization } return self; } 
+1
source
 If you want to work following code: MyViewController *vctrlr = [[MyViewController alloc] inil]; [self.navigationController pushViewController:vctrlr animated:YES]; Then you should implement following both methods in MyViewController: - (id)init { self = [super initWithNibName:@"MyViewController" bundle:nil]; if (self != nil) { // Do initialization if needed } return self; } - (id)initWithNibName:(NSString *)nibName bundle:(NSBundle *)bundle { NSAssert(NO, @"Init with nib"); return nil; } 
0
source

Source: https://habr.com/ru/post/889060/


All Articles