diff --git a/src/xenia/gpu/d3d12/render_target_cache.cc b/src/xenia/gpu/d3d12/render_target_cache.cc index c53cf4271..02c5d45c9 100644 --- a/src/xenia/gpu/d3d12/render_target_cache.cc +++ b/src/xenia/gpu/d3d12/render_target_cache.cc @@ -1128,24 +1128,22 @@ bool RenderTargetCache::ResolveCopy(SharedMemory* shared_memory, DepthRenderTargetToTextureFormat(DepthRenderTargetFormat(src_format)); src_64bpp = false; } else { - // Texture formats k_16_16_EDRAM and k_16_16_16_16_EDRAM are not the same as - // k_16_16 and k_16_16_16_16, but they are emulated with the same DXGI - // formats as k_16_16 and k_16_16_16_16 on the host, so they are treated as - // a special case of such formats. + // Force k_16_16 and k_16_16_16_16 RTs to be always resolved via drawing, + // because resolving to a k_16_16 or a k_16_16_16_16 texture should result + // in unsigned texture data, unlike the render target which is signed. if (ColorRenderTargetFormat(src_format) == ColorRenderTargetFormat::k_16_16) { - src_texture_format = TextureFormat::k_16_16; + src_texture_format = TextureFormat::k_16_16_EDRAM; } else if (ColorRenderTargetFormat(src_format) == ColorRenderTargetFormat::k_16_16_16_16) { - src_texture_format = TextureFormat::k_16_16_16_16; + src_texture_format = TextureFormat::k_16_16_16_16_EDRAM; } else { - src_texture_format = - ColorRenderTargetToTextureFormat(ColorRenderTargetFormat(src_format)); + src_texture_format = GetBaseFormat(ColorRenderTargetToTextureFormat( + ColorRenderTargetFormat(src_format))); } src_64bpp = IsColorFormat64bpp(ColorRenderTargetFormat(src_format)); } assert_true(src_texture_format != TextureFormat::kUnknown); - src_texture_format = GetBaseFormat(src_texture_format); // The destination format is specified as k_8_8_8_8 when resolving depth, // apparently there's no format conversion. TextureFormat dest_format = diff --git a/src/xenia/gpu/d3d12/texture_cache.cc b/src/xenia/gpu/d3d12/texture_cache.cc index 07da70e4d..db55e8bc9 100644 --- a/src/xenia/gpu/d3d12/texture_cache.cc +++ b/src/xenia/gpu/d3d12/texture_cache.cc @@ -199,18 +199,18 @@ const TextureCache::HostFormat TextureCache::host_formats_[64] = { DXGI_FORMAT_R16_SNORM, LoadMode::kUnknown, DXGI_FORMAT_UNKNOWN, LoadMode::kUnknown, DXGI_FORMAT_R16_UNORM, ResolveTileMode::k16bpp, true}, // k_16_16 - // TODO(Triang3l): Check if this is the correct way of specifying a signed - // resolve destination format. + // The resolve format being unorm is correct (with snorm distortion effects + // in Halo 3 cause stretching of one corner of the screen). {DXGI_FORMAT_R16G16_TYPELESS, DXGI_FORMAT_R16G16_UNORM, LoadMode::k32bpb, DXGI_FORMAT_R16G16_SNORM, LoadMode::kUnknown, DXGI_FORMAT_UNKNOWN, - LoadMode::kUnknown, DXGI_FORMAT_R16G16_SNORM, ResolveTileMode::k32bpp, + LoadMode::kUnknown, DXGI_FORMAT_R16G16_UNORM, ResolveTileMode::k32bpp, false}, // k_16_16_16_16 - // TODO(Triang3l): Check if this is the correct way of specifying a signed - // resolve destination format. + // The resolve format being unorm is correct (with snorm distortion effects + // in Halo 3 cause stretching of one corner of the screen). {DXGI_FORMAT_R16G16B16A16_TYPELESS, DXGI_FORMAT_R16G16B16A16_UNORM, LoadMode::k64bpb, DXGI_FORMAT_R16G16B16A16_SNORM, LoadMode::kUnknown, - DXGI_FORMAT_UNKNOWN, LoadMode::kUnknown, DXGI_FORMAT_R16G16B16A16_SNORM, + DXGI_FORMAT_UNKNOWN, LoadMode::kUnknown, DXGI_FORMAT_R16G16B16A16_UNORM, ResolveTileMode::k64bpp, false}, // k_16_EXPAND {DXGI_FORMAT_R16_FLOAT, DXGI_FORMAT_R16_FLOAT, LoadMode::k16bpb,