27

好的,我有一个UITableViewwith custom UITableViewCell,每个都包含一个UIImageView通过NSURLConnection. 所有非常标准的东西......

问题是,当表格滚动时,新图像会在后台正确下载,但在表格停止移动之前不会渲染。

即使在移动时,如何让表格呈现其内容?谢谢。

- 更新 -

仔细观察后,我发现NSURLConnection在表格停止滚动之前,委托方法不会触发。不知道为什么。任何帮助都会很棒。

4

4 回答 4

65

在您停止滚动之前连接委托消息不会触发的原因是因为在滚动期间,运行循环位于UITrackingRunLoopMode. 默认情况下,仅NSURLConnection自行安排NSDefaultRunLoopMode,因此您在滚动时不会收到任何消息。

以下是在“常见”模式下安排连接的方法,其中包括UITrackingRunLoopMode

NSURLRequest *request = ...
NSURLConnection *connection = [[NSURLConnection alloc]
                               initWithRequest:request
                               delegate:self
                               startImmediately:NO];
[connection scheduleInRunLoop:[NSRunLoop currentRunLoop]
            forMode:NSRunLoopCommonModes];
[connection start];

请注意,您必须startImmediately:NO在初始化程序中指定,这似乎与 Apple 的文档背道而驰,该文档建议您即使在启动后也可以更改运行循环模式。

于 2010-01-03T15:45:16.703 回答
1

你应该阅读 NSRunLoop。我怀疑,在滚动期间,运行循环在 NSEventTrackingRunLoopMode 中运行,并且 NSURLConnection 不包含在该模式中。你可以通过调用 NSURLConnection 的 scheduleInRunLoop:forMode: 来解决这个问题,这样下载就可以在滚动期间进行。

这可能会影响滚动性能,这可能首先是单独运行循环模式的原因。但是尝试一下,看看感觉如何!

于 2009-12-01T20:30:39.990 回答
1

如果您将图像下载和更新包装在 NSOperation 中,则更新将随着 table-view 滚动而发生。

NSOperation 的另一个好处是,您可以在单元格滑出屏幕时取消操作。它会感觉对用户反应更快。尤其是当他们快速滚动长列表时。今年的 Apple 技术讲座鼓励了这种技术。

如果您的列表不是那么长,或者您希望它们继续加载,则可以改为操纵 NSOperation 优先级。

于 2009-12-07T19:41:07.183 回答
0

首先......您的连接可能直到它到达 mainRunLoop 才开始,这也是滚动动画正在处理的地方。

我遇到了同样的问题并通过告诉图像的连接在创建后立即启动来解决它。

    NSURLConnection *connection = [[NSURLConnection alloc] initWithRequest:wrapper.request delegate:wrapper];

    [connection start];

在您接收图像并将 cell.imageView.image 设置为接收到的图像的完成例程中,您应该检查此单元格是否属于当前在表格中显示的单元格之一......如果是,请调用 [表视图重新加载数据]。

    NSInteger itemIndex = theIndexInTheRowDataOfTheCellYouStuffedTheImage

    NSArray *indicies = [_tableView indexPathsForVisibleRows];
    NSUInteger rows = indicies.count;

    if (rows > 0 &&
        itemIndex >= ((NSIndexPath *)[indicies objectAtIndex:0]).row &&
        itemIndex <= ((NSIndexPath *)[indicies objectAtIndex:rows - 1]).row)
    {       
        [_tableView reloadData];
    }
于 2009-12-02T23:47:50.383 回答