Flutter Impeller
impeller::AllocatedTextureSourceVK Class Referencefinal
Inheritance diagram for impeller::AllocatedTextureSourceVK:
impeller::TextureSourceVK

Public Member Functions

 AllocatedTextureSourceVK (const ContextVK &context, const TextureDescriptor &desc, VmaAllocator allocator, vk::Device device, bool supports_memoryless_textures)
 
 ~AllocatedTextureSourceVK ()=default
 
bool IsValid () const
 
vk::Image GetImage () const override
 Get the image handle for this texture source. More...
 
vk::ImageView GetImageView () const override
 Retrieve the image view used for sampling/blitting/compute with this texture source. More...
 
vk::ImageView GetRenderTargetView () const override
 Retrieve the image view used for render target attachments with this texture source. More...
 
bool IsSwapchainImage () const override
 Determines if swapchain image. That is, an image used as the root render target. More...
 
- Public Member Functions inherited from impeller::TextureSourceVK
virtual ~TextureSourceVK ()
 
const TextureDescriptorGetTextureDescriptor () const
 Gets the texture descriptor for this image source. More...
 
fml::Status SetLayout (const BarrierVK &barrier) const
 Encodes the layout transition barrier to barrier.cmd_buffer for the image. More...
 
vk::ImageLayout SetLayoutWithoutEncoding (vk::ImageLayout layout) const
 Store the layout of the image. More...
 
vk::ImageLayout GetLayout () const
 Get the last layout assigned to the TextureSourceVK. More...
 
virtual std::shared_ptr< YUVConversionVKGetYUVConversion () const
 When sampling from textures whose formats are not known to Vulkan, a custom conversion is necessary to setup custom samplers. This accessor provides this conversion if one is present. Most texture source have none. More...
 
void SetCachedFramebuffer (const SharedHandleVK< vk::Framebuffer > &framebuffer)
 
void SetCachedRenderPass (const SharedHandleVK< vk::RenderPass > &render_pass)
 
SharedHandleVK< vk::Framebuffer > GetCachedFramebuffer () const
 
SharedHandleVK< vk::RenderPass > GetCachedRenderPass () const
 

Additional Inherited Members

- Protected Member Functions inherited from impeller::TextureSourceVK
 TextureSourceVK (TextureDescriptor desc)
 
- Protected Attributes inherited from impeller::TextureSourceVK
const TextureDescriptor desc_
 

Detailed Description

Definition at line 285 of file allocator_vk.cc.

Constructor & Destructor Documentation

◆ AllocatedTextureSourceVK()

impeller::AllocatedTextureSourceVK::AllocatedTextureSourceVK ( const ContextVK context,
const TextureDescriptor desc,
VmaAllocator  allocator,
vk::Device  device,
bool  supports_memoryless_textures 
)
inline

Definition at line 287 of file allocator_vk.cc.

292  : TextureSourceVK(desc), resource_(context.GetResourceManager()) {
293  FML_DCHECK(desc.format != PixelFormat::kUnknown);
294  vk::StructureChain<vk::ImageCreateInfo, vk::ImageCompressionControlEXT>
295  image_info_chain;
296  auto& image_info = image_info_chain.get();
297  image_info.flags = ToVKImageCreateFlags(desc.type);
298  image_info.imageType = vk::ImageType::e2D;
299  image_info.format = ToVKImageFormat(desc.format);
300  image_info.extent = VkExtent3D{
301  static_cast<uint32_t>(desc.size.width), // width
302  static_cast<uint32_t>(desc.size.height), // height
303  1u // depth
304  };
305  image_info.samples = ToVKSampleCount(desc.sample_count);
306  image_info.mipLevels = desc.mip_count;
307  image_info.arrayLayers = ToArrayLayerCount(desc.type);
308  image_info.tiling = vk::ImageTiling::eOptimal;
309  image_info.initialLayout = vk::ImageLayout::eUndefined;
310  image_info.usage = AllocatorVK::ToVKImageUsageFlags(
311  desc.format, desc.usage, desc.storage_mode,
312  supports_memoryless_textures);
313  image_info.sharingMode = vk::SharingMode::eExclusive;
314 
315  vk::ImageCompressionFixedRateFlagsEXT frc_rates[1] = {
316  vk::ImageCompressionFixedRateFlagBitsEXT::eNone};
317 
318  const auto frc_rate =
319  CapabilitiesVK::Cast(*context.GetCapabilities())
320  .GetSupportedFRCRate(desc.compression_type,
321  FRCFormatDescriptor{image_info});
322  if (frc_rate.has_value()) {
323  // This array must not be in a temporary scope.
324  frc_rates[0] = frc_rate.value();
325 
326  auto& compression_info =
327  image_info_chain.get<vk::ImageCompressionControlEXT>();
328  compression_info.pFixedRateFlags = frc_rates;
329  compression_info.compressionControlPlaneCount = 1u;
330  compression_info.flags =
331  vk::ImageCompressionFlagBitsEXT::eFixedRateExplicit;
332  } else {
333  image_info_chain.unlink<vk::ImageCompressionControlEXT>();
334  }
335 
336  VmaAllocationCreateInfo alloc_nfo = {};
337 
338  alloc_nfo.usage = ToVMAMemoryUsage();
339  alloc_nfo.preferredFlags =
340  static_cast<VkMemoryPropertyFlags>(ToVKTextureMemoryPropertyFlags(
341  desc.storage_mode, supports_memoryless_textures));
342  alloc_nfo.flags = ToVmaAllocationCreateFlags(desc.storage_mode);
343 
344  auto create_info_native =
345  static_cast<vk::ImageCreateInfo::NativeType>(image_info);
346 
347  VkImage vk_image = VK_NULL_HANDLE;
348  VmaAllocation allocation = {};
349  VmaAllocationInfo allocation_info = {};
350  {
351  auto result = vk::Result{::vmaCreateImage(allocator, //
352  &create_info_native, //
353  &alloc_nfo, //
354  &vk_image, //
355  &allocation, //
356  &allocation_info //
357  )};
358  if (result != vk::Result::eSuccess) {
359  VALIDATION_LOG << "Unable to allocate Vulkan Image: "
360  << vk::to_string(result)
361  << " Type: " << TextureTypeToString(desc.type)
362  << " Mode: " << StorageModeToString(desc.storage_mode)
363  << " Usage: " << TextureUsageMaskToString(desc.usage)
364  << " [VK]Flags: " << vk::to_string(image_info.flags)
365  << " [VK]Format: " << vk::to_string(image_info.format)
366  << " [VK]Usage: " << vk::to_string(image_info.usage)
367  << " [VK]Mem. Flags: "
368  << vk::to_string(vk::MemoryPropertyFlags(
369  alloc_nfo.preferredFlags));
370  return;
371  }
372  }
373 
374  auto image = vk::Image{vk_image};
375 
376  vk::ImageViewCreateInfo view_info = {};
377  view_info.image = image;
378  view_info.viewType = ToVKImageViewType(desc.type);
379  view_info.format = image_info.format;
380  view_info.subresourceRange.aspectMask = ToVKImageAspectFlags(desc.format);
381  view_info.subresourceRange.levelCount = image_info.mipLevels;
382  view_info.subresourceRange.layerCount = ToArrayLayerCount(desc.type);
383 
384  // Vulkan does not have an image format that is equivalent to
385  // `MTLPixelFormatA8Unorm`, so we use `R8Unorm` instead. Given that the
386  // shaders expect that alpha channel to be set in the cases, we swizzle.
387  // See: https://github.com/flutter/flutter/issues/115461 for more details.
388  if (desc.format == PixelFormat::kA8UNormInt) {
389  view_info.components.a = vk::ComponentSwizzle::eR;
390  view_info.components.r = vk::ComponentSwizzle::eA;
391  }
392 
393  auto [result, image_view] = device.createImageViewUnique(view_info);
394  if (result != vk::Result::eSuccess) {
395  VALIDATION_LOG << "Unable to create an image view for allocation: "
396  << vk::to_string(result);
397  return;
398  }
399  // Create a specialized view for render target attachments.
400  view_info.subresourceRange.levelCount = 1u;
401  auto [rt_result, rt_image_view] = device.createImageViewUnique(view_info);
402  if (rt_result != vk::Result::eSuccess) {
403  VALIDATION_LOG << "Unable to create an image view for allocation: "
404  << vk::to_string(rt_result);
405  return;
406  }
407 
408  resource_.Swap(ImageResource(ImageVMA{allocator, allocation, image},
409  std::move(image_view),
410  std::move(rt_image_view)));
411  is_valid_ = true;
412  }
static vk::ImageUsageFlags ToVKImageUsageFlags(PixelFormat format, TextureUsageMask usage, StorageMode mode, bool supports_memoryless_textures)
static CapabilitiesVK & Cast(Capabilities &base)
Definition: backend_cast.h:13
std::optional< vk::ImageCompressionFixedRateFlagBitsEXT > GetSupportedFRCRate(CompressionType compression_type, const FRCFormatDescriptor &desc) const
Get the fixed compression rate supported by the context for the given format and usage.
TextureSourceVK(TextureDescriptor desc)
void Swap(ResourceType &&other)
Reclaims the existing resource, if any, and replaces it.
constexpr uint32_t ToArrayLayerCount(TextureType type)
Definition: formats_vk.h:539
std::string TextureUsageMaskToString(TextureUsageMask mask)
Definition: formats.cc:81
constexpr const char * TextureTypeToString(TextureType type)
Definition: formats.h:269
static constexpr VmaMemoryUsage ToVMAMemoryUsage()
constexpr vk::ImageViewType ToVKImageViewType(TextureType type)
Definition: formats_vk.h:553
constexpr vk::SampleCountFlagBits ToVKSampleCount(SampleCount sample_count)
Definition: formats_vk.h:214
constexpr vk::Format ToVKImageFormat(PixelFormat format)
Definition: formats_vk.h:146
static VmaAllocationCreateFlags ToVmaAllocationCreateFlags(StorageMode mode)
static constexpr vk::Flags< vk::MemoryPropertyFlagBits > ToVKTextureMemoryPropertyFlags(StorageMode mode, bool supports_memoryless_textures)
constexpr const char * StorageModeToString(StorageMode mode)
Definition: formats.h:60
constexpr vk::ImageCreateFlags ToVKImageCreateFlags(TextureType type)
Definition: formats_vk.h:567
constexpr vk::ImageAspectFlags ToVKImageAspectFlags(PixelFormat format)
Definition: formats_vk.h:513
#define VALIDATION_LOG
Definition: validation.h:91

References impeller::TextureDescriptor::compression_type, impeller::TextureDescriptor::format, impeller::ContextVK::GetCapabilities(), impeller::TSize< T >::height, impeller::TextureDescriptor::mip_count, impeller::TextureDescriptor::sample_count, impeller::TextureDescriptor::size, impeller::TextureDescriptor::storage_mode, impeller::StorageModeToString(), impeller::TextureTypeToString(), impeller::TextureUsageMaskToString(), impeller::ToArrayLayerCount(), impeller::ToVKImageAspectFlags(), impeller::ToVKImageCreateFlags(), impeller::ToVKImageFormat(), impeller::ToVKImageViewType(), impeller::ToVKSampleCount(), impeller::ToVKTextureMemoryPropertyFlags(), impeller::ToVmaAllocationCreateFlags(), impeller::ToVMAMemoryUsage(), impeller::TextureDescriptor::type, impeller::TextureDescriptor::usage, VALIDATION_LOG, and impeller::TSize< T >::width.

◆ ~AllocatedTextureSourceVK()

impeller::AllocatedTextureSourceVK::~AllocatedTextureSourceVK ( )
default

Member Function Documentation

◆ GetImage()

vk::Image impeller::AllocatedTextureSourceVK::GetImage ( ) const
inlineoverridevirtual

Get the image handle for this texture source.

Returns
The image.

Implements impeller::TextureSourceVK.

Definition at line 418 of file allocator_vk.cc.

418 { return resource_->image.get().image; }

◆ GetImageView()

vk::ImageView impeller::AllocatedTextureSourceVK::GetImageView ( ) const
inlineoverridevirtual

Retrieve the image view used for sampling/blitting/compute with this texture source.

Returns
The image view.

Implements impeller::TextureSourceVK.

Definition at line 420 of file allocator_vk.cc.

420  {
421  return resource_->image_view.get();
422  }

◆ GetRenderTargetView()

vk::ImageView impeller::AllocatedTextureSourceVK::GetRenderTargetView ( ) const
inlineoverridevirtual

Retrieve the image view used for render target attachments with this texture source.

ImageViews used as render target attachments cannot have any mip levels. In cases where we want to generate mipmaps with the result of this texture, we need to create multiple image views.

Returns
The render target view.

Implements impeller::TextureSourceVK.

Definition at line 424 of file allocator_vk.cc.

424  {
425  return resource_->rt_image_view.get();
426  }

◆ IsSwapchainImage()

bool impeller::AllocatedTextureSourceVK::IsSwapchainImage ( ) const
inlineoverridevirtual

Determines if swapchain image. That is, an image used as the root render target.

Returns
Whether or not this is a swapchain image.

Implements impeller::TextureSourceVK.

Definition at line 428 of file allocator_vk.cc.

428 { return false; }

◆ IsValid()

bool impeller::AllocatedTextureSourceVK::IsValid ( ) const
inline

Definition at line 416 of file allocator_vk.cc.

416 { return is_valid_; }

The documentation for this class was generated from the following file: