m_userName wrote:
I'm not sure what you mean by changing the corresponding text in the data source.
I should have explained that better, since you might have assumed I meant the data source object. I was referring to the data structure used by tableView:cellForRowAtIndexPath: to load each cell. For instance, take a look at tableView:cellForRowAtIndexPath: in this example code I posted in one of your recent threads: [Re: Trouble tracking down EXC
BADACCESS error|http://discussions.apple.com/thread.jspa?messageID=12436920�]. In that case the data for each cell is obtained from the tableDataSource array:
// Set up the cell...
NSDictionary *dictionary = [self.tableDataSource objectAtIndex:indexPath.row];
cell.textLabel.text = [dictionary objectForKey:@"Title"];
return cell;
So what I meant in my last post is that whenever you change the data in a cell (the detailTextLabel in this case), you must also change the data which tableView:cellForRowAtIndexPath: will use when replacing that cell. Otherwise whatever change you made will be reversed as soon as that cell is replaced (which usually happens when the cell is scrolled out of view, then scrolled back into view, but can happen at other times as well).
Here's an example of how to use [reloadRowsAtIndexPaths:withRowAnimation:|http://developer.apple.com/library/io s/documentation/UIKit/Reference/UITableView
Class/Reference/Reference.html#//appleref/doc/uid/TP40006943-CH3-SW40] to change the detail text label of one of the cells. Note that we don't need to find the cell and modify the label directly. We just change the data source for the target row then reload the cell for that row:
// RootViewController.m
#import "RootViewController.h"
#define kDetailText @"Detail Text"
@implementation RootViewController
@synthesize data, tableDataSource;
- (void)viewDidLoad
{
[super viewDidLoad];
level = [self.navigationController.viewControllers count];
NSLog(@"%s: level=%d", _func_, level);
if (level <= 1) {
NSString *Path = [[NSBundle mainBundle] bundlePath];
NSString *DataPath = [Path stringByAppendingPathComponent:@"data.plist"];
NSDictionary *tempDict = [[NSDictionary alloc] initWithContentsOfFile:DataPath];
self.data = tempDict;
[tempDict release];
self.tableDataSource = [data objectForKey:@"Children"];
self.navigationItem.title = [data objectForKey:@"Title"];
}
else
; // tableDataSource and navigationItem.title were set by previous controller
// NSLog(@"%s: self.tableView=%@", _func_, self.tableView);
// make a nav bar button to toggle the detail text for row 0
UIBarButtonItem *detailBBI = [[UIBarButtonItem alloc]
initWithTitle:@"Detail" style:UIBarButtonItemStylePlain
target:self action:@selector(toggleDetailTextForRow0)];
self.navigationItem.rightBarButtonItem = detailBBI;
[detailBBI release];
// initialize the detail text
detailText = kDetailText;
}
- (void)toggleDetailTextForRow0 {
if ([tableDataSource count]) {
detailText = [detailText isEqualToString:@""] ? kDetailText : @"";
// get index path for row 0 and reload that row
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:0 inSection:0];
NSArray *indexPathArray = [NSArray arrayWithObject:indexPath];
[self.tableView reloadRowsAtIndexPaths:indexPathArray
withRowAnimation:UITableViewRowAnimationNone];
}
}
- (void)viewDidDisappear:(BOOL)animated {
[super viewDidDisappear:animated];
if (self.navigationController == nil) {
NSLog(@"%s: *POPPED* level=%d", _func_, level);
}
}
#pragma mark Table view methods
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
// Customize the number of rows in the table view.
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return [tableDataSource count];
}
// Customize the appearance of table view cells.
- (UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"TableViewCell";
UITableViewCell *cell = (UITableViewCell*)
[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil)
{
// NSLog(@"%s: level=%d row=%d", _func_, level, indexPath.row);
cell = [[UITableViewCell alloc]
initWithStyle:UITableViewCellStyleValue1
reuseIdentifier:CellIdentifier];
}
// set the text label
NSDictionary *dictionary = [self.tableDataSource objectAtIndex:indexPath.row];
cell.textLabel.text = [dictionary objectForKey:@"Title"];
// set the detail text label
if (indexPath.row == 0)
cell.detailTextLabel.text = detailText;
else
cell.detailTextLabel.text = kDetailText;
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// NSLog(@"%s: tableDataSource=%@", _func_, self.tableDataSource);
NSDictionary* dictionary = [self.tableDataSource objectAtIndex:indexPath.row];
// NSLog(@"%s: dictionary=%@", _func_, dictionary);
NSArray* children = [dictionary objectForKey:@"Children"];
// NSLog(@"%s: children=%@", _func_, children);
if(children)
{
// set up the next controller
RootViewController* rootViewController = [[RootViewController alloc]
initWithNibName:@"RootViewController" bundle:[NSBundle mainBundle]];
rootViewController.navigationItem.title = [dictionary objectForKey:@"Title"];
rootViewController.tableDataSource = children;
// push the next controller onto the stack
[self.navigationController pushViewController:rootViewController animated:YES];
// NSLog(@"%s: stack=%@", _func_, self.navigationController.viewControllers);
[rootViewController release];
}
}
- (void)dealloc {
NSLog(@"%s: level=%d", _func_, level);
[tableDataSource release];
[data release];
[super dealloc];
}
@end
In the above, the data source for the text label is the tableDataSource array while the data source for the detail label text is just two hard-coded strings for the purpose of demonstration. The detailText ivar is the data source for the detail label in row 0, and the string at that ivar is changed in toggleDetailTextForRow0 whenever the Detail button in the nav bar is tapped. Also note that you can add animation to the label change by resetting the second arg of reloadRowsAtIndexPaths::
- Ray