小编JBx*_*JBx的帖子

在UI线程上懒洋洋地加载CGImage/UIImage会导致口吃

我的程序显示一个水平滚动表面,从左到右平铺UIImageViews.代码在UI线程上运行,以确保新显示的UIImageViews分配了一个新加载的UIImage.加载发生在后台线程上.

一切都很好,除了每个图像变得可见时都有口吃.起初我以为我的后台工作者在UI线程中锁定了一些内容.我花了很多时间查看它,并最终意识到UIImage在UI线程第一次变得可见时正在做一些额外的延迟处理.这让我很困惑,因为我的工作线程有明确的解压缩JPEG数据的代码.

无论如何,在预感上,我写了一些代码,以渲染到后台线程上的临时图形上下文中 - 当然,口吃也消失了.UIImage现在正在我的工作线程上预先加载.到现在为止还挺好.

问题是我的新"强力懒惰的图像"方法是不可靠的.它会导致间歇性的EXC_BAD_ACCESS.我不知道UIImage在幕后实际上在做什么.也许它正在解压缩JPEG数据.无论如何,方法是:

+ (void)forceLazyLoadOfImage: (UIImage*)image
{
 CGImageRef imgRef = image.CGImage;

 CGFloat currentWidth = CGImageGetWidth(imgRef);
 CGFloat currentHeight = CGImageGetHeight(imgRef);

    CGRect bounds = CGRectMake(0.0f, 0.0f, 1.0f, 1.0f);

 CGAffineTransform transform = CGAffineTransformIdentity;
 CGFloat scaleRatioX = bounds.size.width / currentWidth;
 CGFloat scaleRatioY = bounds.size.height / currentHeight;

 UIGraphicsBeginImageContext(bounds.size);

 CGContextRef context = UIGraphicsGetCurrentContext();
 CGContextScaleCTM(context, scaleRatioX, -scaleRatioY);
 CGContextTranslateCTM(context, 0, -currentHeight);
 CGContextConcatCTM(context, transform);
 CGContextDrawImage(context, CGRectMake(0, 0, currentWidth, currentHeight), imgRef);

 UIGraphicsEndImageContext();
}
Run Code Online (Sandbox Code Playgroud)

并且EXC_BAD_ACCESS发生在CGContextDrawImage行上.问题1:我是否允许在UI线程以外的线程上执行此操作?问题2:什么是UIImage实际上"预加载"?问题3:解决这个问题的官方方法是什么?

感谢阅读所有这些,任何建议将不胜感激!

iphone lazy-loading exc-bad-access uiimage cgimage

12
推荐指数
3
解决办法
1万
查看次数

标签 统计

cgimage ×1

exc-bad-access ×1

iphone ×1

lazy-loading ×1

uiimage ×1