mirror of https://github.com/PCSX2/pcsx2.git
GS:MTL: Implement clut shaders
This commit is contained in:
parent
e20c2210f5
commit
a2e3522862
|
@ -242,6 +242,7 @@ public:
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_merge_pipeline[4];
|
MRCOwned<id<MTLRenderPipelineState>> m_merge_pipeline[4];
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_interlace_pipeline[NUM_INTERLACE_SHADERS];
|
MRCOwned<id<MTLRenderPipelineState>> m_interlace_pipeline[NUM_INTERLACE_SHADERS];
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_datm_pipeline[2];
|
MRCOwned<id<MTLRenderPipelineState>> m_datm_pipeline[2];
|
||||||
|
MRCOwned<id<MTLRenderPipelineState>> m_clut_pipeline[2];
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_stencil_clear_pipeline;
|
MRCOwned<id<MTLRenderPipelineState>> m_stencil_clear_pipeline;
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_primid_init_pipeline[2][2];
|
MRCOwned<id<MTLRenderPipelineState>> m_primid_init_pipeline[2][2];
|
||||||
MRCOwned<id<MTLRenderPipelineState>> m_hdr_init_pipeline;
|
MRCOwned<id<MTLRenderPipelineState>> m_hdr_init_pipeline;
|
||||||
|
@ -371,6 +372,7 @@ public:
|
||||||
void StretchRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, ShaderConvert shader = ShaderConvert::COPY, bool linear = true) override;
|
void StretchRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, ShaderConvert shader = ShaderConvert::COPY, bool linear = true) override;
|
||||||
void StretchRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, bool red, bool green, bool blue, bool alpha) override;
|
void StretchRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, bool red, bool green, bool blue, bool alpha) override;
|
||||||
void PresentRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, PresentShader shader, float shaderTime, bool linear) override;
|
void PresentRect(GSTexture* sTex, const GSVector4& sRect, GSTexture* dTex, const GSVector4& dRect, PresentShader shader, float shaderTime, bool linear) override;
|
||||||
|
void UpdateCLUTTexture(GSTexture* sTex, u32 offsetX, u32 offsetY, GSTexture* dTex, u32 dOffset, u32 dSize) override;
|
||||||
|
|
||||||
void FlushClears(GSTexture* tex);
|
void FlushClears(GSTexture* tex);
|
||||||
|
|
||||||
|
|
|
@ -26,6 +26,11 @@
|
||||||
#ifdef __APPLE__
|
#ifdef __APPLE__
|
||||||
#include "GSMTLSharedHeader.h"
|
#include "GSMTLSharedHeader.h"
|
||||||
|
|
||||||
|
static constexpr simd::float2 ToSimd(const GSVector2& vec)
|
||||||
|
{
|
||||||
|
return simd::make_float2(vec.x, vec.y);
|
||||||
|
}
|
||||||
|
|
||||||
static constexpr bool IsCommandBufferCompleted(MTLCommandBufferStatus status)
|
static constexpr bool IsCommandBufferCompleted(MTLCommandBufferStatus status)
|
||||||
{
|
{
|
||||||
switch (status)
|
switch (status)
|
||||||
|
@ -918,6 +923,8 @@ bool GSDeviceMTL::Create()
|
||||||
m_hdr_resolve_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_hdr_resolve"), @"HDR Resolve");
|
m_hdr_resolve_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_hdr_resolve"), @"HDR Resolve");
|
||||||
m_fxaa_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_fxaa"), @"fxaa");
|
m_fxaa_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_fxaa"), @"fxaa");
|
||||||
m_shadeboost_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_shadeboost"), @"shadeboost");
|
m_shadeboost_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_shadeboost"), @"shadeboost");
|
||||||
|
m_clut_pipeline[0] = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_convert_clut_4"), @"4-bit CLUT Update");
|
||||||
|
m_clut_pipeline[1] = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_convert_clut_8"), @"8-bit CLUT Update");
|
||||||
pdesc.colorAttachments[0].pixelFormat = ConvertPixelFormat(GSTexture::Format::HDRColor);
|
pdesc.colorAttachments[0].pixelFormat = ConvertPixelFormat(GSTexture::Format::HDRColor);
|
||||||
m_hdr_init_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_hdr_init"), @"HDR Init");
|
m_hdr_init_pipeline = MakePipeline(pdesc, fs_triangle, LoadShader(@"ps_hdr_init"), @"HDR Init");
|
||||||
pdesc.colorAttachments[0].pixelFormat = MTLPixelFormatInvalid;
|
pdesc.colorAttachments[0].pixelFormat = MTLPixelFormatInvalid;
|
||||||
|
@ -954,6 +961,8 @@ bool GSDeviceMTL::Create()
|
||||||
case ShaderConvert::Count:
|
case ShaderConvert::Count:
|
||||||
case ShaderConvert::DATM_0:
|
case ShaderConvert::DATM_0:
|
||||||
case ShaderConvert::DATM_1:
|
case ShaderConvert::DATM_1:
|
||||||
|
case ShaderConvert::CLUT_4:
|
||||||
|
case ShaderConvert::CLUT_8:
|
||||||
case ShaderConvert::HDR_INIT:
|
case ShaderConvert::HDR_INIT:
|
||||||
case ShaderConvert::HDR_RESOLVE:
|
case ShaderConvert::HDR_RESOLVE:
|
||||||
continue;
|
continue;
|
||||||
|
@ -1298,6 +1307,18 @@ void GSDeviceMTL::PresentRect(GSTexture* sTex, const GSVector4& sRect, GSTexture
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
|
|
||||||
|
void GSDeviceMTL::UpdateCLUTTexture(GSTexture* sTex, u32 offsetX, u32 offsetY, GSTexture* dTex, u32 dOffset, u32 dSize)
|
||||||
|
{
|
||||||
|
GSMTLCLUTConvertPSUniform uniform = { ToSimd(sTex->GetScale()), {offsetX, offsetY}, dOffset };
|
||||||
|
|
||||||
|
const bool is_clut4 = dSize == 16;
|
||||||
|
const GSVector4i dRect(0, 0, dSize, 1);
|
||||||
|
|
||||||
|
BeginRenderPass(@"CLUT Update", dTex, MTLLoadActionDontCare, nullptr, MTLLoadActionDontCare);
|
||||||
|
[m_current_render.encoder setFragmentBytes:&uniform length:sizeof(uniform) atIndex:GSMTLBufferIndexUniforms];
|
||||||
|
RenderCopy(sTex, m_clut_pipeline[!is_clut4], dRect);
|
||||||
|
}
|
||||||
|
|
||||||
void GSDeviceMTL::FlushClears(GSTexture* tex)
|
void GSDeviceMTL::FlushClears(GSTexture* tex)
|
||||||
{
|
{
|
||||||
if (tex)
|
if (tex)
|
||||||
|
|
|
@ -64,6 +64,13 @@ struct GSMTLCASPSUniform
|
||||||
vector_int2 srcOffset;
|
vector_int2 srcOffset;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct GSMTLCLUTConvertPSUniform
|
||||||
|
{
|
||||||
|
vector_float2 scale;
|
||||||
|
vector_uint2 offset;
|
||||||
|
uint doffset;
|
||||||
|
};
|
||||||
|
|
||||||
struct GSMTLMainVertex
|
struct GSMTLMainVertex
|
||||||
{
|
{
|
||||||
vector_float2 st;
|
vector_float2 st;
|
||||||
|
|
|
@ -282,6 +282,35 @@ fragment float4 ps_convert_rgba_8i(ConvertShaderData data [[stage_in]], DirectRe
|
||||||
return float4(sel1);
|
return float4(sel1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fragment float4 ps_convert_clut_4(ConvertShaderData data [[stage_in]],
|
||||||
|
texture2d<float> texture [[texture(GSMTLTextureIndexNonHW)]],
|
||||||
|
constant GSMTLCLUTConvertPSUniform& uniform [[buffer(GSMTLBufferIndexUniforms)]])
|
||||||
|
{
|
||||||
|
// CLUT4 is easy, just two rows of 8x8.
|
||||||
|
uint index = uint(data.p.x) + uniform.doffset;
|
||||||
|
uint2 pos = uint2(index % 8, index / 8);
|
||||||
|
|
||||||
|
uint2 final = uint2(float2(uniform.offset + pos) * uniform.scale);
|
||||||
|
return texture.read(final);
|
||||||
|
}
|
||||||
|
|
||||||
|
fragment float4 ps_convert_clut_8(ConvertShaderData data [[stage_in]],
|
||||||
|
texture2d<float> texture [[texture(GSMTLTextureIndexNonHW)]],
|
||||||
|
constant GSMTLCLUTConvertPSUniform& uniform [[buffer(GSMTLBufferIndexUniforms)]])
|
||||||
|
{
|
||||||
|
uint index = min(uint(data.p.x) + uniform.doffset, 255u);
|
||||||
|
|
||||||
|
// CLUT is arranged into 8 groups of 16x2, with the top-right and bottom-left quadrants swapped.
|
||||||
|
// This can probably be done better..
|
||||||
|
uint subgroup = (index / 8) % 4;
|
||||||
|
uint2 pos;
|
||||||
|
pos.x = (index % 8) + ((subgroup >= 2) ? 8 :0u);
|
||||||
|
pos.y = ((index / 32u) * 2u) + (subgroup % 2u);
|
||||||
|
|
||||||
|
uint2 final = uint2(float2(uniform.offset + pos) * uniform.scale);
|
||||||
|
return texture.read(final);
|
||||||
|
}
|
||||||
|
|
||||||
fragment float4 ps_yuv(ConvertShaderData data [[stage_in]], ConvertPSRes res,
|
fragment float4 ps_yuv(ConvertShaderData data [[stage_in]], ConvertPSRes res,
|
||||||
constant GSMTLConvertPSUniform& uniform [[buffer(GSMTLBufferIndexUniforms)]])
|
constant GSMTLConvertPSUniform& uniform [[buffer(GSMTLBufferIndexUniforms)]])
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue