在我的 vulkan 应用程序中,当所有网格使用相同的纹理时,我曾经这样绘制网格
Updatedescriptorsets(texture)
Command buffer record
{
For each mesh
Bind transformubo
Draw mesh
}
但现在我希望每个网格都有独特的纹理,所以我尝试了这个
Command buffer record
{
For each mesh
Bind transformubo
Updatedescriptorsets (textures[meshindex])
Draw mesh
}
但它给出了一个错误,说明描述符集已被破坏或更新。我查看了 vulkan 文档,发现我无法在命令缓冲区记录期间更新描述符集。那么如何才能为每个网格提供独特的纹理呢?
vkUpdateDescriptorSets
与任何事物都不同步。因此,您无法在使用描述符集时更新它。您必须确保使用相关描述符集的所有渲染操作均已完成,并且未将任何命令放置在使用相关描述符集的命令缓冲区中。
它基本上就像一个全局变量;如果没有某种同步,您就无法让人们从多个线程访问全局变量。而且 Vulkan 不会同步对描述符集的访问。
有几种方法可以解决这个问题。您可以为每个对象提供其自己的描述符集。这通常是通过使频繁改变的描述符集数据具有比不频繁改变的数据更高的索引来完成的。这样,您就不必更改每个对象的每个描述符,而只需更改每个对象的描述符。
您可以使用推送常量数据来索引大型表/数组纹理。因此描述符集将具有一个纹理数组或一个纹理数组(如果您有纹理数组的动态索引)。推送常量将提供一个索引,着色器使用该索引从纹理数组/纹理数组中获取特定对象的纹理。这使得频繁的更改相当便宜,并且相同的索引也可以用于为每个对象提供自己的变换矩阵(通过获取矩阵数组)。
如果您有可用的扩展 VK_KHR_push_descriptor,那么您可以将对描述符的更改直接集成到命令缓冲区中。这比推送常量机制好多少当然取决于实现。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)