Images represent multidimensional - up to 3 - arrays of data which can be used for various purposes (e.g. attachments, textures), by binding them to a graphics or compute pipeline via descriptor sets, or by directly specifying them as parameters to certain commands.
Images are represented by VkImage
handles:
VK_DEFINE_NON_DISPATCHABLE_HANDLE(VkImage)
To create images, call:
VkResult vkCreateImage( VkDevice device, const VkImageCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkImage* pImage);
device
is the logical device that creates the image.
pCreateInfo
is a pointer to an instance of the
VkImageCreateInfo
structure containing parameters to be used to
create the image.
pAllocator
controls host memory allocation as described in the
Memory Allocation chapter.
pImage
points to a VkImage
handle in which the resulting
image object is returned.
The VkImageCreateInfo
structure is defined as:
typedef struct VkImageCreateInfo { VkStructureType sType; const void* pNext; VkImageCreateFlags flags; VkImageType imageType; VkFormat format; VkExtent3D extent; uint32_t mipLevels; uint32_t arrayLayers; VkSampleCountFlagBits samples; VkImageTiling tiling; VkImageUsageFlags usage; VkSharingMode sharingMode; uint32_t queueFamilyIndexCount; const uint32_t* pQueueFamilyIndices; VkImageLayout initialLayout; } VkImageCreateInfo;
sType
is the type of this structure.
pNext
is NULL
or a pointer to an extension-specific structure.
flags
is a bitmask describing additional parameters of the image.
See VkImageCreateFlagBits
below for a description of the supported
bits.
imageType
is a VkImageType
specifying the basic
dimensionality of the image, as described below.
Layers in array textures do not count as a dimension for the purposes of
the image type.
format
is a VkFormat
describing the format and type of the
data elements that will be contained in the image.
extent
is a VkExtent3D
describing the number of data
elements in each dimension of the base level.
mipLevels
describes the number of levels of detail available for
minified sampling of the image.
arrayLayers
is the number of layers in the image.
samples
is the number of sub-data element samples in the image as
defined in VkSampleCountFlagBits
.
See Multisampling.
tiling
is a VkImageTiling
specifying the tiling arrangement
of the data elements in memory, as described below.
usage
is a bitmask describing the intended usage of the image.
See VkImageUsageFlagBits
below for a description of the supported
bits.
sharingMode
is the sharing mode of the image when it will be
accessed by multiple queue families, and must be one of the values
described for VkSharingMode
in the Resource Sharing section below.
queueFamilyIndexCount
is the number of entries in the
pQueueFamilyIndices
array.
pQueueFamilyIndices
is a list of queue families that will access
this image (ignored if sharingMode
is not
VK_SHARING_MODE_CONCURRENT
).
initialLayout
selects the initial VkImageLayout
state of all
image subresources of the image.
See Image Layouts.
initialLayout
must be VK_IMAGE_LAYOUT_UNDEFINED
or
VK_IMAGE_LAYOUT_PREINITIALIZED
.
Valid limits for the image extent
, mipLevels
, arrayLayers
and samples
members are queried with the
vkGetPhysicalDeviceImageFormatProperties
command.
Images created with tiling
equal to VK_IMAGE_TILING_LINEAR
have
further restrictions on their limits and capabilities compared to images
created with tiling
equal to VK_IMAGE_TILING_OPTIMAL
.
Creation of images with tiling VK_IMAGE_TILING_LINEAR
may not be
supported unless other parameters meet all of the constraints:
imageType
is VK_IMAGE_TYPE_2D
format
is not a depth/stencil format
mipLevels
is 1
arrayLayers
is 1
samples
is VK_SAMPLE_COUNT_1_BIT
usage
only includes VK_IMAGE_USAGE_TRANSFER_SRC_BIT
and/or
VK_IMAGE_USAGE_TRANSFER_DST_BIT
Implementations may support additional limits and capabilities beyond those
listed above.
To determine the specific capabilities of an implementation, query the valid
usage
bits by calling vkGetPhysicalDeviceFormatProperties
and
the valid limits for mipLevels
and arrayLayers
by calling
vkGetPhysicalDeviceImageFormatProperties
.
The intended usage of an image is specified by the bitmask
VkImageCreateInfo
::usage
.
Bits which can be set include:
typedef enum VkImageUsageFlagBits { VK_IMAGE_USAGE_TRANSFER_SRC_BIT = 0x00000001, VK_IMAGE_USAGE_TRANSFER_DST_BIT = 0x00000002, VK_IMAGE_USAGE_SAMPLED_BIT = 0x00000004, VK_IMAGE_USAGE_STORAGE_BIT = 0x00000008, VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT = 0x00000010, VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT = 0x00000020, VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT = 0x00000040, VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT = 0x00000080, } VkImageUsageFlagBits;
These bits have the following meanings:
VK_IMAGE_USAGE_TRANSFER_SRC_BIT
indicates that the image can be
used as the source of a transfer command.
VK_IMAGE_USAGE_TRANSFER_DST_BIT
indicates that the image can be
used as the destination of a transfer command.
VK_IMAGE_USAGE_SAMPLED_BIT
indicates that the image can be used
to create a VkImageView
suitable for occupying a
VkDescriptorSet
slot either of type
VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE
or
VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER
, and be sampled by a
shader.
VK_IMAGE_USAGE_STORAGE_BIT
indicates that the image can be used
to create a VkImageView
suitable for occupying a
VkDescriptorSet
slot of type
VK_DESCRIPTOR_TYPE_STORAGE_IMAGE
.
VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT
indicates that the image can
be used to create a VkImageView
suitable for use as a color or
resolve attachment in a VkFramebuffer
.
VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT
indicates that the
image can be used to create a VkImageView
suitable for use as a
depth/stencil attachment in a VkFramebuffer
.
VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT
indicates that the memory
bound to this image will have been allocated with the
VK_MEMORY_PROPERTY_LAZILY_ALLOCATED_BIT
(see Chapter 10, Memory Allocation for more
detail).
This bit can be set for any image that can be used to create a
VkImageView
suitable for use as a color, resolve, depth/stencil,
or input attachment.
VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT
indicates that the image can
be used to create a VkImageView
suitable for occupying
VkDescriptorSet
slot of type
VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT
; be read from a shader as an
input attachment; and be used as an input attachment in a framebuffer.
Additional parameters of an image are specified by
VkImageCreateInfo
::flags
.
Bits which can be set include:
typedef enum VkImageCreateFlagBits { VK_IMAGE_CREATE_SPARSE_BINDING_BIT = 0x00000001, VK_IMAGE_CREATE_SPARSE_RESIDENCY_BIT = 0x00000002, VK_IMAGE_CREATE_SPARSE_ALIASED_BIT = 0x00000004, VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT = 0x00000008, VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT = 0x00000010, } VkImageCreateFlagBits;
These bits have the following meanings:
VK_IMAGE_CREATE_SPARSE_BINDING_BIT
indicates that the image will
be backed using sparse memory binding.
VK_IMAGE_CREATE_SPARSE_RESIDENCY_BIT
indicates that the image can
be partially backed using sparse memory binding.
Images created with this flag must also be created with the
VK_IMAGE_CREATE_SPARSE_BINDING_BIT
flag.
VK_IMAGE_CREATE_SPARSE_ALIASED_BIT
indicates that the image will
be backed using sparse memory binding with memory ranges that might also
simultaneously be backing another image (or another portion of the same
image).
Images created with this flag must also be created with the
VK_IMAGE_CREATE_SPARSE_BINDING_BIT
flag
VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT
indicates that the image can
be used to create a VkImageView
with a different format from the
image.
VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT
indicates that the image can
be used to create a VkImageView
of type
VK_IMAGE_VIEW_TYPE_CUBE
or VK_IMAGE_VIEW_TYPE_CUBE_ARRAY
.
If any of the bits VK_IMAGE_CREATE_SPARSE_BINDING_BIT
,
VK_IMAGE_CREATE_SPARSE_RESIDENCY_BIT
, or
VK_IMAGE_CREATE_SPARSE_ALIASED_BIT
are set,
VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT
must not also be set.
See Sparse Resource Features and Sparse Physical Device Features for more details.
The basic dimensionality of an image is specified by
VkImageCreateInfo
::imageType
, which must be one of the values
typedef enum VkImageType { VK_IMAGE_TYPE_1D = 0, VK_IMAGE_TYPE_2D = 1, VK_IMAGE_TYPE_3D = 2, } VkImageType;
These values specify one-, two-, or three-dimensional images, respectively.
The tiling arrangement of data elements in an image is specified by
VkImageCreateInfo
::tiling
, which must be one of the values
typedef enum VkImageTiling { VK_IMAGE_TILING_OPTIMAL = 0, VK_IMAGE_TILING_LINEAR = 1, } VkImageTiling;
VK_IMAGE_TILING_OPTIMAL
specifies optimal tiling (texels are laid out
in an implementation-dependent arrangement, for more optimal memory access),
and VK_IMAGE_TILING_LINEAR
specifies linear tiling (texels are laid
out in memory in row-major order, possibly with some padding on each row).
To query the host access layout of an image subresource, for an image created with linear tiling, call:
void vkGetImageSubresourceLayout( VkDevice device, VkImage image, const VkImageSubresource* pSubresource, VkSubresourceLayout* pLayout);
device
is the logical device that owns the image.
image
is the image whose layout is being queried.
pSubresource
is a pointer to a VkImageSubresource
structure
selecting a specific image for the image subresource.
pLayout
points to a VkSubresourceLayout
structure in which
the layout is returned.
vkGetImageSubresourceLayout
is invariant for the lifetime of a single
image.
The VkImageSubresource
structure is defined as:
typedef struct VkImageSubresource { VkImageAspectFlags aspectMask; uint32_t mipLevel; uint32_t arrayLayer; } VkImageSubresource;
aspectMask
is a VkImageAspectFlags
selecting the image
aspect.
mipLevel
selects the mipmap level.
arrayLayer
selects the array layer.
Information about the layout of the image subresource is returned in a
VkSubresourceLayout
structure:
typedef struct VkSubresourceLayout { VkDeviceSize offset; VkDeviceSize size; VkDeviceSize rowPitch; VkDeviceSize arrayPitch; VkDeviceSize depthPitch; } VkSubresourceLayout;
offset
is the byte offset from the start of the image where the
image subresource begins.
size
is the size in bytes of the image subresource.
size
includes any extra memory that is required based on
rowPitch
.
rowPitch
describes the number of bytes between each row of texels
in an image.
arrayPitch
describes the number of bytes between each array layer
of an image.
depthPitch
describes the number of bytes between each slice of 3D
image.
For images created with linear tiling, rowPitch
, arrayPitch
and
depthPitch
describe the layout of the image subresource in linear
memory.
For uncompressed formats, rowPitch
is the number of bytes between
texels with the same x coordinate in adjacent rows (y coordinates differ by
one).
arrayPitch
is the number of bytes between texels with the same x and y
coordinate in adjacent array layers of the image (array layer values differ
by one).
depthPitch
is the number of bytes between texels with the same x and y
coordinate in adjacent slices of a 3D image (z coordinates differ by one).
Expressed as an addressing formula, the starting byte of a texel in the
image subresource has address:
// (x,y,z,layer) are in texel coordinates address(x,y,z,layer) = layer*arrayPitch + z*depthPitch + y*rowPitch + x*elementSize + offset
For compressed formats, the rowPitch
is the number of bytes between
compressed texel blocks in adjacent rows.
arrayPitch
is the number of bytes between compressed texel blocks in
adjacent array layers.
depthPitch
is the number of bytes between compressed texel blocks in
adjacent slices of a 3D image.
// (x,y,z,layer) are in compressed texel block coordinates address(x,y,z,layer) = layer*arrayPitch + z*depthPitch + y*rowPitch + x*compressedTexelBlockByteSize + offset;
arrayPitch
is undefined for images that were not created as arrays.
depthPitch
is defined only for 3D images.
For color formats, the aspectMask
member of VkImageSubresource
must be VK_IMAGE_ASPECT_COLOR_BIT
.
For depth/stencil formats, aspectMask
must be either
VK_IMAGE_ASPECT_DEPTH_BIT
or VK_IMAGE_ASPECT_STENCIL_BIT
.
On implementations that store depth and stencil aspects separately, querying
each of these image subresource layouts will return a different offset
and size
representing the region of memory used for that aspect.
On implementations that store depth and stencil aspects interleaved, the
same offset
and size
are returned and represent the interleaved
memory allocation.
To destroy an image, call:
void vkDestroyImage( VkDevice device, VkImage image, const VkAllocationCallbacks* pAllocator);
device
is the logical device that destroys the image.
image
is the image to destroy.
pAllocator
controls host memory allocation as described in the
Memory Allocation chapter.