mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-03-22 23:30:14 +00:00
Fix animated M2 flicker: free bone descriptor sets on instance removal
The boneDescPool_ had MAX_BONE_SETS=2048 but sets were never freed when instances were removed (only when clear() reset the whole pool on map load). As tiles streamed in/out, each new animated instance consumed 2 pool slots (one per frame index) permanently. After ~1024 animated instances created total, vkAllocateDescriptorSets began failing silently and returning VK_NULL_HANDLE. render() skips instances with null boneSet[frameIndex], making them invisible — appearing as per-frame flicker as the culling pass included them but the render pass excluded them. Fix: destroyInstanceBones() now calls vkFreeDescriptorSets() for each non-null boneSet before destroying the bone SSBO. The pool already had VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT set for this purpose. Also increased MAX_BONE_SETS from 2048 to 8192 for extra headroom.
This commit is contained in:
parent
7b3b33e664
commit
caea24f6ea
2 changed files with 10 additions and 2 deletions
|
|
@ -381,7 +381,7 @@ private:
|
|||
VkDescriptorPool materialDescPool_ = VK_NULL_HANDLE;
|
||||
VkDescriptorPool boneDescPool_ = VK_NULL_HANDLE;
|
||||
static constexpr uint32_t MAX_MATERIAL_SETS = 8192;
|
||||
static constexpr uint32_t MAX_BONE_SETS = 2048;
|
||||
static constexpr uint32_t MAX_BONE_SETS = 8192;
|
||||
|
||||
// Dynamic particle buffers
|
||||
::VkBuffer smokeVB_ = VK_NULL_HANDLE;
|
||||
|
|
|
|||
|
|
@ -751,14 +751,22 @@ void M2Renderer::destroyModelGPU(M2ModelGPU& model) {
|
|||
|
||||
void M2Renderer::destroyInstanceBones(M2Instance& inst) {
|
||||
if (!vkCtx_) return;
|
||||
VkDevice device = vkCtx_->getDevice();
|
||||
VmaAllocator alloc = vkCtx_->getAllocator();
|
||||
for (int i = 0; i < 2; i++) {
|
||||
// Free bone descriptor set so the pool slot is immediately reusable.
|
||||
// Without this, the pool fills up over a play session as tiles stream
|
||||
// in/out, eventually causing vkAllocateDescriptorSets to fail and
|
||||
// making animated instances invisible (perceived as flickering).
|
||||
if (inst.boneSet[i] != VK_NULL_HANDLE) {
|
||||
vkFreeDescriptorSets(device, boneDescPool_, 1, &inst.boneSet[i]);
|
||||
inst.boneSet[i] = VK_NULL_HANDLE;
|
||||
}
|
||||
if (inst.boneBuffer[i]) {
|
||||
vmaDestroyBuffer(alloc, inst.boneBuffer[i], inst.boneAlloc[i]);
|
||||
inst.boneBuffer[i] = VK_NULL_HANDLE;
|
||||
inst.boneMapped[i] = nullptr;
|
||||
}
|
||||
// boneSet freed when pool is reset/destroyed
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue