mirror of
https://github.com/MobileGL-Dev/MobileGL
synced 2026-09-12 06:08:30 +09:00
[Feat] (MG_Backend/DirectVulkan): TextureManager mipmap completeness check
This commit is contained in:
@@ -68,10 +68,11 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
|
|
||||||
Bool VkTextureManager::SyncTexture(MG_State::GLState::ITextureObject &texture,
|
Bool VkTextureManager::SyncTexture(MG_State::GLState::ITextureObject &texture,
|
||||||
TextureResource &outResource) {
|
TextureResource &outResource) {
|
||||||
TextureUploadTarget level0Target = TextureUploadTarget::Unknown;
|
TextureUploadTarget uploadTarget = TextureUploadTarget::Unknown;
|
||||||
IntVec3 texelSize{0, 0, 0};
|
IntVec3 texelSize{0, 0, 0};
|
||||||
SizeT byteSize = 0;
|
SizeT byteSize = 0;
|
||||||
if (!CheckLevel0Completeness(texture, level0Target, texelSize, byteSize)) {
|
Uint32 mipLevelCount = 0;
|
||||||
|
if (!CheckMipmapCompleteness(texture, uploadTarget, texelSize, byteSize, mipLevelCount)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -80,18 +81,13 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const Uint32 mipLevelCount = GetUploadMipLevelCount(*mipTexture, level0Target);
|
if (!SyncTextureResource(texture, uploadTarget, texelSize, byteSize, mipLevelCount, outResource)) {
|
||||||
if (mipLevelCount == 0) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!SyncTextureResource(texture, level0Target, texelSize, byteSize, mipLevelCount, outResource)) {
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Bool hasDirtyMipLevel = false;
|
Bool hasDirtyMipLevel = false;
|
||||||
for (Uint32 level = 0; level < mipLevelCount; ++level) {
|
for (Uint32 level = 0; level < mipLevelCount; ++level) {
|
||||||
if (mipTexture->IsStorageDirty(level0Target, level)) {
|
if (mipTexture->IsStorageDirty(uploadTarget, level)) {
|
||||||
hasDirtyMipLevel = true;
|
hasDirtyMipLevel = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -100,14 +96,14 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!UploadDirtyMipLevels(*mipTexture, level0Target, outResource)) {
|
if (!UploadDirtyMipLevels(*mipTexture, uploadTarget, outResource)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
Bool VkTextureManager::SyncTextureResource(const MG_State::GLState::ITextureObject &texture,
|
Bool VkTextureManager::SyncTextureResource(const MG_State::GLState::ITextureObject &texture,
|
||||||
TextureUploadTarget level0Target,
|
TextureUploadTarget uploadTarget,
|
||||||
const IntVec3 &texelSize, SizeT byteSize, Uint32 mipLevels,
|
const IntVec3 &texelSize, SizeT byteSize, Uint32 mipLevels,
|
||||||
TextureResource &resource) {
|
TextureResource &resource) {
|
||||||
const VkFormat format = GetVkFormat(texture.GetFormat());
|
const VkFormat format = GetVkFormat(texture.GetFormat());
|
||||||
@@ -120,7 +116,7 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
if (mipLevels == 0) {
|
if (mipLevels == 0) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (level0Target != TextureUploadTarget::Texture2D) {
|
if (uploadTarget != TextureUploadTarget::Texture2D) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -175,7 +171,7 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Bool VkTextureManager::UploadDirtyMipLevels(MG_State::GLState::TextureObjectMipmap &mipmapTexture,
|
Bool VkTextureManager::UploadDirtyMipLevels(MG_State::GLState::TextureObjectMipmap &mipmapTexture,
|
||||||
TextureUploadTarget level0Target,
|
TextureUploadTarget uploadTarget,
|
||||||
TextureResource &outResource) {
|
TextureResource &outResource) {
|
||||||
struct UploadItem {
|
struct UploadItem {
|
||||||
Uint32 level = 0;
|
Uint32 level = 0;
|
||||||
@@ -190,18 +186,18 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
|
|
||||||
VkDeviceSize stagingSize = 0;
|
VkDeviceSize stagingSize = 0;
|
||||||
for (Uint32 level = 0; level < outResource.mipLevels; ++level) {
|
for (Uint32 level = 0; level < outResource.mipLevels; ++level) {
|
||||||
if (!mipmapTexture.IsStorageDirty(level0Target, level)) {
|
if (!mipmapTexture.IsStorageDirty(uploadTarget, level)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto texelSize = mipmapTexture.GetMipmapTexelSize(level0Target, level);
|
const auto texelSize = mipmapTexture.GetMipmapTexelSize(uploadTarget, level);
|
||||||
const auto byteSize = mipmapTexture.GetMipmapByteSize(level0Target, level);
|
const auto byteSize = mipmapTexture.GetMipmapByteSize(uploadTarget, level);
|
||||||
if (texelSize.x() <= 0 || texelSize.y() <= 0 || byteSize == 0) {
|
if (texelSize.x() <= 0 || texelSize.y() <= 0 || byteSize == 0) {
|
||||||
mipmapTexture.MarkStorageDirty(level0Target, level, false);
|
mipmapTexture.MarkStorageDirty(uploadTarget, level, false);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const void* source = mipmapTexture.MapMipmapData(level0Target, level);
|
const void* source = mipmapTexture.MapMipmapData(uploadTarget, level);
|
||||||
if (source == nullptr) {
|
if (source == nullptr) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -298,7 +294,7 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
for (const auto& item : uploadItems) {
|
for (const auto& item : uploadItems) {
|
||||||
mipmapTexture.MarkStorageDirty(level0Target, item.level, false);
|
mipmapTexture.MarkStorageDirty(uploadTarget, item.level, false);
|
||||||
}
|
}
|
||||||
outResource.layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
outResource.layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||||
return true;
|
return true;
|
||||||
@@ -350,8 +346,11 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
resource.format = VK_FORMAT_UNDEFINED;
|
resource.format = VK_FORMAT_UNDEFINED;
|
||||||
}
|
}
|
||||||
|
|
||||||
Bool VkTextureManager::CheckLevel0Completeness(const MG_State::GLState::ITextureObject& texture, TextureUploadTarget& outTarget,
|
Bool VkTextureManager::CheckMipmapCompleteness(const MG_State::GLState::ITextureObject& texture,
|
||||||
IntVec3& outTexelSize, SizeT& outByteSize) {
|
TextureUploadTarget& outTarget,
|
||||||
|
IntVec3& outTexelSize,
|
||||||
|
SizeT& outByteSize,
|
||||||
|
Uint32& outMipLevelCount) {
|
||||||
const auto* mipTexture = dynamic_cast<const MG_State::GLState::TextureObjectMipmap*>(&texture);
|
const auto* mipTexture = dynamic_cast<const MG_State::GLState::TextureObjectMipmap*>(&texture);
|
||||||
if (!mipTexture) {
|
if (!mipTexture) {
|
||||||
return false;
|
return false;
|
||||||
@@ -360,10 +359,26 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
if (targets.empty()) {
|
if (targets.empty()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
outTarget = targets.front();
|
|
||||||
outTexelSize = mipTexture->GetMipmapTexelSize(outTarget, 0);
|
for (const auto target : targets) {
|
||||||
outByteSize = mipTexture->GetMipmapByteSize(outTarget, 0);
|
const Uint32 mipLevelCount = GetUploadMipLevelCount(*mipTexture, target);
|
||||||
return outTexelSize.x() > 0 && outTexelSize.y() > 0 && outByteSize > 0;
|
if (mipLevelCount == 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto level0TexelSize = mipTexture->GetMipmapTexelSize(target, 0);
|
||||||
|
const auto level0ByteSize = mipTexture->GetMipmapByteSize(target, 0);
|
||||||
|
if (level0TexelSize.x() <= 0 || level0TexelSize.y() <= 0 || level0ByteSize == 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
outTarget = target;
|
||||||
|
outTexelSize = level0TexelSize;
|
||||||
|
outByteSize = level0ByteSize;
|
||||||
|
outMipLevelCount = mipLevelCount;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Uint32 VkTextureManager::GetUploadMipLevelCount(const MG_State::GLState::TextureObjectMipmap& texture,
|
Uint32 VkTextureManager::GetUploadMipLevelCount(const MG_State::GLState::TextureObjectMipmap& texture,
|
||||||
|
|||||||
@@ -48,16 +48,19 @@ private:
|
|||||||
Bool SyncTexture(MG_State::GLState::ITextureObject &texture,
|
Bool SyncTexture(MG_State::GLState::ITextureObject &texture,
|
||||||
TextureResource &outResource);
|
TextureResource &outResource);
|
||||||
Bool SyncTextureResource(const MG_State::GLState::ITextureObject &texture,
|
Bool SyncTextureResource(const MG_State::GLState::ITextureObject &texture,
|
||||||
TextureUploadTarget level0Target,
|
TextureUploadTarget uploadTarget,
|
||||||
const IntVec3 &texelSize, SizeT byteSize, Uint32 mipLevels,
|
const IntVec3 &texelSize, SizeT byteSize, Uint32 mipLevels,
|
||||||
TextureResource &resource);
|
TextureResource &resource);
|
||||||
Bool UploadDirtyMipLevels(MG_State::GLState::TextureObjectMipmap &mipmapTexture,
|
Bool UploadDirtyMipLevels(MG_State::GLState::TextureObjectMipmap &mipmapTexture,
|
||||||
TextureUploadTarget level0Target,
|
TextureUploadTarget uploadTarget,
|
||||||
TextureResource &outResource);
|
TextureResource &outResource);
|
||||||
Bool ExecuteCmdBufImmediate(const std::function<void(VkCommandBuffer)>& recorder) const;
|
Bool ExecuteCmdBufImmediate(const std::function<void(VkCommandBuffer)>& recorder) const;
|
||||||
void DestroyTextureResource(TextureResource& resource) const;
|
void DestroyTextureResource(TextureResource& resource) const;
|
||||||
static Bool CheckLevel0Completeness(const MG_State::GLState::ITextureObject& texture, TextureUploadTarget& outTarget,
|
static Bool CheckMipmapCompleteness(const MG_State::GLState::ITextureObject& texture,
|
||||||
IntVec3& outTexelSize, SizeT& outByteSize);
|
TextureUploadTarget& outTarget,
|
||||||
|
IntVec3& outTexelSize,
|
||||||
|
SizeT& outByteSize,
|
||||||
|
Uint32& outMipLevelCount);
|
||||||
static Uint32 GetUploadMipLevelCount(const MG_State::GLState::TextureObjectMipmap& texture, TextureUploadTarget target);
|
static Uint32 GetUploadMipLevelCount(const MG_State::GLState::TextureObjectMipmap& texture, TextureUploadTarget target);
|
||||||
static VkFormat GetVkFormat(TextureInternalFormat format);
|
static VkFormat GetVkFormat(TextureInternalFormat format);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user