finished support autoGenerateMipmaps
This commit is contained in:
parent
10c79f30a0
commit
2c5fd977f2
@ -1 +1 @@
|
|||||||
Subproject commit 59523b92969fc7f015b6d63667c7524d526db1ac
|
Subproject commit 741edebad8108eeee4b256bef0dae3ba0a9fdbcb
|
@ -89,8 +89,10 @@ private:
|
|||||||
if(!axis_pipeline)return(false);
|
if(!axis_pipeline)return(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
{
|
{
|
||||||
|
texture.color =db->LoadTexture2D(OS_TEXT("res/image/Brickwall/Albedo.Tex2D"),true);
|
||||||
|
texture.normal =db->LoadTexture2D(OS_TEXT("res/image/Brickwall/Normal.Tex2D"),true);
|
||||||
|
|
||||||
VkSamplerCreateInfo sampler_create_info=
|
VkSamplerCreateInfo sampler_create_info=
|
||||||
{
|
{
|
||||||
VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
|
VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
|
||||||
@ -103,20 +105,17 @@ private:
|
|||||||
VK_SAMPLER_ADDRESS_MODE_REPEAT,
|
VK_SAMPLER_ADDRESS_MODE_REPEAT,
|
||||||
VK_SAMPLER_ADDRESS_MODE_REPEAT,
|
VK_SAMPLER_ADDRESS_MODE_REPEAT,
|
||||||
0.0f,
|
0.0f,
|
||||||
false,
|
VK_TRUE,
|
||||||
0,
|
device->GetGPUPhysicalDevice()->GetMaxSamplerAnisotropy(),
|
||||||
false,
|
false,
|
||||||
VK_COMPARE_OP_NEVER,
|
VK_COMPARE_OP_NEVER,
|
||||||
0.0f,
|
0.0f,
|
||||||
1.0f,
|
static_cast<float>(texture.color->GetMipLevel()),
|
||||||
VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK,
|
VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK,
|
||||||
false
|
false
|
||||||
};
|
};
|
||||||
|
|
||||||
texture.sampler =db->CreateSampler(&sampler_create_info);
|
texture.sampler =db->CreateSampler(&sampler_create_info);
|
||||||
|
|
||||||
texture.color =db->LoadTexture2D(OS_TEXT("res/image/Brickwall/Albedo.Tex2D"));
|
|
||||||
texture.normal =db->LoadTexture2D(OS_TEXT("res/image/Brickwall/Normal.Tex2D"));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
{
|
{
|
||||||
|
@ -104,7 +104,7 @@ public:
|
|||||||
|
|
||||||
cili.lunarg.standard_validation = true;
|
cili.lunarg.standard_validation = true;
|
||||||
cili.khronos.validation = true;
|
cili.khronos.validation = true;
|
||||||
cili.RenderDoc.Capture = false;
|
cili.RenderDoc.Capture = true;
|
||||||
|
|
||||||
inst=CreateInstance("VulkanTest",nullptr,&cili);
|
inst=CreateInstance("VulkanTest",nullptr,&cili);
|
||||||
|
|
||||||
|
@ -131,11 +131,11 @@ public: //Texture
|
|||||||
|
|
||||||
void Clear(TextureCreateInfo *);
|
void Clear(TextureCreateInfo *);
|
||||||
|
|
||||||
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,const VkBufferImageCopy *,const int count);
|
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,const VkBufferImageCopy *,const int count, const uint32_t miplevel=1);
|
||||||
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,const List<ImageRegion> &);
|
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,const List<ImageRegion> &, const uint32_t miplevel=1);
|
||||||
|
|
||||||
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,uint32_t left,uint32_t top,uint32_t width,uint32_t height);
|
bool ChangeTexture2D(Texture2D *,GPUBuffer *buf,uint32_t left,uint32_t top,uint32_t width,uint32_t height, const uint32_t miplevel=1);
|
||||||
bool ChangeTexture2D(Texture2D *,void *data,uint32_t left,uint32_t top,uint32_t width,uint32_t height,uint32_t size);
|
bool ChangeTexture2D(Texture2D *,void *data, uint32_t left,uint32_t top,uint32_t width,uint32_t height,uint32_t size,const uint32_t miplevel=1);
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
bool ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const RectScope2<T> &rs)
|
bool ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const RectScope2<T> &rs)
|
||||||
@ -160,8 +160,6 @@ public: //Texture
|
|||||||
size);
|
size);
|
||||||
}
|
}
|
||||||
|
|
||||||
void GenerateMipmaps(Texture2D *);
|
|
||||||
|
|
||||||
public: //
|
public: //
|
||||||
|
|
||||||
Sampler *CreateSampler(VkSamplerCreateInfo *sci=nullptr);
|
Sampler *CreateSampler(VkSamplerCreateInfo *sci=nullptr);
|
||||||
|
@ -15,12 +15,13 @@ protected:
|
|||||||
VkImageAspectFlags aspect_mask;
|
VkImageAspectFlags aspect_mask;
|
||||||
|
|
||||||
VkExtent3D extent;
|
VkExtent3D extent;
|
||||||
|
uint32_t miplevel;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
friend ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,VkImageAspectFlags aspectMask,VkImage img);
|
friend ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,const uint32_t &miplevel,VkImageAspectFlags aspectMask,VkImage img);
|
||||||
|
|
||||||
ImageView(VkDevice dev,VkImageView iv,const VkImageViewType vt,const VkFormat fmt,const VkExtent3D &ext,const VkImageAspectFlags am)
|
ImageView(VkDevice dev,VkImageView iv,const VkImageViewType vt,const VkFormat fmt,const VkExtent3D &ext,const uint32_t &ml,const VkImageAspectFlags am)
|
||||||
{
|
{
|
||||||
device =dev;
|
device =dev;
|
||||||
image_view =iv;
|
image_view =iv;
|
||||||
@ -28,6 +29,7 @@ private:
|
|||||||
format =fmt;
|
format =fmt;
|
||||||
aspect_mask =am;
|
aspect_mask =am;
|
||||||
extent =ext;
|
extent =ext;
|
||||||
|
miplevel =ml;
|
||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
@ -41,6 +43,7 @@ public:
|
|||||||
const VkImageViewType GetViewType ()const{return view_type;}
|
const VkImageViewType GetViewType ()const{return view_type;}
|
||||||
const VkFormat GetFormat ()const{return format;}
|
const VkFormat GetFormat ()const{return format;}
|
||||||
const VkExtent3D & GetExtent ()const{return extent;}
|
const VkExtent3D & GetExtent ()const{return extent;}
|
||||||
|
const uint32_t & GetMipLevel ()const{return miplevel;}
|
||||||
const VkImageAspectFlags GetAspectFlags ()const{return aspect_mask;}
|
const VkImageAspectFlags GetAspectFlags ()const{return aspect_mask;}
|
||||||
|
|
||||||
const bool hasColor ()const{return aspect_mask&VK_IMAGE_ASPECT_COLOR_BIT;}
|
const bool hasColor ()const{return aspect_mask&VK_IMAGE_ASPECT_COLOR_BIT;}
|
||||||
@ -49,12 +52,12 @@ public:
|
|||||||
const bool hasDepthStencil ()const{return aspect_mask&(VK_IMAGE_ASPECT_DEPTH_BIT|VK_IMAGE_ASPECT_STENCIL_BIT);}
|
const bool hasDepthStencil ()const{return aspect_mask&(VK_IMAGE_ASPECT_DEPTH_BIT|VK_IMAGE_ASPECT_STENCIL_BIT);}
|
||||||
};//class ImageView
|
};//class ImageView
|
||||||
|
|
||||||
ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,VkImageAspectFlags aspectMask,VkImage img);
|
ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,const uint32_t &miplevel,VkImageAspectFlags aspectMask,VkImage img);
|
||||||
|
|
||||||
#define CREATE_IMAGE_VIEW(short_name,larget_name) \
|
#define CREATE_IMAGE_VIEW(short_name,larget_name) \
|
||||||
inline ImageView *CreateImageView##short_name(VkDevice device,VkFormat format,const VkExtent3D &ext,VkImageAspectFlags aspectMask,VkImage img=VK_NULL_HANDLE) \
|
inline ImageView *CreateImageView##short_name(VkDevice device,VkFormat format,const VkExtent3D &ext,const uint32_t &miplevel,VkImageAspectFlags aspectMask,VkImage img=VK_NULL_HANDLE) \
|
||||||
{ \
|
{ \
|
||||||
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_##larget_name,format,ext,aspectMask,img); \
|
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_##larget_name,format,ext,miplevel,aspectMask,img); \
|
||||||
}
|
}
|
||||||
|
|
||||||
CREATE_IMAGE_VIEW(1D,1D);
|
CREATE_IMAGE_VIEW(1D,1D);
|
||||||
|
@ -92,19 +92,22 @@ public:
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
const uint32_t GetMaxImage1D ()const{return properties.limits.maxImageDimension1D;}
|
const uint32_t GetMaxImage1D ()const{return properties.limits.maxImageDimension1D;}
|
||||||
const uint32_t GetMaxImage2D ()const{return properties.limits.maxImageDimension2D;}
|
const uint32_t GetMaxImage2D ()const{return properties.limits.maxImageDimension2D;}
|
||||||
const uint32_t GetMaxImage3D ()const{return properties.limits.maxImageDimension3D;}
|
const uint32_t GetMaxImage3D ()const{return properties.limits.maxImageDimension3D;}
|
||||||
const uint32_t GetMaxImageCube ()const{return properties.limits.maxImageDimensionCube;}
|
const uint32_t GetMaxImageCube ()const{return properties.limits.maxImageDimensionCube;}
|
||||||
const uint32_t GetMaxImageArrayLayers ()const{return properties.limits.maxImageArrayLayers;}
|
const uint32_t GetMaxImageArrayLayers ()const{return properties.limits.maxImageArrayLayers;}
|
||||||
const uint32_t GetMaxUBORange ()const{return properties.limits.maxUniformBufferRange;}
|
const uint32_t GetMaxUBORange ()const{return properties.limits.maxUniformBufferRange;}
|
||||||
const uint32_t GetMaxSSBORange ()const{return properties.limits.maxStorageBufferRange;}
|
const uint32_t GetMaxSSBORange ()const{return properties.limits.maxStorageBufferRange;}
|
||||||
const uint32_t GetMaxBoundDescriptorSets()const{return properties.limits.maxBoundDescriptorSets;}
|
const uint32_t GetMaxBoundDescriptorSets()const{return properties.limits.maxBoundDescriptorSets;}
|
||||||
|
|
||||||
const uint32_t GetMaxVertexInputAttributes ()const{return properties.limits.maxVertexInputAttributes;}
|
const uint32_t GetMaxVertexInputAttributes ()const{return properties.limits.maxVertexInputAttributes;}
|
||||||
const uint32_t GetMaxVertexInputBindings ()const{return properties.limits.maxVertexInputBindings;}
|
const uint32_t GetMaxVertexInputBindings ()const{return properties.limits.maxVertexInputBindings;}
|
||||||
|
|
||||||
const uint32_t GetMaxColorAttachments ()const{return properties.limits.maxColorAttachments;}
|
const uint32_t GetMaxColorAttachments ()const{return properties.limits.maxColorAttachments;}
|
||||||
|
|
||||||
|
const float GetMaxSamplerAnisotropy ()const{return properties.limits.maxSamplerAnisotropy;}
|
||||||
|
const float GetMaxSamplerLodBias ()const{return properties.limits.maxSamplerLodBias;}
|
||||||
|
|
||||||
const void GetPointSize(float &granularity,float &min_size,float &max_size)
|
const void GetPointSize(float &granularity,float &min_size,float &max_size)
|
||||||
{
|
{
|
||||||
|
@ -115,7 +115,7 @@ public: //Material
|
|||||||
|
|
||||||
public: //texture
|
public: //texture
|
||||||
|
|
||||||
Texture2D * LoadTexture2D(const OSString &);
|
Texture2D * LoadTexture2D(const OSString &,bool auto_mipmaps=false);
|
||||||
|
|
||||||
public: //Get
|
public: //Get
|
||||||
|
|
||||||
|
@ -30,7 +30,7 @@ public:
|
|||||||
GPUMemory * GetMemory () {return data?data->memory:nullptr;}
|
GPUMemory * GetMemory () {return data?data->memory:nullptr;}
|
||||||
ImageView * GetImageView () {return data?data->image_view:nullptr;}
|
ImageView * GetImageView () {return data?data->image_view:nullptr;}
|
||||||
|
|
||||||
const uint32 GetMipLevels ()const {return data?data->mip_levels:0;}
|
const uint32 GetMipLevel ()const {return data?data->miplevel:0;}
|
||||||
const bool IsOptimal ()const {return data?data->tiling==VK_IMAGE_TILING_OPTIMAL:false;}
|
const bool IsOptimal ()const {return data?data->tiling==VK_IMAGE_TILING_OPTIMAL:false;}
|
||||||
const bool IsLinear ()const {return data?data->tiling==VK_IMAGE_TILING_LINEAR:false;}
|
const bool IsLinear ()const {return data?data->tiling==VK_IMAGE_TILING_LINEAR:false;}
|
||||||
|
|
||||||
|
@ -9,7 +9,7 @@ struct TextureData
|
|||||||
VkImage image =VK_NULL_HANDLE;
|
VkImage image =VK_NULL_HANDLE;
|
||||||
VkImageLayout image_layout=VK_IMAGE_LAYOUT_UNDEFINED;
|
VkImageLayout image_layout=VK_IMAGE_LAYOUT_UNDEFINED;
|
||||||
ImageView * image_view =nullptr;
|
ImageView * image_view =nullptr;
|
||||||
uint32 mip_levels =0;
|
uint32 miplevel =0;
|
||||||
VkImageTiling tiling =VK_IMAGE_TILING_OPTIMAL;
|
VkImageTiling tiling =VK_IMAGE_TILING_OPTIMAL;
|
||||||
};//struct TextureData
|
};//struct TextureData
|
||||||
|
|
||||||
|
@ -78,21 +78,21 @@ namespace
|
|||||||
return(VK_NULL_HANDLE);
|
return(VK_NULL_HANDLE);
|
||||||
}
|
}
|
||||||
|
|
||||||
ImageView *Create2DImageView(VkDevice device,VkFormat format,const VkExtent2D &ext,VkImage img=VK_NULL_HANDLE)
|
ImageView *Create2DImageView(VkDevice device,VkFormat format,const VkExtent2D &ext,const uint32_t miplevel,VkImage img=VK_NULL_HANDLE)
|
||||||
{
|
{
|
||||||
VkExtent3D extent;
|
VkExtent3D extent;
|
||||||
|
|
||||||
copy(extent,ext);
|
copy(extent,ext);
|
||||||
|
|
||||||
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_2D,format,extent,VK_IMAGE_ASPECT_COLOR_BIT,img);
|
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_2D,format,extent,miplevel,VK_IMAGE_ASPECT_COLOR_BIT,img);
|
||||||
}
|
}
|
||||||
|
|
||||||
ImageView *CreateDepthImageView(VkDevice device,VkFormat format,const VkExtent2D &ext,VkImage img=VK_NULL_HANDLE)
|
ImageView *CreateDepthImageView(VkDevice device,VkFormat format,const VkExtent2D &ext,const uint32_t miplevel,VkImage img=VK_NULL_HANDLE)
|
||||||
{
|
{
|
||||||
VkExtent3D extent;
|
VkExtent3D extent;
|
||||||
|
|
||||||
copy(extent,ext,1);
|
copy(extent,ext,1);
|
||||||
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_2D,format,extent,VK_IMAGE_ASPECT_DEPTH_BIT,img);
|
return CreateImageView(device,VK_IMAGE_VIEW_TYPE_2D,format,extent,miplevel,VK_IMAGE_ASPECT_DEPTH_BIT,img);
|
||||||
}
|
}
|
||||||
|
|
||||||
VkDescriptorPool CreateDescriptorPool(VkDevice device,uint32_t sets_count)
|
VkDescriptorPool CreateDescriptorPool(VkDevice device,uint32_t sets_count)
|
||||||
|
@ -10,10 +10,100 @@
|
|||||||
VK_NAMESPACE_BEGIN
|
VK_NAMESPACE_BEGIN
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
const uint32_t GetMipLevels(const uint32_t size)
|
const uint32_t GetMipLevel(const uint32_t size)
|
||||||
{
|
{
|
||||||
return static_cast<uint32_t>(std::floor(std::log2(size)))+1;
|
return static_cast<uint32_t>(std::floor(std::log2(size)))+1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const uint32_t GetMipLevel(const VkExtent2D &ext)
|
||||||
|
{
|
||||||
|
return GetMipLevel(std::max(ext.width,ext.height));
|
||||||
|
}
|
||||||
|
|
||||||
|
const uint32_t GetMipLevel(const VkExtent3D &ext)
|
||||||
|
{
|
||||||
|
return GetMipLevel(std::max(std::max(ext.width,ext.height),ext.depth));
|
||||||
|
}
|
||||||
|
|
||||||
|
void GenerateMipmaps(GPUCmdBuffer *texture_cmd_buf,VkImage image,VkImageAspectFlags aspect_mask,const int32_t width,const int32_t height,const uint32_t mipLevels)
|
||||||
|
{
|
||||||
|
//VkImage image, VkFormat imageFormat, int32_t texWidth, int32_t texHeight, uint32_t mipLevels) {
|
||||||
|
// Check if image format supports linear blitting
|
||||||
|
|
||||||
|
VkImageMemoryBarrier barrier{};
|
||||||
|
barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
||||||
|
barrier.image = image;
|
||||||
|
barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||||
|
barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||||
|
barrier.subresourceRange.aspectMask = aspect_mask;
|
||||||
|
barrier.subresourceRange.baseArrayLayer = 0;
|
||||||
|
barrier.subresourceRange.layerCount = 1;
|
||||||
|
barrier.subresourceRange.levelCount = 1;
|
||||||
|
|
||||||
|
int32_t mipWidth = width;
|
||||||
|
int32_t mipHeight = height;
|
||||||
|
|
||||||
|
for (uint32_t i = 1; i < mipLevels; i++)
|
||||||
|
{
|
||||||
|
barrier.subresourceRange.baseMipLevel = i - 1;
|
||||||
|
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||||
|
barrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL;
|
||||||
|
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||||
|
barrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||||
|
|
||||||
|
texture_cmd_buf->PipelineBarrier(
|
||||||
|
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0,
|
||||||
|
0, nullptr,
|
||||||
|
0, nullptr,
|
||||||
|
1, &barrier);
|
||||||
|
|
||||||
|
VkImageBlit blit{};
|
||||||
|
blit.srcOffsets[0] = {0, 0, 0};
|
||||||
|
blit.srcOffsets[1] = {mipWidth, mipHeight, 1};
|
||||||
|
blit.srcSubresource.aspectMask = aspect_mask;
|
||||||
|
blit.srcSubresource.mipLevel = i - 1;
|
||||||
|
blit.srcSubresource.baseArrayLayer = 0;
|
||||||
|
blit.srcSubresource.layerCount = 1;
|
||||||
|
blit.dstOffsets[0] = {0, 0, 0};
|
||||||
|
blit.dstOffsets[1] = { mipWidth > 1 ? mipWidth / 2 : 1, mipHeight > 1 ? mipHeight / 2 : 1, 1 };
|
||||||
|
blit.dstSubresource.aspectMask = aspect_mask;
|
||||||
|
blit.dstSubresource.mipLevel = i;
|
||||||
|
blit.dstSubresource.baseArrayLayer = 0;
|
||||||
|
blit.dstSubresource.layerCount = 1;
|
||||||
|
|
||||||
|
texture_cmd_buf->BlitImage(
|
||||||
|
image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
|
||||||
|
image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
|
||||||
|
1, &blit,
|
||||||
|
VK_FILTER_LINEAR);
|
||||||
|
|
||||||
|
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL;
|
||||||
|
barrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||||
|
barrier.srcAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||||
|
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||||
|
|
||||||
|
texture_cmd_buf->PipelineBarrier(
|
||||||
|
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0,
|
||||||
|
0, nullptr,
|
||||||
|
0, nullptr,
|
||||||
|
1, &barrier);
|
||||||
|
|
||||||
|
if (mipWidth > 1) mipWidth /= 2;
|
||||||
|
if (mipHeight > 1) mipHeight /= 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
barrier.subresourceRange.baseMipLevel = mipLevels - 1;
|
||||||
|
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||||
|
barrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||||
|
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||||
|
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||||
|
|
||||||
|
texture_cmd_buf->PipelineBarrier(
|
||||||
|
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0,
|
||||||
|
0, nullptr,
|
||||||
|
0, nullptr,
|
||||||
|
1, &barrier);
|
||||||
|
}
|
||||||
}//namespace
|
}//namespace
|
||||||
|
|
||||||
bool GPUDevice::CheckFormatSupport(const VkFormat format,const uint32_t bits,ImageTiling tiling) const
|
bool GPUDevice::CheckFormatSupport(const VkFormat format,const uint32_t bits,ImageTiling tiling) const
|
||||||
@ -51,9 +141,11 @@ Texture2D *GPUDevice::CreateTexture2D(TextureCreateInfo *tci)
|
|||||||
|
|
||||||
if(tci->extent.width*tci->extent.height*tci->extent.depth<=0)return(nullptr);
|
if(tci->extent.width*tci->extent.height*tci->extent.depth<=0)return(nullptr);
|
||||||
|
|
||||||
|
const uint32_t miplevels=((tci->mipmap==0)?GetMipLevel(tci->extent):tci->mipmap);
|
||||||
|
|
||||||
if(!tci->image)
|
if(!tci->image)
|
||||||
{
|
{
|
||||||
Image2DCreateInfo ici(tci->usage,tci->tiling,tci->format,tci->extent.width,tci->extent.height,tci->mipmap);
|
Image2DCreateInfo ici(tci->usage,tci->tiling,tci->format,tci->extent.width,tci->extent.height,miplevels);
|
||||||
tci->image=CreateImage(&ici);
|
tci->image=CreateImage(&ici);
|
||||||
|
|
||||||
if(!tci->image)
|
if(!tci->image)
|
||||||
@ -66,7 +158,7 @@ Texture2D *GPUDevice::CreateTexture2D(TextureCreateInfo *tci)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if(!tci->image_view)
|
if(!tci->image_view)
|
||||||
tci->image_view=CreateImageView2D(attr->device,tci->format,tci->extent,tci->aspect,tci->image);
|
tci->image_view=CreateImageView2D(attr->device,tci->format,tci->extent,miplevels,tci->aspect,tci->image);
|
||||||
|
|
||||||
TextureData *tex_data=new TextureData;
|
TextureData *tex_data=new TextureData;
|
||||||
|
|
||||||
@ -74,8 +166,7 @@ Texture2D *GPUDevice::CreateTexture2D(TextureCreateInfo *tci)
|
|||||||
tex_data->image_layout = tci->image_layout;
|
tex_data->image_layout = tci->image_layout;
|
||||||
tex_data->image = tci->image;
|
tex_data->image = tci->image;
|
||||||
tex_data->image_view = tci->image_view;
|
tex_data->image_view = tci->image_view;
|
||||||
|
tex_data->miplevel = miplevels;
|
||||||
tex_data->mip_levels = tci->mipmap;
|
|
||||||
tex_data->tiling = VkImageTiling(tci->tiling);
|
tex_data->tiling = VkImageTiling(tci->tiling);
|
||||||
|
|
||||||
Texture2D *tex=CreateTexture2D(tex_data);
|
Texture2D *tex=CreateTexture2D(tex_data);
|
||||||
@ -91,7 +182,7 @@ Texture2D *GPUDevice::CreateTexture2D(TextureCreateInfo *tci)
|
|||||||
|
|
||||||
if(tci->buffer)
|
if(tci->buffer)
|
||||||
{
|
{
|
||||||
ChangeTexture2D(tex,tci->buffer,0,0,tci->extent.width,tci->extent.height);
|
ChangeTexture2D(tex,tci->buffer,0,0,tci->extent.width,tci->extent.height,tex_data->miplevel);
|
||||||
delete tci->buffer;
|
delete tci->buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -99,7 +190,7 @@ Texture2D *GPUDevice::CreateTexture2D(TextureCreateInfo *tci)
|
|||||||
return tex;
|
return tex;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const VkBufferImageCopy *buffer_image_copy,const int count)
|
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const VkBufferImageCopy *buffer_image_copy,const int count,const uint32_t miplevel)
|
||||||
{
|
{
|
||||||
if(!tex||!buf)
|
if(!tex||!buf)
|
||||||
return(false);
|
return(false);
|
||||||
@ -107,18 +198,17 @@ bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const VkBufferImag
|
|||||||
VkImageSubresourceRange subresourceRange;
|
VkImageSubresourceRange subresourceRange;
|
||||||
subresourceRange.aspectMask = tex->GetAspect();
|
subresourceRange.aspectMask = tex->GetAspect();
|
||||||
subresourceRange.baseMipLevel = 0;
|
subresourceRange.baseMipLevel = 0;
|
||||||
subresourceRange.levelCount = 1;
|
subresourceRange.levelCount = miplevel;
|
||||||
subresourceRange.baseArrayLayer = 0;
|
subresourceRange.baseArrayLayer = 0;
|
||||||
subresourceRange.layerCount = 1;
|
subresourceRange.layerCount = 1;
|
||||||
|
|
||||||
ImageMemoryBarrier imageMemoryBarrier;
|
ImageMemoryBarrier imageMemoryBarrier(tex->GetImage());
|
||||||
imageMemoryBarrier.srcAccessMask = 0;
|
imageMemoryBarrier.srcAccessMask = 0;
|
||||||
imageMemoryBarrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
imageMemoryBarrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||||
imageMemoryBarrier.oldLayout = VK_IMAGE_LAYOUT_UNDEFINED;
|
imageMemoryBarrier.oldLayout = VK_IMAGE_LAYOUT_UNDEFINED;
|
||||||
imageMemoryBarrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
imageMemoryBarrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||||
imageMemoryBarrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
imageMemoryBarrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||||
imageMemoryBarrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
imageMemoryBarrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||||
imageMemoryBarrier.image = tex->GetImage();
|
|
||||||
imageMemoryBarrier.subresourceRange = subresourceRange;
|
imageMemoryBarrier.subresourceRange = subresourceRange;
|
||||||
|
|
||||||
texture_cmd_buf->Begin();
|
texture_cmd_buf->Begin();
|
||||||
@ -138,25 +228,43 @@ bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const VkBufferImag
|
|||||||
buffer_image_copy);
|
buffer_image_copy);
|
||||||
|
|
||||||
imageMemoryBarrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
imageMemoryBarrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||||
imageMemoryBarrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
|
||||||
imageMemoryBarrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
imageMemoryBarrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||||
imageMemoryBarrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
|
||||||
|
VkPipelineStageFlags destinationStage;
|
||||||
|
|
||||||
|
if(miplevel>1)
|
||||||
|
{
|
||||||
|
imageMemoryBarrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||||
|
imageMemoryBarrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||||
|
|
||||||
|
destinationStage = VK_PIPELINE_STAGE_TRANSFER_BIT;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
imageMemoryBarrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||||
|
imageMemoryBarrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||||
|
|
||||||
|
destinationStage = VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT;
|
||||||
|
}
|
||||||
|
|
||||||
texture_cmd_buf->PipelineBarrier(
|
texture_cmd_buf->PipelineBarrier(
|
||||||
VK_PIPELINE_STAGE_TRANSFER_BIT,
|
VK_PIPELINE_STAGE_TRANSFER_BIT,
|
||||||
VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT,
|
destinationStage,
|
||||||
0,
|
0,
|
||||||
0, nullptr,
|
0, nullptr,
|
||||||
0, nullptr,
|
0, nullptr,
|
||||||
1, &imageMemoryBarrier);
|
1, &imageMemoryBarrier);
|
||||||
|
|
||||||
|
if(miplevel>1)
|
||||||
|
GenerateMipmaps(texture_cmd_buf,tex->GetImage(),tex->GetAspect(),tex->GetWidth(),tex->GetHeight(),miplevel);
|
||||||
|
|
||||||
texture_cmd_buf->End();
|
texture_cmd_buf->End();
|
||||||
|
|
||||||
SubmitTexture(*texture_cmd_buf);
|
SubmitTexture(*texture_cmd_buf);
|
||||||
return(true);
|
return(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const List<ImageRegion> &ir_list)
|
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const List<ImageRegion> &ir_list,const uint32_t miplevel)
|
||||||
{
|
{
|
||||||
if(!tex||!buf||ir_list.GetCount()<=0)
|
if(!tex||!buf||ir_list.GetCount()<=0)
|
||||||
return(false);
|
return(false);
|
||||||
@ -191,10 +299,10 @@ bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,const List<ImageRe
|
|||||||
++tp;
|
++tp;
|
||||||
}
|
}
|
||||||
|
|
||||||
return ChangeTexture2D(tex,buf,buffer_image_copy,ir_count);
|
return ChangeTexture2D(tex,buf,buffer_image_copy,ir_count,miplevel);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,uint32_t left,uint32_t top,uint32_t width,uint32_t height)
|
bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,uint32_t left,uint32_t top,uint32_t width,uint32_t height,const uint32_t miplevel)
|
||||||
{
|
{
|
||||||
if(!tex||!buf
|
if(!tex||!buf
|
||||||
||left<0||left+width>tex->GetWidth()
|
||left<0||left+width>tex->GetWidth()
|
||||||
@ -217,10 +325,10 @@ bool GPUDevice::ChangeTexture2D(Texture2D *tex,GPUBuffer *buf,uint32_t left,uint
|
|||||||
buffer_image_copy.imageExtent.height= height;
|
buffer_image_copy.imageExtent.height= height;
|
||||||
buffer_image_copy.imageExtent.depth = 1;
|
buffer_image_copy.imageExtent.depth = 1;
|
||||||
|
|
||||||
return ChangeTexture2D(tex,buf,&buffer_image_copy,1);
|
return ChangeTexture2D(tex,buf,&buffer_image_copy,1,miplevel);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GPUDevice::ChangeTexture2D(Texture2D *tex,void *data,uint32_t left,uint32_t top,uint32_t width,uint32_t height,uint32_t size)
|
bool GPUDevice::ChangeTexture2D(Texture2D *tex,void *data,uint32_t left,uint32_t top,uint32_t width,uint32_t height,uint32_t size,const uint32_t miplevel)
|
||||||
{
|
{
|
||||||
if(!tex||!data
|
if(!tex||!data
|
||||||
||left<0||left+width>tex->GetWidth()
|
||left<0||left+width>tex->GetWidth()
|
||||||
@ -231,100 +339,13 @@ bool GPUDevice::ChangeTexture2D(Texture2D *tex,void *data,uint32_t left,uint32_t
|
|||||||
|
|
||||||
GPUBuffer *buf=CreateBuffer(VK_BUFFER_USAGE_TRANSFER_SRC_BIT,size,data);
|
GPUBuffer *buf=CreateBuffer(VK_BUFFER_USAGE_TRANSFER_SRC_BIT,size,data);
|
||||||
|
|
||||||
bool result=ChangeTexture2D(tex,buf,left,top,width,height);
|
bool result=ChangeTexture2D(tex,buf,left,top,width,height,miplevel);
|
||||||
|
|
||||||
delete buf;
|
delete buf;
|
||||||
|
|
||||||
return(result);
|
return(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
void GPUDevice::GenerateMipmaps(Texture2D *tex)
|
|
||||||
{
|
|
||||||
//VkImage image, VkFormat imageFormat, int32_t texWidth, int32_t texHeight, uint32_t mipLevels) {
|
|
||||||
// Check if image format supports linear blitting
|
|
||||||
|
|
||||||
const uint32_t mipLevels=GetMipLevels(std::max(tex->GetWidth(),tex->GetHeight()));
|
|
||||||
|
|
||||||
VkImage image=tex->GetImage();
|
|
||||||
|
|
||||||
VkImageMemoryBarrier barrier{};
|
|
||||||
barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
|
||||||
barrier.image = image;
|
|
||||||
barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
|
||||||
barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
|
||||||
barrier.subresourceRange.aspectMask = tex->GetAspect();
|
|
||||||
barrier.subresourceRange.baseArrayLayer = 0;
|
|
||||||
barrier.subresourceRange.layerCount = 1;
|
|
||||||
barrier.subresourceRange.levelCount = 1;
|
|
||||||
|
|
||||||
int32_t mipWidth = tex->GetWidth();
|
|
||||||
int32_t mipHeight = tex->GetHeight();
|
|
||||||
|
|
||||||
texture_cmd_buf->Begin();
|
|
||||||
|
|
||||||
for (uint32_t i = 1; i < mipLevels; i++) {
|
|
||||||
barrier.subresourceRange.baseMipLevel = i - 1;
|
|
||||||
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
|
||||||
barrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL;
|
|
||||||
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
|
||||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
|
||||||
|
|
||||||
texture_cmd_buf->PipelineBarrier(
|
|
||||||
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0,
|
|
||||||
0, nullptr,
|
|
||||||
0, nullptr,
|
|
||||||
1, &barrier);
|
|
||||||
|
|
||||||
VkImageBlit blit{};
|
|
||||||
blit.srcOffsets[0] = {0, 0, 0};
|
|
||||||
blit.srcOffsets[1] = {mipWidth, mipHeight, 1};
|
|
||||||
blit.srcSubresource.aspectMask = tex->GetAspect();
|
|
||||||
blit.srcSubresource.mipLevel = i - 1;
|
|
||||||
blit.srcSubresource.baseArrayLayer = 0;
|
|
||||||
blit.srcSubresource.layerCount = 1;
|
|
||||||
blit.dstOffsets[0] = {0, 0, 0};
|
|
||||||
blit.dstOffsets[1] = { mipWidth > 1 ? mipWidth / 2 : 1, mipHeight > 1 ? mipHeight / 2 : 1, 1 };
|
|
||||||
blit.dstSubresource.aspectMask = tex->GetAspect();
|
|
||||||
blit.dstSubresource.mipLevel = i;
|
|
||||||
blit.dstSubresource.baseArrayLayer = 0;
|
|
||||||
blit.dstSubresource.layerCount = 1;
|
|
||||||
|
|
||||||
texture_cmd_buf->BlitImage(
|
|
||||||
image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
|
|
||||||
image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
|
|
||||||
1, &blit,
|
|
||||||
VK_FILTER_LINEAR);
|
|
||||||
|
|
||||||
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL;
|
|
||||||
barrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
|
||||||
barrier.srcAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
|
||||||
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
|
||||||
|
|
||||||
texture_cmd_buf->PipelineBarrier(
|
|
||||||
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0,
|
|
||||||
0, nullptr,
|
|
||||||
0, nullptr,
|
|
||||||
1, &barrier);
|
|
||||||
|
|
||||||
if (mipWidth > 1) mipWidth /= 2;
|
|
||||||
if (mipHeight > 1) mipHeight /= 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
barrier.subresourceRange.baseMipLevel = mipLevels - 1;
|
|
||||||
barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
|
||||||
barrier.newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
|
||||||
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
|
||||||
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
|
||||||
|
|
||||||
texture_cmd_buf->PipelineBarrier(
|
|
||||||
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0,
|
|
||||||
0, nullptr,
|
|
||||||
0, nullptr,
|
|
||||||
1, &barrier);
|
|
||||||
|
|
||||||
texture_cmd_buf->End();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GPUDevice::SubmitTexture(const VkCommandBuffer *cmd_bufs,const uint32_t count)
|
bool GPUDevice::SubmitTexture(const VkCommandBuffer *cmd_bufs,const uint32_t count)
|
||||||
{
|
{
|
||||||
if(!cmd_bufs||count<=0)
|
if(!cmd_bufs||count<=0)
|
||||||
|
@ -6,7 +6,7 @@ ImageView::~ImageView()
|
|||||||
vkDestroyImageView(device,image_view,nullptr);
|
vkDestroyImageView(device,image_view,nullptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,VkImageAspectFlags aspectMask,VkImage img)
|
ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,const VkExtent3D &ext,const uint32_t &miplevel,VkImageAspectFlags aspectMask,VkImage img)
|
||||||
{
|
{
|
||||||
ImageViewCreateInfo iv_createinfo;
|
ImageViewCreateInfo iv_createinfo;
|
||||||
|
|
||||||
@ -15,7 +15,7 @@ ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,
|
|||||||
iv_createinfo.viewType =type;
|
iv_createinfo.viewType =type;
|
||||||
iv_createinfo.subresourceRange.aspectMask =aspectMask;
|
iv_createinfo.subresourceRange.aspectMask =aspectMask;
|
||||||
iv_createinfo.subresourceRange.baseMipLevel =0;
|
iv_createinfo.subresourceRange.baseMipLevel =0;
|
||||||
iv_createinfo.subresourceRange.levelCount =ext.depth;
|
iv_createinfo.subresourceRange.levelCount =miplevel;
|
||||||
iv_createinfo.subresourceRange.baseArrayLayer =0;
|
iv_createinfo.subresourceRange.baseArrayLayer =0;
|
||||||
iv_createinfo.subresourceRange.layerCount =ext.depth;
|
iv_createinfo.subresourceRange.layerCount =ext.depth;
|
||||||
|
|
||||||
@ -42,6 +42,6 @@ ImageView *CreateImageView(VkDevice device,VkImageViewType type,VkFormat format,
|
|||||||
if(vkCreateImageView(device,&iv_createinfo,nullptr,&img_view)!=VK_SUCCESS)
|
if(vkCreateImageView(device,&iv_createinfo,nullptr,&img_view)!=VK_SUCCESS)
|
||||||
return(nullptr);
|
return(nullptr);
|
||||||
|
|
||||||
return(new ImageView(device,img_view,type,format,ext,aspectMask));
|
return(new ImageView(device,img_view,type,format,ext,miplevel,aspectMask));
|
||||||
}
|
}
|
||||||
VK_NAMESPACE_END
|
VK_NAMESPACE_END
|
||||||
|
@ -170,16 +170,16 @@ Sampler *RenderResource::CreateSampler(VkSamplerCreateInfo *sci)
|
|||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
Texture2D *CreateTextureFromFile(GPUDevice *device,const OSString &filename);
|
Texture2D *CreateTextureFromFile(GPUDevice *device,const OSString &filename,bool auto_mipmaps);
|
||||||
|
|
||||||
Texture2D *RenderResource::LoadTexture2D(const OSString &filename)
|
Texture2D *RenderResource::LoadTexture2D(const OSString &filename,bool auto_mipmaps)
|
||||||
{
|
{
|
||||||
Texture2D *tex;
|
Texture2D *tex;
|
||||||
|
|
||||||
if(texture_by_name.Get(filename,(Texture *&)tex))
|
if(texture_by_name.Get(filename,(Texture *&)tex))
|
||||||
return tex;
|
return tex;
|
||||||
|
|
||||||
tex=CreateTextureFromFile(device,filename);
|
tex=CreateTextureFromFile(device,filename,auto_mipmaps);
|
||||||
|
|
||||||
if(tex)
|
if(tex)
|
||||||
{
|
{
|
||||||
|
@ -95,15 +95,18 @@ namespace
|
|||||||
VkFormat format;
|
VkFormat format;
|
||||||
GPUBuffer *buf;
|
GPUBuffer *buf;
|
||||||
|
|
||||||
|
bool auto_mipmaps;
|
||||||
|
|
||||||
Texture2D *tex;
|
Texture2D *tex;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
VkTexture2DLoader(GPUDevice *dev):device(dev)
|
VkTexture2DLoader(GPUDevice *dev,const bool am):device(dev)
|
||||||
{
|
{
|
||||||
buf=nullptr;
|
buf=nullptr;
|
||||||
format=VK_FORMAT_UNDEFINED;
|
format=VK_FORMAT_UNDEFINED;
|
||||||
tex=nullptr;
|
tex=nullptr;
|
||||||
|
auto_mipmaps=am;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~VkTexture2DLoader()
|
virtual ~VkTexture2DLoader()
|
||||||
@ -159,6 +162,15 @@ namespace
|
|||||||
|
|
||||||
TextureCreateInfo *tci=new TextureCreateInfo(format);
|
TextureCreateInfo *tci=new TextureCreateInfo(format);
|
||||||
|
|
||||||
|
if(auto_mipmaps)
|
||||||
|
{
|
||||||
|
if(device->CheckFormatSupport(format,VK_FORMAT_FEATURE_BLIT_DST_BIT))
|
||||||
|
{
|
||||||
|
tci->usage|=VK_IMAGE_USAGE_TRANSFER_SRC_BIT;
|
||||||
|
tci->SetAutoMipmaps();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
tci->SetData(buf,file_header.width,file_header.height);
|
tci->SetData(buf,file_header.width,file_header.height);
|
||||||
|
|
||||||
tex=device->CreateTexture2D(tci);
|
tex=device->CreateTexture2D(tci);
|
||||||
@ -176,9 +188,9 @@ namespace
|
|||||||
};//class VkTexture2DLoader
|
};//class VkTexture2DLoader
|
||||||
}//namespace
|
}//namespace
|
||||||
|
|
||||||
Texture2D *CreateTextureFromFile(GPUDevice *device,const OSString &filename)
|
Texture2D *CreateTextureFromFile(GPUDevice *device,const OSString &filename,bool auto_mipmaps)
|
||||||
{
|
{
|
||||||
VkTexture2DLoader loader(device);
|
VkTexture2DLoader loader(device,auto_mipmaps);
|
||||||
|
|
||||||
if(!loader.Load(filename))
|
if(!loader.Load(filename))
|
||||||
return(nullptr);
|
return(nullptr);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user