滚动时UITableCell内容损坏

时间:2012-06-02 05:41:29

标签: objective-c ios uitableview

我有一个带有UIWebView的单元格的UITableView,我有两个问题。首先,Web视图覆盖了它所在的单元格,因此它使单元格看起来有点奇怪。

第二个更严重的问题和这个主题的主要问题是滚动表时发生的损坏。随机地,Web视图将在错误的单元格中呈现,并且滚动得越快,越多的单元格就像这样被破坏。如果我慢慢滚动,所有渲染都应该如此。

最初绘制表时,它会正确呈现。当用户滚动表格时,它才会开始变坏。当它弄乱时,UIWebView出现在一些不应该出现的单元格上。这种情况会发生,除非你慢慢滚动,滚动得越快就越糟糕。这不仅仅是一个图形故障,因为在这些单元格中存在活动的实时Web视图,而不应该存在。我还注意到,我的手机配件图标在第一个单元格上从无,也变为显示三角形。我尝试发布一些这样的图片,但我太新了不允许(垃圾邮件发送者破坏了每个人的乐趣)

这是我的cellForRowAtIndexPath代码。请温柔我只是在学习这一切是如何运作的。 :)

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifierMediaType];
    switch ([indexPath section]) {
        case 0: {
            if (!cell) {
                cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierLongDescription];
            }
            [cell.contentView addSubview:self.longDescriptionWebView];
            break;
        }
        case 1: {
            if (!cell) {
                cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierMediaType];
            }
            NSDictionary *cellDict = [self.subMediaTypes objectAtIndex:[indexPath row]];
            cell.textLabel.text = [cellDict objectForKey:@"SHORT_DESCRIPTION"];
            break;
        }    
        default:
            if (!cell) {
                cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierMediaType];
            }
            break;
    }

    return cell;
}

首先,我尝试在cellForRowAtIndexPath中定义重用单元格但是产生了相同的结果,因此我将单元格移出并将它们设置为实例变量。这也有效,但我仍然有腐败问题所以我猜我在哪里设置重用单元真的没关系。这是我设置重用单元格的代码块。

if (!self.mediaTypeCell) self.mediaTypeCell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierMediaType];
if (!self.longDescriptionCell) self.longDescriptionCell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierLongDescription];
if (!self.longDescriptionWebView) self.longDescriptionWebView = [[UIWebView alloc] initWithFrame:self.longDescriptionCell.bounds];
self.mediaTypeCell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
self.longDescriptionCell.accessoryType = UITableViewCellAccessoryNone;
[self.longDescriptionCell.contentView addSubview:self.longDescriptionWebView];
self.longDescriptionCell.contentView.autoresizesSubviews = YES;
self.longDescriptionWebView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
[self.longDescriptionWebView loadHTMLString:self.mediaTypeLongDescription baseURL:nil];

该表只需要两种类型的单元格。有一个没有附件的单元格包含Web视图(longDescriptionCell),表格的其余部分包含带有公开指示器附件的简单文本字符串(mediaTypeCell)的单元格。

1 个答案:

答案 0 :(得分:0)

所以...我们应该从哪里开始......?

一般来说,在单元格内使用uiwebview(uiscrollview)并不是一个好主意。 但这并非不可能,你只需要关心它,所以,如果你只是想学习如何使用表格,你可以从更简单的事情开始......

顺便说一下,你正在做的更大的错误:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
// (..)
       if (!cell) {
            cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifierLongDescription];
        }
        [cell.contentView addSubview:self.longDescriptionWebView];
// (..)
} 

每次表格需要显示一个单元格时,都会使用并调用此协议方法,因此它会在第一次显示(对于每个单元格)以及用户向下和向上滚动时运行。

表的神奇之处在于重用在屏幕外上升的单元格(如果用户向下滚动),以便在向下数据所需的新数据下重用相同的单元格。

你应该问这样的事情:

   UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifierMediaType];

该代码只询问是否存在可用于新所需数据的未使用单元格。 此时,如果它不存在,我们需要分配一个新的并设置它的对象以显示正确的数据。

但如果它存在,我们不需要分配一个新的(这就是你正在做的,好的) 我们应该在其中添加新对象(或者我们应该删除其中的旧对象)

每次滚动时都会添加一个Web视图,并将其添加到旧视图上,其中包含:

       [cell.contentView addSubview:self.longDescriptionWebView];

这是一个很大的错误,您应该重复使用旧的webView,告诉它加载一个新的html页面(或者你在其中显示的其他内容)

还有一件事:当你使用

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifierMediaType];

您要求id为CellIdentifierMediaType

的现有单元格

然后你问并使用不同的id细胞(CellIdentifierLongDescription)