[ WWDC2018 ] - 优化 App Assets Optimizing App Assets

概述

学习如何在你的应用通过使用assets达到最好的视觉效果和最高效的使用视图资源,概述了iOS12种的新特性。可以了解到如何使用assets分类来最优化的组织、优化、制作视图资源。可以学习到更好的简化设计和开发人员之间工作流程的一些手段。通过充分的使用视图asset,可以提高应用的交付质量,占用更小的空间,受益到更多的用户。

本文章主要介绍了使用asset分类的最佳实践,通过使用asset分类来优化应用资源的部署,下面将从图片压缩、设计和开发、分类以及部署流程这四个方面展开介绍

1.png

图片压缩

选择合适的压缩类型

2.png

图片压缩是asset分类的核心,asset分类默认会提供多种压缩类型,对于一种给定的图片或文字asset系统会默认选择最优的压缩类型,这种情况对于大多数的工程应该是已经足够用了。但是,如果能够详细的了解系统提供的这些可供调试参数的用途的话就能根据开发的环境作出做好的权衡。

自动图片打包

在assets分类之前使用的是自动图片打包的方式,将图片直接放到工程的bundle中组织。这种方式存在一些缺点和权衡。

不同的类型会存储各自的元信息和其他的一些属性信息,如果存在很多同类型的资源,这部新信息会冗余浪费多余的空间。对于一些小的资源文件,也没有进行充分的压缩。 就是在组织文件的时候,处理这些比较大的分散的图片资源会比较麻烦,而且调用的接口也不一样。 还要注意不同图片的不一致性。

assets分类会根据图片的图谱对图片进行分类通过图集的方式进行存储,帮我们处理图片的压缩以及元数据的存储工作。图片资源越大使用assets分类后优化的效果就越明显。

有损压缩

有损压缩主要是图片的质量和大小的权衡 适合于一些特定的场景下,比如一些显示时间比较短的图片资源

High Efficiency Image File Format

assets分类支持High Efficiency Image File Format,并且将High Efficiency Image File Format格式作为assets分类有损压缩的默认格式

比现有的格式图片更大的压缩率 支持透明度 assets分类可以自动将其他类型的图片转换为High Efficiency Image File Format,只要选择有损压缩的形式就会自动做这种转换无需做其他的额外的工作。

无损压缩

无损压缩是默认的压缩形式,工程中大部分assets分类都是使用的无所压缩。

3.png

图片资源可以根据使用的色谱和轮廓分为两类,不同的形式在有损压缩时会有不同的优化方式。一种是简单的图片资源,这类使用了简单的配色和使用简单的设计简单,例如很多应用的icon。另一类指的是复杂的图片资源。有损压缩针对这两种形式都做了不同形式的优化。

Apple Deep Pixel Image Compression

Apple Deep Pixel Image Compression是苹果新引入的一种压缩形式,这是一种灵活的压缩形式,会根据图片的色谱特性选择最优的算法进行压缩

会适配图片色谱 选择最优的压缩算法 压缩的大小能够提高15-20%

Size improvement

4.png

解码时间也会提高20%

5.png

部署版本和应用瘦身

6.png

由于为了使更多的用户使用,应用会向前兼容一些iOS版本。应用瘦身会根据不同的系统进行相应的优化,但以往的兼容形式无法向前兼容。因此,苹果推出了新的兼容方案OS Variant Thinning,会根据不同的系统进行瘦身,一直兼容到iOS9,并且在最新的系统上会使用最新的优化效果。

应用瘦身报告

打包后会生成报告包括不同版本的包大小、优化空间等信息

App variant export

7.png

Design and production

图片资源

资源来自很多不同的地方 都是人设计出来的 需要很多精力来组织资源文件

颜色管理

没有颜色的像素点只是字节! 颜色配置文件提供预期的显示样式 维护颜色配置文件 保持设计的样式 应用会在很广泛的显示样式上运行 颜色映射会在将对应的颜色映射到设备上

在编译的时候asset Catalogs会进行颜色的配对工作,这部分工作就不用在设备上来做了。并且这样做达到的额外的好处就是可以缩减颜色配置文件。

工作空间

针对所有设计文件的颜色配置保持一致性 sRGB / 8 bits是被广泛使用的颜色协议 Display P3 / 16 bits使用于生动的图像设计 提供了广泛灵活的颜色选项

Working with Wide Color WWDC 2016

图片拉伸

设计工具支持分片 区分可拉伸区域和不可拉伸区域

为了适配很多的设备和界面可能会遇到拉伸图片资源的情况。传统的方法是将图片分解开,然后在组合起来。这样做的缺点是最后组合起来的时候比较耗费cpu,而且实现起来可能稍微有点复杂。这种形式对于流行的gpu也不是很适合。

Single image + metadata = smooth GPU animation  

Asset Catalog “Show Slicing”

8.png 9.png

会根据拉伸的区域进行优化,按原有的尺寸进行设计,不需要考虑各种边界的情况

Asset Catalog分片逻辑

确保拉伸的元数据和图片资源一致 所有设计相关的逻辑都收敛到一处

Vector assets

不同的显示比率使用不同的asseasts(1x, 2x, 3x) 将所有需要的asset数组组合成一个PDF格式 Xcode会根据不同的显示比例生成优化的bitmaps 保持数组数据可以在运行时尺寸改变时动态调整
如果大于自然的尺寸会通过数组数据来优化大小改变时的显示效果,

Design for 2x

Retina 2X是最常用的显示比例 没有像素点对齐的时候还是会出现虚的情况 将边缘的点和像素对齐可以使设备的像素点对齐 数组资源可以使用2x格来优化没有像素点对齐的情况
将2x的素材放入2x的槽内,Xcode会自动生成其他比例的素材

Assets提示

如果还是有问题的话可以手动根据提示拖入指定的槽位,这样会更可控一些

分类

提供很多选项 只使用需要用到的部分
我们提供了很强的处理引擎和有组织模式提供给使用者很多的能力,建议实用之初尽量使用需要到的简单的方法。

Bundles

对于大规模的工程来说bundle组织是一个挑战 通过多个bundle来解决这个问题 高效的重用策略

大工程都放到主bundle里面难以维护、要保证命名不会冲突 xcode会把所有的图片资源都针对每个target打到一个bundle里面。可以将图片资源打到一个bundle里面,使用一致的命名空间,可以方便复用。

UIImage(named: UIImage.Name, in: Bundle, compatibleWith: UITraitCollection) Bundle.image(forResource: NSImage.Name) -> NSImage?  

通过指定bundle获取bundle内的图片

每一个单独的bundle都会提供一个唯一的命名空间,这样bundle之间就不会有命名冲突的情况

Namespaces

大的集合对于命名来说是一个挑战 带命名空间目录是用来分组的

10.png

选中provides namespace会在asset catalog中对应图片会自动添加目录路径

部署

App Thinning

提供不同设备所需的所有内容,应用瘦身会根据每个设备选取对应的子集

Performance classes

硬件的能力不同 不需要限制可兼容设备! 通过可适配的资源来解决这些问题
通过性能分类来进行优化
内存分类

11.png

图像能力分类

12.png

分为两个方面,一个是metal属性,Metal 是一种低层次的渲染应用程序编程接口,提供了软件所需的最低层,保证软件可以运行在不同的图形芯片上。另一个方面是特定版本的处理器

能力矩阵

通过能力矩阵我们就能适配我们的assets资源

13.png

提供了三种指定的assets,一种是为了兼容老版本的,另外两个是优化的2g下的Metal4的另一个是3G下的Metal3的。 我们举例通过iphone 8来选择。4g下没有找到,在3g下找到了metal3的。尽管有GPU完全匹配的选项,但是由于我们的策略是内存优先的,因为内存对总体的性能影响会更大,所以最后选择了3g下找到了metal的asset。

Using Performance Classes

Higher memory —> larger / richer assets  
Higher graphics —> more complex assets  

对于比较大的或交互比较丰富,还有比较需要显示很多细节的图片资源最好使用内存优先的形式,这样用户体验会更好一些。 一些复杂的图片资源对CPU和GPU要求比较高更适合使用图像优先的方式。

NSDataAsset可以提供灵活的容器

可以放在asset分类里,内容可以是任何类型的文件,可以利用性能分类的功能来做文件的选择和路由。

例如可以根据不同的设备的类型通过性能分类获取到对应的plist文件

Sprite atlases

SpriteKit是对文本图片进行动画的一个图像渲染和动画构建的库

将所有相关图片打包成一个整体 整个图集一次性加载

图片通过图集中位置来引用

通过UIImage / NSImage 获取图片

在一些特殊的场合使用异步加载
SKTextureAtlas.preloadTextureAtlasesNamed(_: [String],  
withCompletionHandler: (Error?, [SKTextureAtlas]) -> Void)  

这个方法耗费I/O和内存的操作,使用时需谨慎

Xcode通过像素格式、设备特性和压缩类型自动进行应用瘦身的优化

asset分类的特性也都应用到了Sprite atlases上了

总结

Optimizing App Assets

图片资源最好的选择 在iOS12的应用上可以减少10-20%的空间 应用瘦身功能针对最新的系统进行了优化 可以在应用中使用分类功能来适配资源

文章来源:

Author:caojiaxin
link:https://techblog.toutiao.com/2018/06/19/untitled-41/