fix mipmaps on generated textures in d3d10, d3d11 and d3d12 (#18513)

This commit is contained in:
hunterk authored and GitHub committed 2025-12-14 11:32:09 +01:00
1 parent e83e9674e0
commit 66a7657e8b
3 files changed
+64 -37

No files matched your search

+9 -3
View File
@@ -406,10 +406,10 @@ static void d3d10_init_texture(D3D10Device device, d3d10_texture_t* texture)
unsigned width, height;
texture->desc.BindFlags |= D3D10_BIND_RENDER_TARGET;
width = texture->desc.Width >> 5;
height = texture->desc.Height >> 5;
width = texture->desc.Width;
height = texture->desc.Height;
while (width && height)
while ((width > 1) || (height > 1))
{
width >>= 1;
height >>= 1;
@@ -2378,6 +2378,7 @@ static void d3d10_init_render_targets(d3d10_video_t* d3d10,
d3d10->pass[i].rt.desc.BindFlags = D3D10_BIND_RENDER_TARGET;
d3d10->pass[i].rt.desc.Format = glslang_format_to_dxgi(
d3d10->pass[i].semantics.format);
d3d10->pass[i].rt.desc.MiscFlags = D3D10_RESOURCE_MISC_GENERATE_MIPS;
d3d10_release_texture(&d3d10->pass[i].rt);
d3d10_init_texture(d3d10->device, &d3d10->pass[i].rt);
@@ -2720,6 +2721,11 @@ static bool d3d10_gfx_frame(
#endif /* D3D10_ROLLING_SCANLINE_SIMULATION */
context->lpVtbl->Draw(context, 4, 0);
/* Generate mipmaps for render target if needed */
if (d3d10->pass[i].rt.desc.MiscFlags & D3D10_RESOURCE_MISC_GENERATE_MIPS)
context->lpVtbl->GenerateMips(context, d3d10->pass[i].rt.view);
texture = &d3d10->pass[i].rt;
}
else
+11 -3
View File
@@ -568,10 +568,11 @@ static void d3d11_init_texture(D3D11Device device, d3d11_texture_t* texture)
unsigned width, height;
texture->desc.BindFlags |= D3D11_BIND_RENDER_TARGET;
width = texture->desc.Width >> 5;
height = texture->desc.Height >> 5;
width = texture->desc.Width;
height = texture->desc.Height;
texture->desc.MipLevels = 1;
while (width && height)
while ((width > 1) || (height > 1))
{
width >>= 1;
height >>= 1;
@@ -3092,10 +3093,13 @@ static void d3d11_init_render_targets(d3d11_video_t* d3d11, unsigned width, unsi
d3d11->pass[i].viewport.Width = width;
d3d11->pass[i].viewport.Height = height;
d3d11->pass[i].viewport.MaxDepth = 1.0;
d3d11->pass[i].rt.desc.Width = width;
d3d11->pass[i].rt.desc.Height = height;
d3d11->pass[i].rt.desc.BindFlags = D3D11_BIND_RENDER_TARGET;
d3d11->pass[i].rt.desc.Format = glslang_format_to_dxgi(d3d11->pass[i].semantics.format);
d3d11->pass[i].rt.desc.MiscFlags = D3D11_RESOURCE_MISC_GENERATE_MIPS;
d3d11_release_texture(&d3d11->pass[i].rt);
d3d11_init_texture(d3d11->device, &d3d11->pass[i].rt);
@@ -3576,6 +3580,10 @@ static bool d3d11_gfx_frame(
else
context->lpVtbl->Draw(context, 4, 4);
/* Generate mipmaps for render target if needed */
if (d3d11->pass[i].rt.desc.MiscFlags & D3D11_RESOURCE_MISC_GENERATE_MIPS)
context->lpVtbl->GenerateMips(context, d3d11->pass[i].rt.view);
texture = &d3d11->pass[i].rt;
}
}
+44 -31
View File
@@ -708,13 +708,13 @@ static void d3d12_init_texture(D3D12Device device, d3d12_texture_t* texture)
if (!texture->desc.MipLevels)
texture->desc.MipLevels = 1;
if ( !(texture->desc.Width >> (texture->desc.MipLevels - 1))
&& !(texture->desc.Height >> (texture->desc.MipLevels - 1)))
/* Calculate mipmap count */
if (texture->desc.Width > 1 || texture->desc.Height > 1)
{
unsigned width = texture->desc.Width >> 5;
unsigned height = texture->desc.Height >> 5;
unsigned width = texture->desc.Width;
unsigned height = texture->desc.Height;
texture->desc.MipLevels = 1;
while (width && height)
while ((width > 1) || (height > 1))
{
width >>= 1;
height >>= 1;
@@ -823,33 +823,11 @@ static void d3d12_init_texture(D3D12Device device, d3d12_texture_t* texture)
texture->size_data.w = 1.0f / texture->desc.Height;
}
static void d3d12_upload_texture(D3D12GraphicsCommandList cmd,
d3d12_texture_t* texture, void *userdata)
static void d3d12_generate_mipmaps(
D3D12GraphicsCommandList cmd,
d3d12_texture_t* texture,
void *userdata)
{
D3D12_TEXTURE_COPY_LOCATION src, dst;
src.pResource = texture->upload_buffer;
src.Type = D3D12_TEXTURE_COPY_TYPE_PLACED_FOOTPRINT;
src.PlacedFootprint = texture->layout;
dst.pResource = texture->handle;
dst.Type = D3D12_TEXTURE_COPY_TYPE_SUBRESOURCE_INDEX;
dst.SubresourceIndex = 0;
D3D12_RESOURCE_TRANSITION(
cmd,
texture->handle,
D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE,
D3D12_RESOURCE_STATE_COPY_DEST);
cmd->lpVtbl->CopyTextureRegion(cmd, &dst, 0, 0, 0, &src, NULL);
D3D12_RESOURCE_TRANSITION(
cmd,
texture->handle,
D3D12_RESOURCE_STATE_COPY_DEST,
D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE);
if (texture->desc.MipLevels > 1)
{
unsigned i;
@@ -903,6 +881,36 @@ static void d3d12_upload_texture(D3D12GraphicsCommandList cmd,
}
}
}
}
static void d3d12_upload_texture(D3D12GraphicsCommandList cmd,
d3d12_texture_t* texture, void *userdata)
{
D3D12_TEXTURE_COPY_LOCATION src, dst;
src.pResource = texture->upload_buffer;
src.Type = D3D12_TEXTURE_COPY_TYPE_PLACED_FOOTPRINT;
src.PlacedFootprint = texture->layout;
dst.pResource = texture->handle;
dst.Type = D3D12_TEXTURE_COPY_TYPE_SUBRESOURCE_INDEX;
dst.SubresourceIndex = 0;
D3D12_RESOURCE_TRANSITION(
cmd,
texture->handle,
D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE,
D3D12_RESOURCE_STATE_COPY_DEST);
cmd->lpVtbl->CopyTextureRegion(cmd, &dst, 0, 0, 0, &src, NULL);
D3D12_RESOURCE_TRANSITION(
cmd,
texture->handle,
D3D12_RESOURCE_STATE_COPY_DEST,
D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE);
d3d12_generate_mipmaps(cmd, texture, userdata);
texture->dirty = false;
}
@@ -3625,6 +3633,8 @@ static void d3d12_init_render_targets(d3d12_video_t* d3d12, unsigned width, unsi
d3d12->pass[i].rt.desc.Flags = D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET;
d3d12->pass[i].rt.srv_heap = &d3d12->desc.srv_heap;
d3d12->pass[i].rt.desc.Format = glslang_format_to_dxgi(d3d12->pass[i].semantics.format);
/* Initialize MipLevels so mipmaps are created for render target */
d3d12->pass[i].rt.desc.MipLevels = 0;
d3d12_release_texture(&d3d12->pass[i].rt);
d3d12_init_texture(d3d12->device, &d3d12->pass[i].rt);
@@ -4258,6 +4268,9 @@ static bool d3d12_gfx_frame(
d3d12->pass[i].rt.handle,
D3D12_RESOURCE_STATE_RENDER_TARGET,
D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE);
/* Generate mipmaps for framebuffer if it has multiple mipmap levels */
d3d12_generate_mipmaps(cmd, &d3d12->pass[i].rt, d3d12);
texture = &d3d12->pass[i].rt;
}
else