UIcollectionView cellForItemAtIndexPath仅在iOS 10中返回Null.适用于iOS 9和iOS 8

Joe*_*nni 3 ios uicollectionview uicollectionviewcell ios10 xcode8

我有一个应用程序,愉快地运输了几年.它在UICollectionView中检索RSS源.cellForItemAtIndexPath方法设置文本并调用数据源方法以从源中指定的链接加载图像.如果不存在,则加载网页数据并搜索<img>标签以获取图像.找到/加载图像后,调用委托方法将图像添加到单元格.(下面)

当在iOS 8和9中运行时,一切都很开心,但是当在iOS 10中运行时,可视单元格在最初加载RSS源时用图像更新但滚动时没有添加图像,我从cellForItemAtIndexPath获得NULL.

当我向后滚动时显示图像,如果我向imageWasLoadedForStory添加reloadItemsAtIndexPaths但是reloadItemsAtIndexPaths会破坏性能,则会显示图像.

- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
           // ...    

          if (story.thumbnail) {
          [imageView setAlpha: 1.0];
          imageView.image = story.thumbnail;
          UIActivityIndicatorView *lActivity = (UIActivityIndicatorView *) [collectionView viewWithTag: 900];
          [lActivity removeFromSuperview];
          }else{
               [story setDelegate: self];
               [story findArticleImageForIndexPath: indexPath];
          }
          //  ...
}



//delegate method.  Called when image has been loaded for cell at specified indexpath

- (void) imageWasLoadedForStory: (RSSStory *) story forIndexPath: (NSIndexPath *) indexPath
{
        //get cell
        CustomCollectionViewCell *customCell = (id) [self.collectionview cellForItemAtIndexPath: indexPath];

        NSLog(@"imageWasLoadedForStory row %i section %i  and class %@", (int)indexPath.row, (int)indexPath.section, [customCell class]);

        //if cell is visible ie: cell is not nil then update imageview
        if (customCell) {
                 UIImageView *imageView = (UIImageView *) [customCell viewWithTag: 300];
                 imageView.image = story.thumbnail;
                 UIActivityIndicatorView *lActivity = (UIActivityIndicatorView *) [customCell viewWithTag: 900];
                 [lActivity removeFromSuperview];
                 [customCell setNeedsLayout];
                 [customCell setNeedsDisplay];
                 }
                    //[self.collectionview reloadItemsAtIndexPaths: [NSArray arrayWithObject: indexPath]];           
}



- (void) findArticleImageForIndexPath: (NSIndexPath *) indexPath
{
           //kick off image search
           dispatch_async( dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{

                self.thumbnail = [self findArticleForStoryForIndexPath:indexPath];
                dispatch_async( dispatch_get_main_queue(), ^{
                //image set - return
                      [self.delegate imageWasLoadedForStory: self forIndexPath: indexPath];
                });
        });
}
Run Code Online (Sandbox Code Playgroud)

Joe*_*nni 20

我鼓励大家阅读Prefetching - iOS 10中的新功能.简单的解决方案是:

[self.customCollectionview setPrefetchingEnabled:NO];
Run Code Online (Sandbox Code Playgroud)

事实证明,细胞现在已被预取.这意味着加载/不可见细胞和加载/可见细胞之间现在存在差异.

在iOS 10中,现在可以预加载一个单元格,但如果它不可见,它仍将返回nil.因此调用cellForItemAtIndexPath来预加载单元格.然后完全有可能图像将完成加载,如果单元格不可见,则cellForItemAtIndexPath将返回nil.这意味着不会设置imageView.滚动时,由于单元格已经创建,因此不会将图像添加到单元格中.

在UITableView或UICollectionView上加载vs可见单元格