Search code examples
objective-ciosuiviewxibnib

iOS (Re)Use a NIB as a Template


I have created a nib file with different views. I was planning to use this nib file as a template, much like in web (i.e. html). So create a new instance of this nib fill it with actual data, create another new instance of nib & fill with actual data etc...

But when I try to do this, nib instance is not behaving the same. Only one gets created. Am I missing something? Aren't nib files supposed to be used this way?

Here's how I tried to use my nib file -

    int yCoord = 0;

    for(int i=0; i<[resultSet count]; i++)
    {
        [[NSBundle mainBundle] loadNibNamed:@"msgView" owner:self options:nil];
        UIView *tmpMsgView = [[UIView alloc] initWithFrame:CGRectMake(0, yCoord, msgView.view.frame.size.width, msgView.view.frame.size.height)];
        tmpMsgView         = msgView.view;

        UILabel *senderLabel = (UILabel *)[tmpMsgView viewWithTag:1];
        [senderLabel setText:@"trial"];

        [self.view addSubview:tmpMsgView];
        [tmpMsgView release];
        yCoord += msg.view.frame.size.height;

    }

this msgView is hooked up to the nib file (through IB) and the owner of that nib file too is defined as this viewController class.


Solution

  • Your code is adding the same instance over and over again, not a new instance each time.

    UIView *testView = [[UIView alloc] init];
    testView.backgroundColor = [UIColor blueColor];
    for (int i=0; i<5; i++) {
        testView.frame = CGRectMake(0.0, (i+1)*40.0, 200.0, 20.0);
        [self.window addSubview:testView];
    }
    [testView release];
    

    and

    for (int i=0; i<5; i++) {
        UIView *testView = [[UIView alloc] init];
        testView.backgroundColor = [UIColor blueColor];
        testView.frame = CGRectMake(0.0, (i+1)*40.0, 200.0, 20.0);
        [self.window addSubview:testView];
        [testView release];
    }
    

    are two very different things. the first actually makes very little sense and results in a single blue bar, the second makes much more sense and results in 5 blue bars -- I think this is what you want.

    look at the following, it will create 5 rectangles with all different colors -- this is to illustrate that each is rectangle is its seperate instance loaded from a nib:

    for (int i=0; i<5; i++) {
        NSArray *nibObjects = [[NSBundle mainBundle] loadNibNamed:@"aView" owner:self options:nil];        
        UIView *nibView = [nibObjects objectAtIndex:0];
    
        nibView.backgroundColor = [UIColor colorWithRed:(i+1)*0.14 green:(i+1)*0.11 blue:200.0 alpha:1.0];
        nibView.frame = CGRectMake(0.0, (i+1)*40.0, 200.0, 20.0);
        [self.window addSubview:nibView];
    }
    

    now, if we assign our nibObjects array only once before the loop, we again have the same issue in that we add the same instance over and over again, which will result in one rectangle only:

    NSArray *nibObjects = [[NSBundle mainBundle] loadNibNamed:@"aView" owner:self options:nil];        
    for (int i=0; i<5; i++) {
        UIView *nibView = [nibObjects objectAtIndex:0];
    
        nibView.backgroundColor = [UIColor colorWithRed:(i+1)*0.14 green:(i+1)*0.11 blue:200.0 alpha:1.0];
        nibView.frame = CGRectMake(0.0, (i+1)*40.0, 200.0, 20.0);
        [self.window addSubview:nibView];
    }
    

    hope this helps