我已将此UICollectionViewDelegate添加到我的实现中:
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
SAPCollectionViewCell *collectionViewCell = (SAPCollectionViewCell *)[collectionView dequeueReusableCellWithReuseIdentifier:@"SAPCollectionViewCell" forIndexPath:indexPath];
NSInteger index = indexPath.item + indexPath.section * 2;
NSString *imagePath = [_images objectAtIndex:index];
collectionViewCell.index = index;
[collectionViewCell setImageWithPath:imagePath];
collectionViewCell.delegateCell = self;
return collectionViewCell;
}
在我的自定义单元格中,我有这种方法:
- (void)setImageWithPath:(NSString *)imagePath
{
if (!self.imageView)
{
CGRect rect = self.contentView.frame;
self.imageView = [[UIImageView alloc] initWithFrame:rect];
[self.contentView addSubview:self.imageView];
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
UIImage *image = [UIImage imageFromPath:imagePath];
UIImage *resizedImage = [UIImage imageWithImage:image scaledToWidth:rect.size.width];
dispatch_async(dispatch_get_main_queue(), ^{
[self.imageView setImage:resizedImage];
});
});
}
}
因此,您可以看到单元格是否没有UIImageView然后我开始创建它,在后台我从本地路径获取图像并将其调整为单元格内容视图宽度,然后在主队列中将图像设置为UIImageView。 / p>
这部分工作正常,但是当我尝试滚动我的UICollectionView时,例如有10个图像我注意到,例如,当我向下滚动时,前2个顶部图像消失,然后当我滚动回到顶部时,图像被更改放置。
这是向下滚动前的图像状态:
在我将UIColectionView
滚动到顶部之后的状态:
因此,您可以看到第一项改变了他们的位置。正如我在上面的代码中设置了if (!self.imageView)
,它应该意味着图像永远不会被创建两次或更多次。
我打开调试器并检查此方法:
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
因此,当UICollectionView刚刚第一次创建单元格时,图像路径逐个返回。
第一次第一次UICollectionViewCell有0x8fbc1d0 第二个是0x8d0a4c0地址
但是当我向下滚动然后向上滚动调试器时,首先显示第二个地址为0x8d0a4c0,然后显示为0x8fbc1d0
但我无法理解为什么物品会改变他们的顺序。或者这可能是另一个问题?
此外,我在代码中没有任何方法可以让我为单元重新排序。只有少数UICollection视图方法委托配置单元格数并创建它们。
此外,如果我删除if (!self.imageView)
似乎一切正常,但我的代码每次调用对我都不利的调度,因为当我将图像调整为单元格大小时,我不需要做两次。< / p>
答案 0 :(得分:0)
当您将两个项目滚动到屏幕外时,您的CollectionView
会将关联的单元格放回“队列”中。当您再次向上滚动时,dequeueResuableCellwithReuseIdentifier
中的cellForItemAtIndexPath
会从该队列中检索它们,但(正如您所见)不一定按相同顺序。因此,项目0的单元格已用于项目1,反之亦然。正如您所见,if (!self.imageView)
实际上会阻止加载正确的图像。如果你想避免每次都检索和调整它们,那么我会将(调整大小的)imageViews存储在一个数组中。
答案 1 :(得分:0)
- (void)setImageWithPath:(NSString *)imagePath
{
if (!self.imageView)
{
CGRect rect = self.contentView.frame;
self.imageView = [[UIImageView alloc] initWithFrame:rect];
[self.contentView addSubview:self.imageView];
}
if (![self.imagePath isEqualsToString:imagePath] && self.imageView.image == nil)
{
self.imagePath = imagePath;
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
UIImage *image = [UIImage imageFromPath:imagePath];
UIImage *resizedImage = [UIImage imageWithImage:image scaledToWidth:rect.size.width];
dispatch_async(dispatch_get_main_queue(), ^{
if ([self.imagePath isEqualsToString:imagePath])
{
[self.imageView setImage:resizedImage];
}
});
});
}
}