UITableViewCell仅在滚动时正确布局

时间:2013-12-27 08:09:22

标签: ios iphone objective-c uitableview

我有UITableView个自定义UITableViewCells。根据我从服务器收到的文本,单元格需要具有不同的高度。我按如下方式改变高度:

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (indexPath.row == 0)
        return [self getHeightOfQuestion];
    else if (indexPath.row == 1)
        return 64.0f;
    else // ****** this is the cell in question!
        return [self getHeightOfAnswerAtIndexPath:indexPath];
    return 300.0f;
}

]- (CGFloat) getHeightOfAnswerAtIndexPath:(NSIndexPath*) indexPath
{
    CGRect answerFrame = CGRectZero;
    if ([QXTUtility currentOsVersion] >= 7.0f)
    {
        answerFrame = [[[[self.answerDetails objectForKey:kAnswers] objectAtIndex:indexPath.row-2] objectForKey:kAnswerText] boundingRectWithSize:CGSizeMake(242.0f, 900.0f) options:NSStringDrawingUsesLineFragmentOrigin attributes:@{NSFontAttributeName:[UIFont fontWithName:@"Roboto-Light" size:14.0f]} context:nil];
    }
    else
    {
        CGSize answerSize = [[[[self.answerDetails objectForKey:kAnswers] objectAtIndex:indexPath.row-2] objectForKey:kAnswerText] sizeWithFont:[UIFont fontWithName:@"Roboto-Light" size:14.0f] constrainedToSize:CGSizeMake(242.0f, 500.0f) lineBreakMode:NSLineBreakByTruncatingTail];
        answerFrame.size = answerSize;
    }
    NSLog(@"Frame %@", NSStringFromCGRect(answerFrame));

    return answerFrame.size.height + 50;
}

在iOS6上运行正常。但在iOS7中,我得到以下输出:

enter image description here

但是,如果我再次滚动UITableView,那么单元格完全如下:

enter image description here

这是我的cellForRowAtIndexPath

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *answerCellIdentifier = @"QXTAnswerCell";

    QXTAnswerCell *answerCell = (QXTAnswerCell *)[tableView dequeueReusableCellWithIdentifier:answerCellIdentifier];
    if (answerCell == nil)
    {
        NSArray *nib = [[NSBundle mainBundle] loadNibNamed:@"QXTAnswerCell" owner:self options:nil];
        answerCell = [nib objectAtIndex:0];
    }
    [self setDataToAnswerCell:answerCell AtIndexPath:indexPath];
    [self layoutAnswerCell:answerCell AtIndexPath: indexPath];
    [answerCell setNeedsLayout];
    return answerCell;

}

- (void) layoutAnswerCell:(QXTAnswerCell*) answerCell
              AtIndexPath:(NSIndexPath*) indexPath
{
    CGRect answerCellFrame = answerCell.answer.frame;
    answerCellFrame.origin.y = answerCell.name.frame.origin.y + answerCell.name.frame.size.height + 6;
    if ([QXTUtility currentOsVersion] >= 7.0f)
    {
        answerCellFrame.size.height += 30.0f;
        answerCell.answer.lineBreakMode = NSLineBreakByWordWrapping;
    }
    answerCell.answer.frame = answerCellFrame;
    dispatch_async(dispatch_get_main_queue(), ^{
        [answerCell setNeedsLayout];
    });
}

请帮帮我。一旦填写了答案的数据源,我就会调用重新加载数据。 感谢。

更新

刚刚发现,一旦从服务器收到答案,就不会调用第一个reloadData

// Delegate from Network Class
- (void) answersReceivedWithDetails:(id)answerDetails
{
    NSLog(@"Answer Details %@", answerDetails);
    self.answerDetails = [[NSMutableDictionary alloc] initWithDictionary:answerDetails];
    [self.tableView reloadData];
    [self.tableView setNeedsDisplay];
}

这是细胞的限制因素:

enter image description here

2 个答案:

答案 0 :(得分:1)

以下是我为解决问题所做的工作。使用IBOutlets创建的boundingRectWithSizeUILabels存在一些问题。所以我做了以上操作,然后将其分配给使用代码创建的UILabel并将其添加到单元格中。一切都运作良好!

- (void) layoutAnswerCell:(QXTAnswerCell*) answerCell
              AtIndexPath:(NSIndexPath*) indexPath
{
    if ([QXTUtility currentOsVersion] >= 7.0f)
    {
        [answerCell.answer removeFromSuperview];
        NSString *answerString = <your string>
        CGRect answerFrame = [answerString boundingRectWithSize:CGSizeMake(242.0f, 900.0f) options:NSStringDrawingUsesLineFragmentOrigin attributes:@{NSFontAttributeName:[UIFont fontWithName:@"Roboto-Light" size:14.0f]} context:nil];
        answerFrame.origin.x = 20.0f;

        answerFrame.origin.y = answerCell.name.frame.origin.y + answerCell.name.frame.size.height + 6;
        answerFrame.size.height = ceilf(answerFrame.size.height);
        answerFrame.size.height += 30.0f;
        answerCell.answer.lineBreakMode = NSLineBreakByTruncatingTail;
        answerCell.answer.frame = answerFrame;

        UILabel *newLabel = [[UILabel alloc] initWithFrame:answerFrame];
        [newLabel setFont:[UIFont fontWithName:@"Roboto-Light" size:14.0f]];
        newLabel.text = answerString;
        newLabel.numberOfLines = 0;
        [answerCell.contentView addSubview:newLabel];
        [answerCell setNeedsDisplay];
    }
}

看看这是否适用于其他任何人。如果是这样的话,我会接受这个答案。但确实为我完成了工作。

答案 1 :(得分:0)

我认为问题在于在 tableView中返回正确的高度:heightForRowAtIndexPath:

它始终在indexPath.row = 1

返回64.0f
static CGFloat answerCellDefaultHeight = 200.0f; //change this to the actual value of the height of the answer table cell

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
    if (indexPath.row == 0) {
        return [self getHeightOfQuestion];
    } else if (indexPath.row == 1) {
        return 64.0f; 
    } else {
        CGFloat computedHeight = [self getHeightOfAnswerAtIndexPath:indexPath];
        return (computedHeight > answerCellDefaultHeight) ? computedHeight : answerCellDefaultHeight;
    }
}