I taken a custom cell and i am not reusing the identifier over there. I am using the identifier in the table view where i am using that custom cells. But when i run my application and entering the data in textfield my data getting erased when i scroll the view.and My cell are not reusing that data.Can any one help me out in this thing. Thanks!
Custom cell code
-(UITableViewCell *)returnCellForEach:(UITableView *)tableView
{
[[NSBundle mainBundle] loadNibNamed:#"CustomCell" owner:self options:nil];
myLabel = (UILabel *)[customCell.contentView viewWithTag:10];
return customCell;
}
Table view 'cellForRowAtIndexPath' code
static NSString *CellIdentifier = #"Cell";
cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil)
{
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleValue1 reuseIdentifier:#"Hello"] autorelease];
}
whats mistake i this thing. Thanks!
Cells should not be used to store your data. If the user enters something in the edit field, you need to copy the content to e.g. a member variable in your view controller. If the cell is scrolled out of view, it is either destroyed, or it MIGHT be kept for reuse. Either way, you can not rely on that edit field to exist anymore.
I dont get your question actually, But I have done like following :
cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil)
{
cell = (CustomCell *)[[[NSBundle mainBundle] loadNibNamed:#"CustomCell" owner:self options:nil] objectAtIndex:0];
}
myLabel = (UILabel *)[customCell.contentView viewWithTag:10];
//myLabel = cell.labelWithTag10;
myLable.text = #"Text";
And It works fine for me;
Related
I have created a custom cell with a UISegmentedControl on it and loaded the cell like,
static NSString *CellIdentifier = #"Cell";
SegmentedCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil)
{
NSArray *cells =[[NSBundle mainBundle] loadNibNamed:#"SegmentedCell" owner:nil options:nil];
for (UIView *view in cells)
{
if([view isKindOfClass:[UITableViewCell class]])
{
cell = (SegmentedCell *)view;
[cell.SegmentedControl addTarget:self
action:#selector(segmentedControlChanged:)
forControlEvents:UIControlEventValueChanged];
}
}
}
cell.textLabel.text = #"Sample";
cell.selectionStyle = UITableViewCellSelectionStyleNone;
The custom cell successfully loaded and I get the action of the SegmentedControl.
But when I scroll the table view, state of the SegmentedControl is changed.
When you scroll a tableview that uses dequeueReusableCellWithIdentifier, you aren't actually saving all the different cells. To fix your problem you need to implement a few things.
Set your segmented control up to store its value to a variable every time it is pressed.
Put this value into an array
In the cellForRowAtIndexPath method, get the variable out of the array and set the segmented control's value to this value of the variable.
Currently I have the following method, but it doesn't quite work...
- (UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *MyIdentifier = #"cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier];
if (cell == nil) {
[[NSBundle mainBundle] loadNibNamed:#"TVCell" owner:self options:nil];
cell = tvCell;
self.tvCell = nil;
}
UILabel *label;
label = (UILabel *)[cell viewWithTag:5];
label.text = [NSString stringWithFormat:#"Hole #%d", indexPath.row];
return cell;
}
The table view gets created with no errors, but each individual cell contains nothing, but clearly the TVCell.xib has a label with a tag of 5. The only question I have is this. I don't quite understand these steps apple gives here...
Select File’s Owner in the nib document window, open the Identity pane of the inspector, and set the class of File’s Owner to your custom view controller class.
Connect the cell outlet of File’s Owner (now the placeholder instance of your custom subclass) to the table-view cell object in the nib-file document.
Here is where those steps are...
http://developer.apple.com/library/ios/#documentation/UserExperience/Conceptual/TableView_iPhone/TableViewCells/TableViewCells.html#//apple_ref/doc/uid/TP40007451-CH7
Can someone please explain those steps for a noob like me? I think that is what I messed up on, but I could have done anything wrong.
I don't think TcCell becomes a property of self. Try this instead when the cell queue is empty:
if (cell == nil) {
cell=[[NSBundle mainBundle] loadNibNamed:#"TVCell" owner:self options:nil];
}
It's kind of difficult to explain the steps that you said you don't understand in words. I would suggest looking for tutorials that have images or videos for that. (I did a quick search and there are lots available, but I didn't really want to choose one to direct you to without having read them more closely).
However, I prefer to create custom table view cells this way:
http://www.mobilesce.com/2011/12/27/the-best-way-to-do-custom-reusable-uitableviewcells/
It's slightly different from the way described in the apple docs, but I've seen a lot of people use it and I find it easier.
The NSBundle method loadNibNamed:owner:options: returns an NSArray containing the top level objects in your nib file. Try this:
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier];
if (cell == nil) {
NSArray *nibArray = [[NSBundle mainBundle] loadNibNamed:#"TVCell" owner:self options:nil];
cell = [nibArray objectAtIndex:0];
}
I am having trouble wiht UITableViewCell loaded from nib. I used apple documentation to that but I do't know where I am going wrong. UITableViewCell created through IB contains 5 UIlable. Nib are loaded perfectly but the problem is when I scroll text of the label changes automatically to different.
Following is the my code for cell for row at indexpath. Please let me know where I am going worng.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
int rowNo = [indexPath row];
NSLog(#"Row No:%d",rowNo);
Transfer *tempTransferRecord =(Transfer*)[self.transferInformation objectAtIndex:rowNo];
seasonYear.text=tempTransferRecord.seasonYear;
longName.text=tempTransferRecord.longName;
transactionDate.text=tempTransferRecord.transactionDate;
toTeam.text=tempTransferRecord.toTeam;
fromTeam.text=tempTransferRecord.fromTeam;
/*
static NSString *MyIdentifier = #"MyIdentifier2";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier] ;
if (cell == nil)
{
[[NSBundle mainBundle] loadNibNamed:#"PlayerTransfers" owner:self options:nil];
cell=transfersInfoCell;
self.transfersInfoCell=nil;
}
*/
static NSString *CellIdentifier = #"MyIdentifier2";
static NSString *CellNib = #"PlayerTransfers";
UITableViewCell *cell = (UITableViewCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:CellNib owner:self options:nil];
cell = (UITableViewCell *)[nib objectAtIndex:0];
}
// perform additional custom work...
return cell;
}
Try moving your cell loading code to the top of cellForRowAtIndexPath, and the rowNo and value setting after that. Cells changing content must mean you're either changing what's in the data source between when you first set it and when you scroll, or you're setting values at the wrong point in time (i.e setting values on row 5 but then loading row 6 from a nib, or setting values on a row but then loading the nib for it afterwards so the values you set are overridden). Also, I'm a bit concerned that you set local variables rather than, say, (PlayerTransfers*)cell.seasonYear.text = tempTransferRecord.seasonYear or (UILabel *)[cell viewWithTag:1].text = tempTransferRecord.seasonYear. Shouldn't you be setting the values within each cell rather than on your table view class? That could explain why values are changing to something different: you may use the same variables to set every cell.
Have you set a CellIdentifier in Interface Builder?
I am trying to understand how the rendering of each cell works. Here's my code:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *cellIdentifier = #"QuestionCell";
static NSString *cellNib = #"QuestionsTableViewCell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil)
{
//cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:cellNib owner:self options:nil];
cell = [nib objectAtIndex:0];
NSLog(#"%#", #"--> load from nib");
}
return cell;
}
The NSLog in this code is called 8 times initially (because I have 8 rows visible initially). Then when I start scrolling, it's called once and then no more after. I thought it should've been called once and that's it since it should be re-using it after the first call? And why is it called once more after the initial 8? (scratching head...)
It's possible that there could be 9 cells on screen when you are scrolling the table view. This wasn't needed when you started but as you scroll, the 9th cell is required as the top one leaves, a new cell at bottom enters. A cell can't be reused in halves. :)
I have a class which extends UITableViewCell. For the purpose of this exercise, let's call it "CustomCell". In CustomCell, I have a UIImageView IBOutlet setup. The image instance name in this case is myImage. I wish to display this image based on certain criteria that's coming back from a server. That data is a dictionary which in this exercise we'll call "serverData". At first, the UITableView renders just fine with the UIImageView showing up in cells which it should. The problem occurs when I start scrolling the actual UITableView, the image gets lost. Somehow it's not properly being either cached or dequeued. Not sure where the problem is or how to better improve on this code. Here's an excerpt:
- (UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CustomCellIdentifier = #"CustomCellIdentifier";
CustomCell *cell = (CustomCell *)[tableView dequeueReusableCellWithIdentifier:CustomCellIdentifier];
if (cell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"CustomCell"
owner:self options:nil];
cell = (CustomCell *)[nib objectAtIndex:0];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
}
NSDictionary *serverData = myData // previously defined.
if ([[serverData valueForKey:#"foo"] isEqualToString:#"0"])
cell.myImage.hidden = YES;
cell.accessoryType = UITableViewCellAccessoryDetailDisclosureButton;
return cell;
}
For memory reasons UITableView reuses cells when scrolling (e.g the dequeueReusableCellWithIdentifier) call.
What this means is that the cell you receive could have been configured in anyway that is valid for use with that identifier so you must reset all these properties.
In your case I suspect you are being given a cell with an image that had been hidden so this will fix it:
NSDictionary *serverData = myData // previously defined.
if ([[serverData valueForKey:#"foo"] isEqualToString:#"0"])
cell.myImage.hidden = YES;
else
cell.myImage.hidden = NO;
Remember that your cells are being reused, so you need to reset the cell.myImage.hidden value each time you use that cell
if (cell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"CustomCell"
owner:self options:nil];
cell = (CustomCell *)[nib objectAtIndex:0];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
} else {
cell.myImage.hidden = NO;
}