出于性能原因,纹理初始化时,纹理数据几乎总是由图形驱动程序复制到视频存储器(VRAM).这使得在GPU上运行的着色器的纹理提取速度明显加快; 如果每个纹理缓存未必通过PCIe总线获取丢失的数据,你肯定不会高兴!
但是,正如您所注意到的,这使得CPU难以读取或修改数据变得困难和/或变慢.不仅PCIe总线相对较慢,而且VRAM通常不能由CPU直接寻址; 通常必须使用特殊的低级DMA命令传输数据.这就是为什么你看到使用XNA的当性能命中GetData<>()
和SetData<>()
:这是不是说的杀了你的函数调用的开销,那就是他们必须来回复制VRAM您的数据背后的事实.
如果要在VRAM中修改数据,则低级渲染API(例如OpenGL或Direct3D 11)为您提供三个选项:
GetData<>()
,并SetData<>()
在内部做.glTexSubImage2D()
,它实际上跳过了"map"步骤并将新的像素数据直接复制回VRAM,覆盖了之前的内容.XNA建立在Direct3D之上,因此它必须在这些限制范围内工作.那么,没有原始像素数据给你!
(顺便说一句,上面的所有内容对于GPU缓冲区数据也是如此.)