TextureFilters(MipMap 生成)如何影响性能?
How does TextureFilters (MipMap generation) affect performance?
我一直在读到选择纹理过滤器(特别是 MipMap 生成)可能会对应用程序的性能产生影响,但我无法真正理解它是如何工作的。那么几个问题:
- MipMap 是每帧生成还是仅在加载纹理时生成一次?
- 如果每一帧,如果场景从一帧到另一帧是静态的(纹理大小和位置是恒定的),它是否仍然会重新生成。就像如果你有一个静态 UI 使用 MipMap 过滤时性能会更差吗?
- 如果只有一次,为什么会影响性能,以何种方式?
我想知道,因为我发现使用时一切看起来都好多了(在 LibGDX):
param.genMipMaps = true;
param.minFilter = TextureFilter.MipMapLinearLinear;
param.magFilter = TextureFilter.Linear;
但为什么不这样做 standard/best 呢?有什么缺点?如果对于我的应用程序,它不会降低 fps,还有其他缺点吗?更多 GPU/CPU 密集?电池消耗更高(对于移动设备)?
只要纹理数据发生变化,就必须生成 Mipmap。只要纹理不变,也不需要重新创建它们。
它们会影响性能,因为每个纹素的读取操作都会变慢。根据您使用的过滤器类型,GPU 必须从多个 mipmap 级别读取多个纹素来计算最终颜色。
例如,GL_NEAREST
将仅读取 1 个纹素,而 return 则为。 GL_LINEAR
已经必须从一个 mipmap 级别读取 4 个纹素并执行双线性插值。如果您现在启用 mipmapping,那么来自第二个纹理级别的信息也会影响结果。使用 GL_LINEAR_MIPMAP_LINEAR
,GPU 将在大于所需大小的 mipmap 级别执行一次线性查找(4 个纹素),并在小于请求大小的 mipmap 级别执行一次线性查找。然后将对这两个查找的结果进行插值以获得最终颜色。所以总而言之,GL_LINEAR_MIPMAL_LINEAR
查找可能会读取 8 个纹素并执行 2 个双线性插值和两个级别之间的线性插值 (trilinear interpolation)。
另一个考虑因素是 GPU 内存消耗。 Mipmaps 需要存储在 gpu 上的某个地方,并且比没有 mipmaps 多占用大约 1/3 space。
有关 Mipmapping 的更多详细信息,还应阅读 Wikipedia Article which explains the concept very well. As stated by others in comments, also this blog 对纹理过滤方法进行了很好的概述。
注意,这里的解释假设二维纹理。另请注意,
显卡可以很好地优化该过程,但所描述的技术在理论上是如何工作的。
我一直在读到选择纹理过滤器(特别是 MipMap 生成)可能会对应用程序的性能产生影响,但我无法真正理解它是如何工作的。那么几个问题:
- MipMap 是每帧生成还是仅在加载纹理时生成一次?
- 如果每一帧,如果场景从一帧到另一帧是静态的(纹理大小和位置是恒定的),它是否仍然会重新生成。就像如果你有一个静态 UI 使用 MipMap 过滤时性能会更差吗?
- 如果只有一次,为什么会影响性能,以何种方式?
我想知道,因为我发现使用时一切看起来都好多了(在 LibGDX):
param.genMipMaps = true;
param.minFilter = TextureFilter.MipMapLinearLinear;
param.magFilter = TextureFilter.Linear;
但为什么不这样做 standard/best 呢?有什么缺点?如果对于我的应用程序,它不会降低 fps,还有其他缺点吗?更多 GPU/CPU 密集?电池消耗更高(对于移动设备)?
只要纹理数据发生变化,就必须生成 Mipmap。只要纹理不变,也不需要重新创建它们。
它们会影响性能,因为每个纹素的读取操作都会变慢。根据您使用的过滤器类型,GPU 必须从多个 mipmap 级别读取多个纹素来计算最终颜色。
例如,GL_NEAREST
将仅读取 1 个纹素,而 return 则为。 GL_LINEAR
已经必须从一个 mipmap 级别读取 4 个纹素并执行双线性插值。如果您现在启用 mipmapping,那么来自第二个纹理级别的信息也会影响结果。使用 GL_LINEAR_MIPMAP_LINEAR
,GPU 将在大于所需大小的 mipmap 级别执行一次线性查找(4 个纹素),并在小于请求大小的 mipmap 级别执行一次线性查找。然后将对这两个查找的结果进行插值以获得最终颜色。所以总而言之,GL_LINEAR_MIPMAL_LINEAR
查找可能会读取 8 个纹素并执行 2 个双线性插值和两个级别之间的线性插值 (trilinear interpolation)。
另一个考虑因素是 GPU 内存消耗。 Mipmaps 需要存储在 gpu 上的某个地方,并且比没有 mipmaps 多占用大约 1/3 space。
有关 Mipmapping 的更多详细信息,还应阅读 Wikipedia Article which explains the concept very well. As stated by others in comments, also this blog 对纹理过滤方法进行了很好的概述。
注意,这里的解释假设二维纹理。另请注意, 显卡可以很好地优化该过程,但所描述的技术在理论上是如何工作的。