Objective-c – How to programmatically create UIView -> UIViewController -> UITableView

ios4iphoneobjective c

I've been struggling to add a UIView above my UITableViewController. Through searches, reading and experimenting I've determined that instead of a UITableViewController I should just be using a UIViewController. I'm having a hard time making this work for a variety of reasons and I'd like to just start fresh with a better architecture.

Basically I'm looking for sample code / tutorials that could help me create the following completely programmatically (no NIBS):

- Navigation-based Layout
- UIViewController
-- UIView
--- UITableView
--- Etc.

The reason why I want a UIView above my UITableView is I want to be able to add UIViews above my table.

-UPDATE-

Adding code to make this more clear:

JMoviesListViewController.m – UITableViewController subclass


- (void)loadView
{
    NSLog(@"loadView called");
    UIView *baseView = [[[UIView alloc] init] autorelease];
    TISwipeableTableView * aTableView = [[[TISwipeableTableView alloc] init] autorelease];   
    [aTableView setDelegate:self];
    [aTableView setDataSource:self];
    [aTableView setSwipeDelegate:self];
    [aTableView setRowHeight:54];
    [baseView addSubview:aTableView];
    self.view = baseView;
    [super loadView];
}

- (void)viewDidLoad {   

    listOfMovies = [[NSMutableArray alloc] init];

    UIView *myProgView = (UIView *)self.progView; // progView is a method that returns a UIView

    [self.view insertSubview:myProgView aboveSubview:self.tableView]; 

    [self.navigationItem setTitle:@"Now Playing"];

    movies = [[Movies alloc] init];
    movies.delegate = self;
    [movies getMovies:[NSURL URLWithString:apiQuery]];

    [super viewDidLoad];
}


- (UIView *)progView {
    if (progView == nil)
    {
        // create a progress view
        //x,y,w,h
        progView = [[UIView alloc] initWithFrame:CGRectMake(110, 110, 95, 30)];
        progView.backgroundColor = [UIColor grayColor];
        progView.tag = 1;    // tag this view for later so we can remove it from recycled table cells
        progView.autoresizingMask = (UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin);
        progView.layer.cornerRadius = 5;


        UILabel *activityLabel = [[UILabel alloc] init];
        activityLabel.text = NSLocalizedString(@"Loading...", @"string1");
        activityLabel.backgroundColor = [UIColor grayColor];
        activityLabel.textColor = [UIColor whiteColor];
        activityLabel.font = [UIFont systemFontOfSize:14];
        [progView addSubview:activityLabel];
        activityLabel.frame = CGRectMake(5, 2, 70, 25);

        UIActivityIndicatorView *activityIndicator = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleWhite];
        [activityIndicator startAnimating];
        [progView addSubview:activityIndicator];
        activityIndicator.frame = CGRectMake(70, 5, 20, 20);


    }
    return progView;

}

To be clear, the code works fine, the problem is that the cell lines of the table are "bleeding through" the UIView spinner that is inserted with this line:
[self.view insertSubview:myProgView aboveSubview:self.tableView];
leading me to believe that myProgView is not aboveSubview:self.tableView.

Best Answer

Views and controllers are separate things. You can have a hierarchy of view controllers and a hierarchy of views. But they're not interleaved, as the title of posts suggests (I know, Interface Builder displays them as a single hierarchy, but views and controllers are more like two parallel hierarchies).

Anyway, you can easily have a view controller set up whatever views you want in code. Override the loadView method, create a view that you assign to self.view, then add subviews to that view.

For example:

- (void)loadView
{
    UIView *view = [[[UIView alloc] init] autorelease];
    UITableView *tableView = [[[UITableView alloc] init] autorelease];
    tableView.dataSource = self;
    tableView.delegate = self;
    [view addSubview:tableView];
    self.view = view;
}

Your view controller should either inherit UITableViewController or implement the UITableViewDataSource and UITableViewDelegate protocols.

Related Topic