Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>***Update - When using custom cells remove the prototype cell as you don't need it!!</p> <p>I finally figured out why it was not working. The whole problem is the Prototype Cell because you have to set a reuse Identifier and in most of the tutorials they use the string "Cell".</p> <p>When the tableview load it already has a cell in it with the Identifier "Cell" so it doesn't create a new cell it just reuses the cell that has the Identifier "Cell".</p> <pre><code>static NSString *CellIdentifier = @"Cell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; if (cell == nil) { cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier]; } </code></pre> <p>The above block if (cell == nil) is never called because it is reusing the Prototype cell that is already there. The other problem is creating the label below this block as in:</p> <pre><code>-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *CellIdentifier = @"Cell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; if (!cell) { cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier]; } FailedBankInfo *info = [_fetchedResultsController objectAtIndex:indexPath.row]; CGRect infoFrame = CGRectMake(10, 10, 200, 16); UILabel *infoLabel = [[UILabel alloc] initWithFrame:infoFrame]; infoLabel.textColor = [UIColor blackColor]; infoLabel.backgroundColor = [UIColor yellowColor]; infoLabel.font = [UIFont systemFontOfSize:12]; infoLabel.textAlignment = NSTextAlignmentCenter; infoLabel.tag = 101; infoLable.text = [NSString stringWithFormat:@"%@, %@", info.city, info.state]; [cell.contentView addSubview:infoLabel]; return cell; } </code></pre> <p>This appears to work fine as it does create the Label but when you scroll the screen you find that Labels are overlapping themselves as in my problem. This is because when a cell goes off screen and comes back on the cellForRowAtIndexPath reuses a cell that already has a label and creates another Label over the top. This keeps happening until you have 7, 8 or more Labels overlapping on the same cell. I worked this out by putting an NSlog in the didSelectRowatIndex to count the number of subviews here:</p> <pre><code>- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath { NSLog(@"Count is:%i", [[tableView cellForRowAtIndexPath:indexPath].contentView.subviews count]); } </code></pre> <p>So what you need to do is create the custom Label inside the if (cell == nil) and use an else to only set the text of the Label. The key for this to work is that each cell has to have a unique reuse Identifier so when CellforRowatIndexPath is called it creates a new cell the first time it appears. When that cell goes off screen and comes back on a new cell is not created it just reuses the existing one and changes the text without creating another Label. I have checked this with another NSlog in the if (cell == nil) it fires once for each cell and after that it doesn't fire because it reuses dequeued cells. I just used a string "myCell" + indexPath.row for the Identifier. In the storyboard I still have the Identifier of "Cell" for the Prototype cell. It complains if you don't have something in there. Here is my final code:</p> <pre><code>- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { NSString *myCellID = [NSString stringWithFormat:@"myCell%i", indexPath.row]; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:myCellID]; FailedBankInfo *info = [_fetchedResultsController objectAtIndexPath:indexPath]; if (cell == nil) { cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:myCellID]; CGRect infoFrame = CGRectMake(10, 10, 200, 16); UILabel *infoLabel = [[UILabel alloc] initWithFrame:infoFrame]; infoLabel.textColor = [UIColor blackColor]; infoLabel.backgroundColor = [UIColor yellowColor]; infoLabel.font = [UIFont systemFontOfSize:12]; infoLabel.textAlignment = NSTextAlignmentCenter; infoLabel.tag = 101; infoLabel.text = [NSString stringWithFormat:@"%@", info.name]; [cell.contentView addSubview:infoLabel]; } else { UILabel *theLabel = (UILabel *)[cell viewWithTag:101]; theLabel.text = [NSString stringWithFormat:@"%@", info.name]; } return cell; } </code></pre> <p>Also I am still using the code:</p> <pre><code>- (void)configureCell:(UITableViewCell *)cell atIndexPath:(NSIndexPath *)indexPath { FailedBankInfo *info = [_fetchedResultsController objectAtIndexPath:indexPath]; UILabel *theLabel = (UILabel *)[cell viewWithTag:101]; theLabel.text = [NSString stringWithFormat:@"%@", info.name]; } </code></pre> <p>To update the label text when the Core data object changes with the following code:</p> <pre><code>- (void)controller:(NSFetchedResultsController *)controller didChangeObject:(id)anObject atIndexPath:(NSIndexPath *)indexPath forChangeType:(NSFetchedResultsChangeType)type newIndexPath:(NSIndexPath *)newIndexPath { UITableView *tableView = self.tableView; switch(type) { case NSFetchedResultsChangeInsert: [tableView insertRowsAtIndexPaths:[NSArray arrayWithObject:newIndexPath] withRowAnimation:UITableViewRowAnimationFade]; break; case NSFetchedResultsChangeDelete: [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; break; case NSFetchedResultsChangeUpdate: [self configureCell:[tableView cellForRowAtIndexPath:indexPath] atIndexPath:indexPath]; break; case NSFetchedResultsChangeMove: [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; [tableView insertRowsAtIndexPaths:[NSArray arrayWithObject:newIndexPath] withRowAnimation:UITableViewRowAnimationFade]; break; } } </code></pre> <p>I also found sometimes when segueing back to the table view the table doesn't always update so to fix this you can use:</p> <pre><code>-(void) viewWillAppear { [self.tableView reloadData]; } </code></pre> <p>Thanks for all of your input it did help me come to a solution and I hope that this helps anyone else who is experiencing the same issue. I think I have explained it well enough. I'm not an expert by any means. Just another guy trying to build an App :)</p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload