特定尺寸的图像具有奇怪的内存大小

Image of specific dimensions has strange memory size

我有一个奇怪的行为,尺寸为 500x500 的格式 R8G8B8A8_UNORM 的图像占用额外的 8000 字节内存量,而其他尺寸恰好占用宽度*高度*4 字节。我正在执行以下操作:

  1. 画色贴
  2. 将颜色附件复制到主机可见图像并将其映射(在所有布局转换之后)。

工作正常,但是,在映射前检查主机可见图像的内存要求时,我得到以下结果:

最后一个案例中生成的图像格式不正确。除了 w*h*4 之外,有什么明显的我遗漏的东西可能导致内存大小的不同公式吗?主机可见图像具有线性平铺,并已在 vkMapMemory 命令之前转换为布局 VK_IMAGE_LAYOUT_GENERAL

这是颜色附件的创建信息:

VkImageCreateInfo color_image_info = {
  VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // sType,
  nullptr, // pNext (see documentation, must be null)
  0, // image flags
  VK_IMAGE_TYPE_2D, // image type
  this->color_format_, // image format
  {this->render_width_, this->render_height_, 1}, // image extent
  1, // level of detail = 1
  1, // layers = 1
  VK_SAMPLE_COUNT_1_BIT, // sampling
  VK_IMAGE_TILING_OPTIMAL, // optimal tiling
  VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT, // used for color
  VK_SHARING_MODE_EXCLUSIVE, // sharing between queue families
  1, // number queue families
  &this->queue_family_index_, // queue family index
  VK_IMAGE_LAYOUT_PREINITIALIZED // initial layout
};

这是主机可见图像:

VkImageCreateInfo host_visible_image_info = {
  VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // sType,
  nullptr, // pNext (see documentation, must be null)
  0, // image flags
  VK_IMAGE_TYPE_2D, // image type
  this->color_format_, // image format
  {this->render_width_, this->render_height_, 1}, // image extent
  1, // level of detail = 1
  1, // layers = 1
  VK_SAMPLE_COUNT_1_BIT, // sampling
  VK_IMAGE_TILING_LINEAR, // linear tiling
  VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT, // used for color
  VK_SHARING_MODE_EXCLUSIVE, // sharing between queue families
  1, // number queue families
  &this->queue_family_index_, // queue family index
  VK_IMAGE_LAYOUT_PREINITIALIZED // initial layout // TODO: !!!Find out whether this has to be transisition first
};

So I guess I will just just compute padding = (required_size - computed_size)/width/4.

没有

Vulkan 允许您通过 vkGetImageSubresourceLayout 查询图像的布局(使用线性平铺)。这就是您在尝试映射纹理和访问其位时应该使用的内容。

VkSubresourceLayout 会告诉您图像的行间距(即:您必须偏移的字节数才能直接到达像素 below/above 它)。此值 不需要 为宽度 * 像素大小。您必须查询您要访问的每个图像。