I have two table View Controllers, EmployeeListViewController, and EmployeeGroupDetailViewController.
EmployeeListViewController sends an variable, _uniqueId, for every table cell selected, over to EmployeeGroupDetailViewController, which is used to lookup detail info about the selected Employee.
The problem is that when I select an Employee, everything looks fine. But if I go back (using “Back” button in ) and select a different Employee, the detail view shows the same values as before.
I’ve tried moving some code over from viewDidLoad() to viewWillAppear(), but all I’ve accomplished is that when selecting a new employee, the detail view show the values from the previously selected employee, but if I scroll so that the cells get out of view and then release, the info is updated.
Why doesn’t the detail view table get updated from the beginning?
My EmployeeListViewController.m:
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// Navigation logic may go here. Create and push another view controller.
if (self.details == nil) {
self.details = [[[EmployeeGroupDetailViewController alloc] initWithNibName:@"EmployeeGroupDetailViewController" bundle:nil] autorelease];
}
// ...
EmployeeInfo *info = [_EmployeeInfos objectAtIndex:indexPath.row];
_details.uniqueId = info.uniqueId;
// Pass the selected object to the new view controller.
[self.navigationController pushViewController:_details animated:YES];
//[EmployeeGroupDetailViewController release];
}
My EmployeeGroupDetailViewController.m:
//
// EmployeeGroupDetailViewController.m
// Whowho
//
// Created by Carl Franzon on 2012-03-14.
// Copyright (c) 2012 Atea SE. All rights reserved.
//
#import "EmployeeGroupDetailViewController.h"
#import "EmployeeDB.h"
#import "EmployeeDetails.h"
@implementation EmployeeGroupDetailViewController
@synthesize uniqueId = _uniqueId;
@synthesize headerDict = _headerDict;
//@synthesize dicContactInfo = _dicContactInfo;
//@synthesize dicEmploymentInfo = _dicEmploymentInfo;
@synthesize sortedKeys = _sortedKeys;
@synthesize details = _details;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)didReceiveMemoryWarning
{
// Releases the view if it doesn't have a superview.
[super didReceiveMemoryWarning];
// Release any cached data, images, etc that aren't in use.
}
#pragma mark - View lifecycle
- (void)viewDidLoad
{
[super viewDidLoad];
//Lookup entry in DB and set labels accordingly
//EmployeeDetails *details = [[EmployeeDB database] EmployeeDetails:_uniqueId];
_details = [[EmployeeDB database] EmployeeDetails:_uniqueId];
//if (details != nil) {
NSArray *arrTemp1 = [[NSArray alloc] initWithObjects:_details.email,_details.shortNo,_details.mobileNo,_details.directNo,nil];
NSArray *arrTemp2 = [[NSArray alloc] initWithObjects:@"Bob",@"Bill",@"Bianca",nil];
NSArray *arrTemp3 = [[NSArray alloc] initWithObjects:@"Candice",@"Clint",@"Chris",nil];
NSDictionary *temp =[[NSDictionary alloc] initWithObjectsAndKeys:arrTemp1,@"A",arrTemp2,@"B",arrTemp3,@"C",nil];
self.headerDict =temp;
[temp release];
self.sortedKeys =[[self.headerDict allKeys] sortedArrayUsingSelector:@selector(compare:)];
[arrTemp1 release];
[arrTemp2 release];
[arrTemp3 release];
// }
// Uncomment the following line to preserve selection between presentations.
// self.clearsSelectionOnViewWillAppear = NO;
// Uncomment the following line to display an Edit button in the navigation bar for this view controller.
// self.navigationItem.rightBarButtonItem = self.editButtonItem;
}
- (void)viewDidUnload
{
[super viewDidUnload];
// Release any retained subviews of the main view.
// e.g. self.myOutlet = nil;
// self.employeeNoLabel = nil;
// self.nameLabel = nil;
// self.emailLabel = nil;
// self.regionLabel = nil;
// self.officeLabel = nil;
// self.departmentLabel = nil;
// self.locationLabel = nil;
// self.roleLabel = nil;
// self.activeLabel = nil;
// self.workHoursLabel = nil;
// self.managerLabel = nil;
// self.costCentreLabel = nil;
// self.adLabel = nil;
// self.origCompNameLabel = nil;
// self.shortNoLabel = nil;
// self.directNoLabel = nil;
// self.mobileLabel = nil;
// self.sexLabel = nil;
// self.shirtJacketLabel = nil;
// self.pantsLabel = nil;
// self.scgLabel = nil;
// self.tempRoleLabel = nil;
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
//Lookup entry in DB and set labels accordingly
// EmployeeDetails *details2 = [[EmployeeDB database] EmployeeDetails:_uniqueId];
_details = [[EmployeeDB database] EmployeeDetails:_uniqueId];
//if (details != nil) {
NSArray *arrTemp1b = [[NSArray alloc] initWithObjects:_details.email,_details.shortNo,_details.mobileNo,_details.directNo,nil];
NSArray *arrTemp2b = [[NSArray alloc] initWithObjects:@"Bob",@"Bill",@"Bianca",nil];
NSArray *arrTemp3b = [[NSArray alloc] initWithObjects:@"Candice",@"Clint",@"Chris",nil];
NSDictionary *temp =[[NSDictionary alloc] initWithObjectsAndKeys:arrTemp1b,@"A",arrTemp2b,@"B",arrTemp3b,@"C",nil];
self.headerDict =temp;
[temp release];
self.sortedKeys =[[self.headerDict allKeys] sortedArrayUsingSelector:@selector(compare:)];
[arrTemp1b release];
[arrTemp2b release];
[arrTemp3b release];
//}
}
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
}
- (void)viewDidDisappear:(BOOL)animated
{
[super viewDidDisappear:animated];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
//#warning Potentially incomplete method implementation.
// Return the number of sections.
return [self.sortedKeys count];
}
- (NSString *)tableView:(UITableView *)tableView
titleForHeaderInSection:(NSInteger)section
{
return [self.sortedKeys objectAtIndex:section];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
//#warning Incomplete method implementation.
// Return the number of rows in the section.
NSArray *listData =[self.headerDict objectForKey:
[self.sortedKeys objectAtIndex:section]];
return [listData count];
//return 0;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *SimpleTableIdentifier = @"SimpleTableIdentifier";
NSArray *listData =[self.headerDict objectForKey:
[self.sortedKeys objectAtIndex:[indexPath section]]];
UITableViewCell * cell = [tableView
dequeueReusableCellWithIdentifier: SimpleTableIdentifier];
if(cell == nil) {
//Initialize cell with left lable style
cell = [[[UITableViewCell alloc]
initWithStyle:UITableViewCellStyleDefault
reuseIdentifier:SimpleTableIdentifier] autorelease];
}
NSUInteger row = [indexPath row];
//cell.textLabel.text = @"default";
cell.textLabel.text = [listData objectAtIndex:row];
// static NSString *CellIdentifier = @"Cell";
//
// UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
// if (cell == nil) {
// cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
// }
// Configure the cell...
return cell;
}
/*
// Override to support conditional editing of the table view.
- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
// Return NO if you do not want the specified item to be editable.
return YES;
}
*/
/*
// Override to support editing the table view.
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
if (editingStyle == UITableViewCellEditingStyleDelete) {
// Delete the row from the data source
[tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
}
else if (editingStyle == UITableViewCellEditingStyleInsert) {
// Create a new instance of the appropriate class, insert it into the array, and add a new row to the table view
}
}
*/
/*
// Override to support rearranging the table view.
- (void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)fromIndexPath toIndexPath:(NSIndexPath *)toIndexPath
{
}
*/
/*
// Override to support conditional rearranging of the table view.
- (BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
// Return NO if you do not want the item to be re-orderable.
return YES;
}
*/
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// Navigation logic may go here. Create and push another view controller.
/*
<#DetailViewController#> *detailViewController = [[<#DetailViewController#> alloc] initWithNibName:@"<#Nib name#>" bundle:nil];
// ...
// Pass the selected object to the new view controller.
[self.navigationController pushViewController:detailViewController animated:YES];
[detailViewController release];
*/
NSArray *listData =[self.headerDict objectForKey:
[self.sortedKeys objectAtIndex:[indexPath section]]];
NSUInteger row = [indexPath row];
NSString *rowValue = [listData objectAtIndex:row];
NSString *message = [[NSString alloc] initWithFormat:rowValue];
UIAlertView *alert = [[UIAlertView alloc]
initWithTitle:@"You selected"
message:message delegate:nil
cancelButtonTitle:@"OK"
otherButtonTitles:nil];
[alert show];
[alert release];
[message release];
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
- (void)dealloc
{
// self.employeeNoLabel = nil;
// self.nameLabel = nil;
// self.emailLabel = nil;
// self.regionLabel = nil;
// self.officeLabel = nil;
// self.departmentLabel = nil;
// self.locationLabel = nil;
// self.roleLabel = nil;
// self.activeLabel = nil;
// self.workHoursLabel = nil;
// self.managerLabel = nil;
// self.costCentreLabel = nil;
// self.adLabel = nil;
// self.origCompNameLabel = nil;
// self.shortNoLabel = nil;
// self.directNoLabel = nil;
// self.mobileLabel = nil;
// self.sexLabel = nil;
// self.shirtJacketLabel = nil;
// self.pantsLabel = nil;
// self.scgLabel = nil;
// self.tempRoleLabel = nil;
[_headerDict release];
[_sortedKeys release];
[super dealloc];
}
@end
Also, the count of rows for each section does not seem to get updated for every new selected employee.
It’s customary when using the master-detail pattern for the master view controller to create a new instance of the detail view controller each time a detail item is selected, passing ownership of that instance off to the navigation controller. (Actually, if you target iOS 5.0+ and use storyboards, it’s done this way for you, and all you do is tell the detail view controller which item to use.) However, this isn’t directly what’s causing your problem.
Your detail view controller updates its internal data to match whatever
uniqueIDhas been set on it inviewWillAppear:(andviewDidLoad:, so it happens twice if the view’s been unloaded). But nowhere does it tell its table view to update to reflect the new data. Calling[self.tableView reloadData]should do that.