13

我正在为CATiledLayer. 在 iPhone 4S 上生成 120 个 256 x 256 的 4 个细节级别的图块大约需要 11 秒。图像本身适合 2048 x 2048。

我的瓶颈是UIImagePNGRepresentation。生成每张 256 x 256 的图像大约需要 0.10-0.15 秒。

我尝试在不同的背景队列上生成多个图块,但这只会将其缩短到大约 9-10 秒。

我也尝试过使用 ImageIO 框架,代码如下:

- (void)writeCGImage:(CGImageRef)image toURL:(NSURL*)url andOptions:(CFDictionaryRef) options
{
    CGImageDestinationRef myImageDest = CGImageDestinationCreateWithURL((__bridge CFURLRef)url, (__bridge CFStringRef)@"public.png", 1, nil);
    CGImageDestinationAddImage(myImageDest, image, options);
    CGImageDestinationFinalize(myImageDest);
    CFRelease(myImageDest);
}

虽然这会生成更小的 PNG 文件(赢了!),但它需要大约 13 秒,比以前多 2 秒。

有什么方法可以CGImage更快地对 PNG 图像进行编码吗?也许像libjpeg-turbo这样使用NEONARM 扩展(iPhone 3GS+)的库呢?

是否有比 PNG 更好的格式来保存不占用大量空间的图块?

我能想到的唯一可行的选择是将图块大小增加到 512 x 512。这将编码时间减少了一半。不过,不确定这会对我的滚动视图产生什么影响。该应用适用于 iPad 2+,仅支持 iOS 6(以 iPhone 4S 为基准)。

4

1 回答 1

4

原来UIImageRepresentation表现如此糟糕的原因是因为它每次都在解压缩原始图像,即使我认为我正在使用CGImageCreateWithImageInRect.

您可以在此处查看 Instruments 的结果:

在此处输入图像描述

注意_cg_jpeg_read_scanlinesdecompress_onepass

这个强制解压缩图像:

UIImage *image = [UIImage imageWithContentsOfFile:path];
UIGraphicsBeginImageContext(CGSizeMake(1, 1));
[image drawAtPoint:CGPointZero];
UIGraphicsEndImageContext();

这个时间大约是 0.10 秒,几乎相当于每次UIImageRepresentation通话所用的时间。

互联网上有许多文章建议将绘图作为强制解压缩图像的一种方式。

有一篇关于 Cocoanetics Avoiding Image Decompression Sickness的文章。文章提供了另一种加载图像的方法:

NSDictionary *dict = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:YES]
                                                 forKey:(id)kCGImageSourceShouldCache];
CGImageSourceRef source = CGImageSourceCreateWithURL((__bridge CFURLRef)[[NSURL alloc] initFileURLWithPath:path], NULL);
CGImageRef cgImage = CGImageSourceCreateImageAtIndex(source, 0, (__bridge CFDictionaryRef)dict);
UIImage *image = [UIImage imageWithCGImage:cgImage];
CGImageRelease(cgImage);
CFRelease(source);

而现在同样的过程大约需要 3 秒!使用 GCD 并行生成图块可以更显着地减少时间。

上述writeCGImage功能大约需要 5 秒。由于文件大小较小,我怀疑 zlib 压缩级别更高。

于 2013-01-02T03:41:54.237 回答