7

将 PNG 添加到 XCode iPhone 项目时,编译器会使用 pngcrush 对其进行优化。一旦在设备上,图像的渲染性能非常快。

我的问题是我的应用程序在运行时从外部源(从 Picasa 网络相册,使用 Google 数据 API)下载其 PNG。不幸的是,这些图像的性能很差。当我在图像上进行自定义渲染时,它似乎比其内部存储的对应物慢 100 倍。我强烈怀疑这是因为下载的图像尚未优化。

有谁知道如何在 iPhone 上运行时优化外部下载的 PNG?我希望有一堂课能做到这一点。我什至考虑将 pngcrush 的源代码添加到我的应用程序中,这似乎很激烈。我自己也找不到合适的答案。我将非常感谢任何帮助。

谢谢!

更新:有些人建议这可能是由于文件的大小,但事实并非如此。在我的测试过程中,我添加了一个切换按钮,用于在使用嵌入式版本和下载完全相同的 PNG 版本之间进行切换。唯一的区别是嵌入式的在编译过程中被“pngcrush”优化了。这会进行一些字节交换(从 RGBA 到 BRGA)和 alpha 的预乘。(http://iphonedevelopment.blogspot.com/2008/10/iphone-optimized-pngs.html

另外,我指的性能不是下载,而是渲染。我将自定义绘画叠加在图像之上(覆盖 UIView 的 drawRect 方法),当背景是下载版本时非常不稳定,而当它是嵌入式(因此优化)版本时非常流畅。同样,它是完全相同的文件。唯一的区别是优化,我希望我可以在运行时,在设备上,下载后对图像执行。

再次感谢大家的帮助!

4

7 回答 7

7

您发布的那个链接几乎可以回答您的问题。

在构建过程中,XCode 会对您的 png 进行预处理,因此它的格式对 iPhone 中的图形芯片更友好。

尚未像这样处理的 Png 可能会使用较慢的渲染路径,该路径处理非原生格式以及必须为每种颜色单独计算 alpha 的事实。

所以你有两个选择;

  1. 执行与 pngcrush 相同的工作并交换排序/预乘 alpha。加速可能是由于其中之一或两者。

  2. 加载图像后,您可以从中“创建”新图像。这个新图像应该是 iPhone 的本机格式,因此性能应该更快。缺点是它可能会占用更多内存。

例如

CGRect area = CGRectMake(0, 0, width, height);
CGSize size = area.size;
UIGraphicsBeginImageContext(size);

[oldImage drawInRect:area];

UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
于 2009-03-13T18:29:36.147 回答
3

你说它“似乎”慢了 100 倍这一事实表明你没有进行任何实验,但做了一个猜测(它必须是 PNG 优化),并且现在正在沿着基于预感的路径前进。

在尝试解决问题之前,您应该花时间确认问题所在。我的直觉说PNG优化不应该是问题:这主要影响图像的加载,但是一旦它们在内存中,它们最初的文件格式就无关紧要了。

无论如何,您应该尝试 AB 比较,或者让您的代码从其他地方加载优化的 PNG 并查看它的比较情况,或者制作一个仅在两种 PNG 类型上进行一些绘图的测试应用程序。一旦您确认了问题所在,您就可以确定是否需要将 pngcrush 编译到您的应用程序中。

于 2009-03-13T00:33:54.687 回答
2

从表面上看,这听起来像是有别的东西在起作用。任何额外的图像处理都只会增加时间,直到它显示在屏幕上......

是否有可能通过发送适当的 HTTP 标头让服务器对图像进行 gzip 压缩?(如果它甚至对文件大小有很大帮助,那就是。)

暂时使用 pngcrush 源可能也是一个很好的测试,只是为了获得一些测量结果。

于 2009-03-13T00:08:57.087 回答
1

好吧,似乎一个好方法(因为你不能在 iPhone 上运行 pngcrush 并期望它加快速度)是通过运行 pngcrush 的代理发出你的请求。代理将具有很好的马力,实际上可以让您在 100 倍的痛苦中获得一些收益。

于 2009-03-13T03:19:54.710 回答
1

您是否以原始下载大小存储 png?如果是大图像,则渲染时间会更长。

于 2009-03-12T23:47:01.227 回答
1

尝试 pincrush 将正常的 png 文件转换为粉碎的 png 文件

于 2010-10-08T06:55:14.300 回答
0

drawRect:你说你通过覆盖 UIView 的方法在图像之上绘图。您是否尝试通过在其上重复绘制整个图像和自定义内容来制作一些动画?

如果您将自定义内容放在单独的视图或图层中,并让操作系统处理在背景上合成结果,您可能会获得更好的结果。操作系统只会更新您实际更改的屏幕部分,而不会经常重新绘制整个图像。

于 2009-03-13T20:24:05.980 回答