dpassage
dpassage

Reputation: 5453

UITableViewCell content moving around

I have an iPhone app in which I'm using a UITableView to format a set of text responses, one per row. I've set up the cell in the storyboard to have a label inside it, and set up a constraint saying that the label should be 10 points from the edge of the cell. I then set up a custom subclass of UITableViewCell, set the cell in the storyboard to be of that class, and connected the outlet.

However, when I load the table, I see the text in the cell moving slightly to the right under some circumstances: when I select the cell, or when I load additional cells into the table. In fact, in the latter case, sometimes everything gets shifted to the right, even cells which were already there!

What the heck is going on here? The only changes I'm making in tableView:cellForRowAtIndexPath: are to the text in the label, and I'm always setting it. And I've unset "Indent While Editing" on the cell in the storyboard.

Answering some of the questions: I'm setting the view up using the storyboard. Xcode isn't reporting any ambiguity with the constraints. Also, here are the screenshots, before and after:

enter image description here enter image description here

Upvotes: 5

Views: 1310

Answers (6)

Dimitris
Dimitris

Reputation: 13670

I had a similar issue when the label would move when the cell was selected. It was a custom cell that I was loading from a custom Nib.

In the Nib I had not set the backgroundView of the UITableViewCell (superclass) to any view. Once I set it (I set it to the ContentView) the issue stopped.

My auto-layout constrains seems fine and had no issues, so I'm assuming it was the above that fixed it.

Upvotes: 0

TomSwift
TomSwift

Reputation: 39512

It might be worth checking to see that your string content doesn't have a space prefixed on it. Also, you could verify the actual position of the label by setting the background color.

Upvotes: 1

gstroup
gstroup

Reputation: 1064

This is just a guess without seeing your code. I had a similar problem once, when the app reused an existing cell, the dimensions of the label were not correct. So, I had to remove the old label in my cellForRowAtIndexPath method, before adding a new label. Here's how I removed the old one:

UIView *oldLabel = [cell viewWithTag:3];
if (oldLabel != nil)
{
    [oldLabel removeFromSuperview];
}

Then I added a new label like this:

[cell.contentView addSubview:newLabelOrWhatever];

Upvotes: 1

Jonathan
Jonathan

Reputation: 21

Did you add a new label to the UITableViewCell, or are you working with the textLabel that already exists in it? If you added a new one, consider removing it and using the cell's existing textLabel property instead. If that's not an option for some reason, double-check that the label you've added is in the contentView of the cell, and that all the constraints are relative to the parent view, not to the cell itself.

Also, for debugging, you could set the cell's contentView background color to red (cell.contentView.backgroundColor = [UIColor redColor];) - this might give you a better sense of what's moving, the label or the whole view.

Upvotes: 1

Kenn Cal
Kenn Cal

Reputation: 3679

If you have a custom subclass of UITableViewCell, try implementing layoutSubviews. Let me try from the top of my head:

static CGFloat const kLeftMargin = 10.0f;

- (void) layoutSubviews
{
  [super layoutSubviews];

  /* Prepare for processing */
  CGSize cellSize = self.bounds.size;

  /* Change the textLabel frame */
  {
    /* Compute the new label frame */
    CGSize labelSize = self.textLabel.bounds.size;
    CGFloat xCoor = kLeftMargin;
    CGFloat yCoor = roundf((cellSize.height - labelSize.height) / 2.0f);
    CGRect labelFrame = CGRectMake(xCoor, yCoor,
                                   labelSize.width, labelSize.height);

    /* Set the new label frame */
    self.textLabel.frame = labelFrame;
  }
}

Now, this isn't what is usually recommended (since a lot of people use Storyboards and NIBs), but from experience, if you want some correct layouting done, implement layoutSubviews.

Upvotes: -1

bilobatum
bilobatum

Reputation: 8918

My guess is that the constraints for the label are ambiguous. Ambiguity can make UI components jump around for inexplicable reasons. You probably need to set more constraints for the label to define its position on both axes.

Or, maybe all you need to do is set the label to the "size that fits content" (intrinsic content size) under the Editor menu in IB.

Upvotes: 1

Related Questions