Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

UICollectionViewController not validly loading from NIB

iOS 6.0, testing on an iPhone 5

I am loading a subclass of UICollectionViewController from a nib. When I hot the awakeFromNib method, it claims that the view is loaded. Calling collectionView returns nil.

I'm therefore having a problem registering the nib which to load my cells from.

- (void)awakeFromNib {
  if ([self isViewLoaded])
    NSLog(@"[%@ %@] registered with %@", NSStringFromClass([self class]), NSStringFromSelector(_cmd),
          self.collectionView);

  UINib *nib = [UINib nibWithNibName:@"MyCollectionCell" bundle:nil];
  [self.collectionView registerNib:nib forCellWithReuseIdentifier:NIB_ID];
}

Output from above:

2012-09-22 19:21:49.129 myApp[7182:907] [MyCollectionViewController awakeFromNib] registered with (null)

Also, loadView and viewDidLoad are not called (expected when loading from a nib).

I fail with exception when trying to load the cells.

Current workaround, redundantly registering nib in collectionView:cellForItemAtIndexPath::

- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath {
  UINib *nib = [UINib nibWithNibName:@"MyCollectionCell" bundle:nil];
  [collectionView registerNib:nib forCellWithReuseIdentifier:NIB_ID];

Questions: Have you run across this? Do you see the error of my ways? Is this a known bug?


Edit: additional information …

breaking in awakeFromNib, collectionView appears inaccessible

(lldb) po [self view]
(UIView *) $1 = 0x1f158400 <UICollectionView: 0x1f158400; frame = (0 0; 320 548); clipsToBounds = YES; opaque = NO; autoresize = W+H; gestureRecognizers = <NSArray: 0x1ed8fcf0>; layer = <CALayer: 0x1ed8f790>; contentOffset: {0, 0}> collection view layout: <UICollectionViewFlowLayout: 0x1ed919a0>
(lldb) po [self collectionView]
(UICollectionView *) $2 = 0x00000000 <nil>

modifying the wakeFromNib to use view instead of collectionView is a better workaround:

  [(UICollectionView *)self.view registerNib:nib forCellWithReuseIdentifier:NIB_ID];
like image 740
bshirley Avatar asked Sep 23 '12 00:09

bshirley


1 Answers

Loading a view controller from a nib is not intended to load the view. The iOS lazy-loading scheme will only load the view once something attempts to access it. This is intended to limit memory consumption for the things which have not been put on the screen.

When you use 'self.view', the UIViewController base class accessor for the 'view' property will load the view if it has not been loaded. (Then your viewDidLoad will be called.)

If you provide a viewDidLoad method for your viewController, you could register your UINib there.

like image 149
Walt Sellers Avatar answered Nov 15 '22 05:11

Walt Sellers