始终使用1的对齐有什么缺点?
glPixelStorei(GL_UNPACK_ALIGNMENT, 1)
glPixelStorei(GL_PACK_ALIGNMENT, 1)
它会影响现代gpus的性能吗?
答案 0 :(得分:42)
数据如何不能以1字节对齐?
这强烈表明对row alignment in pixel transfer operations means。
的理解缺乏了解您传递给OpenGL的图像数据应该被分组为行。每行包含width
个像素数,每个像素的大小由格式和类型参数定义。因此,GL_RGB
格式的类型为GL_UNSIGNED_BYTE
将导致像素大小为24位。否则期望像素被打包,因此这些像素中的16行将占用48个字节。
预期每一行都按照GL_PACK/UNPACK_ALIGNMENT
定义的特定值对齐。这意味着您添加到指针以进入下一行的值为:align(pixel_size * width, GL_*_ALIGNMENT)
。如果像素大小为3字节,宽度为2,对齐为1,则行字节大小为6.如果对齐为4,则行字节大小为 8 < /强>
看到问题?
图像数据可能来自某些图像文件格式,加载了一些图像加载器,具有行对齐。有时这是1字节对齐,有时它不是。 DDS图像具有指定为格式一部分的对齐。在许多情况下,图像具有4字节行对齐;因此,小于32位的像素大小将在具有特定宽度的行的末尾处具有填充。如果你给OpenGL的对齐方式不匹配,那么你会得到格式错误的结构。
您可以将对齐设置为与图像格式的对齐方式匹配。如果您知道或以其他方式可以确保行对齐始终为1(除非您编写自己的图像格式或DDS编写器,否则这种情况不太可能),您需要将行对齐设置为图像格式使用的行对齐。
答案 1 :(得分:10)
它会影响现代gpus的性能吗?
不,因为像素存储设置仅与从GPU传输数据或与GPU传输数据相关,即数据对齐。一旦进入GPU内存,它就会以GPU和驱动程序所需的任何方式对齐。
答案 2 :(得分:0)
对性能没有影响。 (在openGL中)设置更高的对齐方式不会改善任何效果,也不会加快任何效果。
所有对齐方式都是告诉openGL下一行像素在哪里。如果图像像素紧密排列,即在字节行的结束位置与新行的开始位置之间没有间隙,则应始终使用1的对齐方式。
默认对齐方式是4(即openGL期望下一行像素在内存中被4整除后),这在加载非4的R,RG或RGB纹理的情况下可能会引起问题-bytes浮点数,或者宽度不能被4整除。如果图像像素紧紧包装,则必须将对齐方式更改为1才能使拆包工作。
您可能(我个人没有遇到过)具有3x3 RGB ubyte的图像,该图像的行是第4个对齐的,最后还有3个额外的字节用作填充。哪些行可能看起来像这样:
R-G-B-R-G-B-R-G-B-X-X-X(总共16个字节)
其原因是对齐的数据可以提高处理器的性能(不确定在当今的处理器上有多少是正确的/合理的)。 如果,您可以控制原始图像的构成方式,然后也许以一种或另一种方式对齐将改善其处理效果。但这是在openGL之前完成的。 OpenGL无法对此进行任何更改,它只关心在哪里找到像素。
因此,回到上面的3x3图像行-将对齐方式设置为4会很好(并且有必要),以跳过最后一个填充。如果将其设置为1,则结果会混乱,因此您需要将其保存/恢复为4。(请注意,您也可以使用ROW_LENGTH跳过它,因为这是处理图片,在这种情况下,您有时必须跳远3或7个字节(对齐参数8可以为您提供的最大值),在我们的示例中,如果您提供4的行长,并且对齐1工作)。
相同的包装。您可以告诉openGL将像素行对齐为1、2、4和8。如果要保存3x3 RGB ubyte,则应将对齐方式设置为1。从技术上讲,如果希望将结果行紧紧包装,则可以应该总是给出1。如果您出于某种原因想要创建填充,则可以给出另一个值。 (在我们的示例中)将PACK_ALIGNMENT设置为4,将导致创建与上一行类似的行(最后添加3个额外的填充)。请注意,在这种情况下,您的包含对象(openCV垫,位图等)应该能够接收该额外的填充。