D3D11: Support native compressed textures
This commit is contained in:
parent
f5d95dcc86
commit
2d75c2ab10
|
@ -239,6 +239,19 @@ D3D_FEATURE_LEVEL GetFeatureLevel(IDXGIAdapter* adapter)
|
||||||
return feat_level;
|
return feat_level;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool SupportsS3TCTextures(ID3D11Device* device)
|
||||||
|
{
|
||||||
|
UINT bc1_support, bc2_support, bc3_support;
|
||||||
|
if (FAILED(device->CheckFormatSupport(DXGI_FORMAT_BC1_UNORM, &bc1_support)) ||
|
||||||
|
FAILED(device->CheckFormatSupport(DXGI_FORMAT_BC2_UNORM, &bc2_support)) ||
|
||||||
|
FAILED(device->CheckFormatSupport(DXGI_FORMAT_BC3_UNORM, &bc3_support)))
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ((bc1_support & bc2_support & bc3_support) & D3D11_FORMAT_SUPPORT_TEXTURE2D) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
HRESULT Create(HWND wnd)
|
HRESULT Create(HWND wnd)
|
||||||
{
|
{
|
||||||
hWnd = wnd;
|
hWnd = wnd;
|
||||||
|
@ -427,6 +440,7 @@ HRESULT Create(HWND wnd)
|
||||||
UINT format_support;
|
UINT format_support;
|
||||||
device->CheckFormatSupport(DXGI_FORMAT_B8G8R8A8_UNORM, &format_support);
|
device->CheckFormatSupport(DXGI_FORMAT_B8G8R8A8_UNORM, &format_support);
|
||||||
bgra_textures_supported = (format_support & D3D11_FORMAT_SUPPORT_TEXTURE2D) != 0;
|
bgra_textures_supported = (format_support & D3D11_FORMAT_SUPPORT_TEXTURE2D) != 0;
|
||||||
|
g_Config.backend_info.bSupportsST3CTextures = SupportsS3TCTextures(device);
|
||||||
|
|
||||||
stateman = new StateManager;
|
stateman = new StateManager;
|
||||||
return S_OK;
|
return S_OK;
|
||||||
|
|
|
@ -7,6 +7,7 @@
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
|
#include "Common/Assert.h"
|
||||||
#include "Common/CommonTypes.h"
|
#include "Common/CommonTypes.h"
|
||||||
#include "Common/Logging/Log.h"
|
#include "Common/Logging/Log.h"
|
||||||
|
|
||||||
|
@ -29,6 +30,42 @@ static std::unique_ptr<PSTextureEncoder> g_encoder;
|
||||||
const size_t MAX_COPY_BUFFERS = 32;
|
const size_t MAX_COPY_BUFFERS = 32;
|
||||||
ID3D11Buffer* efbcopycbuf[MAX_COPY_BUFFERS] = {0};
|
ID3D11Buffer* efbcopycbuf[MAX_COPY_BUFFERS] = {0};
|
||||||
|
|
||||||
|
static u32 GetLevelPitch(HostTextureFormat format, u32 row_length)
|
||||||
|
{
|
||||||
|
switch (format)
|
||||||
|
{
|
||||||
|
case HostTextureFormat::DXT1:
|
||||||
|
return row_length / 4 * 8;
|
||||||
|
|
||||||
|
case HostTextureFormat::DXT3:
|
||||||
|
case HostTextureFormat::DXT5:
|
||||||
|
return row_length / 4 * 16;
|
||||||
|
|
||||||
|
case HostTextureFormat::RGBA8:
|
||||||
|
default:
|
||||||
|
return row_length * 4;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static DXGI_FORMAT GetDXGIFormatForHostFormat(HostTextureFormat format)
|
||||||
|
{
|
||||||
|
switch (format)
|
||||||
|
{
|
||||||
|
case HostTextureFormat::DXT1:
|
||||||
|
return DXGI_FORMAT_BC1_UNORM;
|
||||||
|
|
||||||
|
case HostTextureFormat::DXT3:
|
||||||
|
return DXGI_FORMAT_BC2_UNORM;
|
||||||
|
|
||||||
|
case HostTextureFormat::DXT5:
|
||||||
|
return DXGI_FORMAT_BC3_UNORM;
|
||||||
|
|
||||||
|
case HostTextureFormat::RGBA8:
|
||||||
|
default:
|
||||||
|
return DXGI_FORMAT_R8G8B8A8_UNORM;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
TextureCache::TCacheEntry::~TCacheEntry()
|
TextureCache::TCacheEntry::~TCacheEntry()
|
||||||
{
|
{
|
||||||
texture->Release();
|
texture->Release();
|
||||||
|
@ -41,6 +78,11 @@ void TextureCache::TCacheEntry::Bind(unsigned int stage)
|
||||||
|
|
||||||
bool TextureCache::TCacheEntry::Save(const std::string& filename, unsigned int level)
|
bool TextureCache::TCacheEntry::Save(const std::string& filename, unsigned int level)
|
||||||
{
|
{
|
||||||
|
// We can't dump compressed textures currently (it would mean drawing them to a RGBA8
|
||||||
|
// framebuffer, and saving that). TextureCache does not call Save for custom textures
|
||||||
|
// anyway, so this is fine for now.
|
||||||
|
_assert_(config.format == HostTextureFormat::RGBA8);
|
||||||
|
|
||||||
// Create a staging/readback texture with the dimensions of the specified mip level.
|
// Create a staging/readback texture with the dimensions of the specified mip level.
|
||||||
u32 mip_width = std::max(config.width >> level, 1u);
|
u32 mip_width = std::max(config.width >> level, 1u);
|
||||||
u32 mip_height = std::max(config.height >> level, 1u);
|
u32 mip_height = std::max(config.height >> level, 1u);
|
||||||
|
@ -132,25 +174,26 @@ void TextureCache::TCacheEntry::CopyRectangleFromTexture(const TCacheEntryBase*
|
||||||
void TextureCache::TCacheEntry::Load(u32 level, u32 width, u32 height, u32 row_length,
|
void TextureCache::TCacheEntry::Load(u32 level, u32 width, u32 height, u32 row_length,
|
||||||
const u8* buffer, size_t buffer_size)
|
const u8* buffer, size_t buffer_size)
|
||||||
{
|
{
|
||||||
u32 src_pitch = row_length * 4;
|
u32 src_pitch = GetLevelPitch(config.format, row_length);
|
||||||
D3D::context->UpdateSubresource(texture->GetTex(), level, nullptr, buffer, src_pitch, 0);
|
D3D::context->UpdateSubresource(texture->GetTex(), level, nullptr, buffer, src_pitch, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
TextureCacheBase::TCacheEntryBase* TextureCache::CreateTexture(const TCacheEntryConfig& config)
|
TextureCacheBase::TCacheEntryBase* TextureCache::CreateTexture(const TCacheEntryConfig& config)
|
||||||
{
|
{
|
||||||
|
DXGI_FORMAT dxgi_format = GetDXGIFormatForHostFormat(config.format);
|
||||||
if (config.rendertarget)
|
if (config.rendertarget)
|
||||||
{
|
{
|
||||||
return new TCacheEntry(
|
return new TCacheEntry(
|
||||||
config, D3DTexture2D::Create(
|
config, D3DTexture2D::Create(config.width, config.height,
|
||||||
config.width, config.height, (D3D11_BIND_FLAG)((int)D3D11_BIND_RENDER_TARGET |
|
(D3D11_BIND_FLAG)((int)D3D11_BIND_RENDER_TARGET |
|
||||||
(int)D3D11_BIND_SHADER_RESOURCE),
|
(int)D3D11_BIND_SHADER_RESOURCE),
|
||||||
D3D11_USAGE_DEFAULT, DXGI_FORMAT_R8G8B8A8_UNORM, 1, config.layers));
|
D3D11_USAGE_DEFAULT, dxgi_format, 1, config.layers));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
const D3D11_TEXTURE2D_DESC texdesc =
|
const D3D11_TEXTURE2D_DESC texdesc =
|
||||||
CD3D11_TEXTURE2D_DESC(DXGI_FORMAT_R8G8B8A8_UNORM, config.width, config.height, 1,
|
CD3D11_TEXTURE2D_DESC(dxgi_format, config.width, config.height, 1, config.levels,
|
||||||
config.levels, D3D11_BIND_SHADER_RESOURCE, D3D11_USAGE_DEFAULT, 0);
|
D3D11_BIND_SHADER_RESOURCE, D3D11_USAGE_DEFAULT, 0);
|
||||||
|
|
||||||
ID3D11Texture2D* pTexture;
|
ID3D11Texture2D* pTexture;
|
||||||
const HRESULT hr = D3D::device->CreateTexture2D(&texdesc, nullptr, &pTexture);
|
const HRESULT hr = D3D::device->CreateTexture2D(&texdesc, nullptr, &pTexture);
|
||||||
|
|
Loading…
Reference in New Issue