From 6a7d601e428f6d03a90cd7a23f1700bb488354c4 Mon Sep 17 00:00:00 2001 From: emufan4568 Date: Sat, 20 Aug 2022 12:17:31 +0300 Subject: [PATCH] rasterizer_cache: Factor morton swizzle and pixel format to dedicate headers * Makes the code cleaner in general by not having to alias PixelFormat and SurfaceType everywhere --- src/video_core/CMakeLists.txt | 2 + .../rasterizer_cache/morton_swizzle.h | 171 ++++++++++++++ .../rasterizer_cache/pixel_format.h | 194 ++++++++++++++++ .../rasterizer_cache/rasterizer_cache.cpp | 212 ++---------------- .../rasterizer_cache/rasterizer_cache.h | 11 +- .../rasterizer_cache/surface_params.cpp | 15 +- .../rasterizer_cache/surface_params.h | 183 +-------------- .../gl_format_reinterpreter.cpp | 2 - .../renderer_opengl/gl_format_reinterpreter.h | 20 +- .../renderer_opengl/gl_rasterizer.cpp | 9 +- .../texture_filters/texture_filter_base.h | 2 +- .../texture_filters/texture_filterer.cpp | 9 +- .../texture_filters/texture_filterer.h | 6 +- 13 files changed, 427 insertions(+), 409 deletions(-) create mode 100644 src/video_core/rasterizer_cache/morton_swizzle.h create mode 100644 src/video_core/rasterizer_cache/pixel_format.h diff --git a/src/video_core/CMakeLists.txt b/src/video_core/CMakeLists.txt index d63b9e002..2975a7a6c 100644 --- a/src/video_core/CMakeLists.txt +++ b/src/video_core/CMakeLists.txt @@ -23,6 +23,8 @@ add_library(video_core STATIC regs_texturing.h renderer_base.cpp renderer_base.h + rasterizer_cache/morton_swizzle.h + rasterizer_cache/pixel_format.h rasterizer_cache/rasterizer_cache.cpp rasterizer_cache/rasterizer_cache.h rasterizer_cache/surface_params.cpp diff --git a/src/video_core/rasterizer_cache/morton_swizzle.h b/src/video_core/rasterizer_cache/morton_swizzle.h new file mode 100644 index 000000000..e8cfc87cd --- /dev/null +++ b/src/video_core/rasterizer_cache/morton_swizzle.h @@ -0,0 +1,171 @@ +// Copyright 2022 Citra Emulator Project +// Licensed under GPLv2 or any later version +// Refer to the license.txt file included. + +#pragma once +#include "common/alignment.h" +#include "core/memory.h" +#include "video_core/rasterizer_cache/pixel_format.h" +#include "video_core/renderer_opengl/gl_vars.h" +#include "video_core/utils.h" +#include "video_core/video_core.h" + +namespace OpenGL { + +template +static void MortonCopyTile(u32 stride, u8* tile_buffer, u8* gl_buffer) { + constexpr u32 bytes_per_pixel = GetFormatBpp(format) / 8; + constexpr u32 aligned_bytes_per_pixel = GetBytesPerPixel(format); + for (u32 y = 0; y < 8; ++y) { + for (u32 x = 0; x < 8; ++x) { + u8* tile_ptr = tile_buffer + VideoCore::MortonInterleave(x, y) * bytes_per_pixel; + u8* gl_ptr = gl_buffer + ((7 - y) * stride + x) * aligned_bytes_per_pixel; + if constexpr (morton_to_gl) { + if constexpr (format == PixelFormat::D24S8) { + gl_ptr[0] = tile_ptr[3]; + std::memcpy(gl_ptr + 1, tile_ptr, 3); + } else if (format == PixelFormat::RGBA8 && GLES) { + // because GLES does not have ABGR format + // so we will do byteswapping here + gl_ptr[0] = tile_ptr[3]; + gl_ptr[1] = tile_ptr[2]; + gl_ptr[2] = tile_ptr[1]; + gl_ptr[3] = tile_ptr[0]; + } else if (format == PixelFormat::RGB8 && GLES) { + gl_ptr[0] = tile_ptr[2]; + gl_ptr[1] = tile_ptr[1]; + gl_ptr[2] = tile_ptr[0]; + } else { + std::memcpy(gl_ptr, tile_ptr, bytes_per_pixel); + } + } else { + if constexpr (format == PixelFormat::D24S8) { + std::memcpy(tile_ptr, gl_ptr + 1, 3); + tile_ptr[3] = gl_ptr[0]; + } else if (format == PixelFormat::RGBA8 && GLES) { + // because GLES does not have ABGR format + // so we will do byteswapping here + tile_ptr[0] = gl_ptr[3]; + tile_ptr[1] = gl_ptr[2]; + tile_ptr[2] = gl_ptr[1]; + tile_ptr[3] = gl_ptr[0]; + } else if (format == PixelFormat::RGB8 && GLES) { + tile_ptr[0] = gl_ptr[2]; + tile_ptr[1] = gl_ptr[1]; + tile_ptr[2] = gl_ptr[0]; + } else { + std::memcpy(tile_ptr, gl_ptr, bytes_per_pixel); + } + } + } + } +} + +template +static void MortonCopy(u32 stride, u32 height, u8* gl_buffer, PAddr base, PAddr start, PAddr end) { + constexpr u32 bytes_per_pixel = GetFormatBpp(format) / 8; + constexpr u32 tile_size = bytes_per_pixel * 64; + + constexpr u32 aligned_bytes_per_pixel = GetBytesPerPixel(format); + static_assert(aligned_bytes_per_pixel >= bytes_per_pixel, ""); + gl_buffer += aligned_bytes_per_pixel - bytes_per_pixel; + + const PAddr aligned_down_start = base + Common::AlignDown(start - base, tile_size); + const PAddr aligned_start = base + Common::AlignUp(start - base, tile_size); + const PAddr aligned_end = base + Common::AlignDown(end - base, tile_size); + + ASSERT(!morton_to_gl || (aligned_start == start && aligned_end == end)); + + const u32 begin_pixel_index = (aligned_down_start - base) / bytes_per_pixel; + u32 x = (begin_pixel_index % (stride * 8)) / 8; + u32 y = (begin_pixel_index / (stride * 8)) * 8; + + gl_buffer += ((height - 8 - y) * stride + x) * aligned_bytes_per_pixel; + + auto glbuf_next_tile = [&] { + x = (x + 8) % stride; + gl_buffer += 8 * aligned_bytes_per_pixel; + if (!x) { + y += 8; + gl_buffer -= stride * 9 * aligned_bytes_per_pixel; + } + }; + + u8* tile_buffer = VideoCore::g_memory->GetPhysicalPointer(start); + + if (start < aligned_start && !morton_to_gl) { + std::array tmp_buf; + MortonCopyTile(stride, &tmp_buf[0], gl_buffer); + std::memcpy(tile_buffer, &tmp_buf[start - aligned_down_start], + std::min(aligned_start, end) - start); + + tile_buffer += aligned_start - start; + glbuf_next_tile(); + } + + const u8* const buffer_end = tile_buffer + aligned_end - aligned_start; + PAddr current_paddr = aligned_start; + while (tile_buffer < buffer_end) { + // Pokemon Super Mystery Dungeon will try to use textures that go beyond + // the end address of VRAM. Stop reading if reaches invalid address + if (!VideoCore::g_memory->IsValidPhysicalAddress(current_paddr) || + !VideoCore::g_memory->IsValidPhysicalAddress(current_paddr + tile_size)) { + LOG_ERROR(Render_OpenGL, "Out of bound texture"); + break; + } + MortonCopyTile(stride, tile_buffer, gl_buffer); + tile_buffer += tile_size; + current_paddr += tile_size; + glbuf_next_tile(); + } + + if (end > std::max(aligned_start, aligned_end) && !morton_to_gl) { + std::array tmp_buf; + MortonCopyTile(stride, &tmp_buf[0], gl_buffer); + std::memcpy(tile_buffer, &tmp_buf[0], end - aligned_end); + } +} + +static constexpr std::array morton_to_gl_fns = { + MortonCopy, // 0 + MortonCopy, // 1 + MortonCopy, // 2 + MortonCopy, // 3 + MortonCopy, // 4 + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, // 5 - 13 + MortonCopy, // 14 + nullptr, // 15 + MortonCopy, // 16 + MortonCopy // 17 +}; + +static constexpr std::array gl_to_morton_fns = { + MortonCopy, // 0 + MortonCopy, // 1 + MortonCopy, // 2 + MortonCopy, // 3 + MortonCopy, // 4 + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, + nullptr, // 5 - 13 + MortonCopy, // 14 + nullptr, // 15 + MortonCopy, // 16 + MortonCopy // 17 +}; + +} // namespace OpenGL diff --git a/src/video_core/rasterizer_cache/pixel_format.h b/src/video_core/rasterizer_cache/pixel_format.h new file mode 100644 index 000000000..a7a5b6fe6 --- /dev/null +++ b/src/video_core/rasterizer_cache/pixel_format.h @@ -0,0 +1,194 @@ +// Copyright 2022 Citra Emulator Project +// Licensed under GPLv2 or any later version +// Refer to the license.txt file included. + +#pragma once +#include +#include "core/hw/gpu.h" +#include "video_core/regs_texturing.h" +#include "video_core/regs_framebuffer.h" + +namespace OpenGL { + +enum class PixelFormat : u8 { + // First 5 formats are shared between textures and color buffers + RGBA8 = 0, + RGB8 = 1, + RGB5A1 = 2, + RGB565 = 3, + RGBA4 = 4, + // Texture-only formats + IA8 = 5, + RG8 = 6, + I8 = 7, + A8 = 8, + IA4 = 9, + I4 = 10, + A4 = 11, + ETC1 = 12, + ETC1A4 = 13, + // Depth buffer-only formats + D16 = 14, + D24 = 16, + D24S8 = 17, + Invalid = 255, +}; + +enum class SurfaceType { + Color = 0, + Texture = 1, + Depth = 2, + DepthStencil = 3, + Fill = 4, + Invalid = 5 +}; + +static constexpr std::string_view PixelFormatAsString(PixelFormat format) { + switch (format) { + case PixelFormat::RGBA8: + return "RGBA8"; + case PixelFormat::RGB8: + return "RGB8"; + case PixelFormat::RGB5A1: + return "RGB5A1"; + case PixelFormat::RGB565: + return "RGB565"; + case PixelFormat::RGBA4: + return "RGBA4"; + case PixelFormat::IA8: + return "IA8"; + case PixelFormat::RG8: + return "RG8"; + case PixelFormat::I8: + return "I8"; + case PixelFormat::A8: + return "A8"; + case PixelFormat::IA4: + return "IA4"; + case PixelFormat::I4: + return "I4"; + case PixelFormat::A4: + return "A4"; + case PixelFormat::ETC1: + return "ETC1"; + case PixelFormat::ETC1A4: + return "ETC1A4"; + case PixelFormat::D16: + return "D16"; + case PixelFormat::D24: + return "D24"; + case PixelFormat::D24S8: + return "D24S8"; + default: + return "NotReal"; + } +} + +static constexpr PixelFormat PixelFormatFromTextureFormat(Pica::TexturingRegs::TextureFormat format) { + const u32 format_index = static_cast(format); + return (format_index < 14) ? static_cast(format) : PixelFormat::Invalid; +} + +static constexpr PixelFormat PixelFormatFromColorFormat(Pica::FramebufferRegs::ColorFormat format) { + const u32 format_index = static_cast(format); + return (format_index < 5) ? static_cast(format) : PixelFormat::Invalid; +} + +static PixelFormat PixelFormatFromDepthFormat(Pica::FramebufferRegs::DepthFormat format) { + const u32 format_index = static_cast(format); + return (format_index < 4) ? static_cast(format_index + 14) + : PixelFormat::Invalid; +} + +static constexpr PixelFormat PixelFormatFromGPUPixelFormat(GPU::Regs::PixelFormat format) { + switch (format) { + // RGB565 and RGB5A1 are switched in PixelFormat compared to ColorFormat + case GPU::Regs::PixelFormat::RGB565: + return PixelFormat::RGB565; + case GPU::Regs::PixelFormat::RGB5A1: + return PixelFormat::RGB5A1; + default: + return ((unsigned int)format < 5) ? (PixelFormat)format : PixelFormat::Invalid; + } +} + +static constexpr SurfaceType GetFormatType(PixelFormat pixel_format) { + const u32 format_index = static_cast(pixel_format); + if (format_index < 5) { + return SurfaceType::Color; + } + + if (format_index < 14) { + return SurfaceType::Texture; + } + + if (pixel_format == PixelFormat::D16 || pixel_format == PixelFormat::D24) { + return SurfaceType::Depth; + } + + if (pixel_format == PixelFormat::D24S8) { + return SurfaceType::DepthStencil; + } + + return SurfaceType::Invalid; +} + +static constexpr bool CheckFormatsBlittable(PixelFormat source_format, PixelFormat dest_format) { + SurfaceType source_type = GetFormatType(source_format); + SurfaceType dest_type = GetFormatType(dest_format); + + if ((source_type == SurfaceType::Color || source_type == SurfaceType::Texture) && + (dest_type == SurfaceType::Color || dest_type == SurfaceType::Texture)) { + return true; + } + + if (source_type == SurfaceType::Depth && dest_type == SurfaceType::Depth) { + return true; + } + + if (source_type == SurfaceType::DepthStencil && dest_type == SurfaceType::DepthStencil) { + return true; + } + + return false; +} + +static constexpr u32 GetFormatBpp(PixelFormat format) { + switch (format) { + case PixelFormat::RGBA8: + case PixelFormat::D24S8: + return 32; + case PixelFormat::RGB8: + case PixelFormat::D24: + return 24; + case PixelFormat::RGB5A1: + case PixelFormat::RGB565: + case PixelFormat::RGBA4: + case PixelFormat::IA8: + case PixelFormat::RG8: + case PixelFormat::D16: + return 16; + case PixelFormat::I8: + case PixelFormat::A8: + case PixelFormat::IA4: + case PixelFormat::ETC1A4: + return 8; + case PixelFormat::I4: + case PixelFormat::A4: + case PixelFormat::ETC1: + return 4; + case PixelFormat::Invalid: + return 0; + } +} + +static constexpr u32 GetBytesPerPixel(PixelFormat format) { + // OpenGL needs 4 bpp alignment for D24 since using GL_UNSIGNED_INT as type + if (format == PixelFormat::D24 || GetFormatType(format) == SurfaceType::Texture) { + return 4; + } + + return GetFormatBpp(format) / 8; +} + +} // namespace OpenGL diff --git a/src/video_core/rasterizer_cache/rasterizer_cache.cpp b/src/video_core/rasterizer_cache/rasterizer_cache.cpp index 06c8fa564..1d03468f5 100644 --- a/src/video_core/rasterizer_cache/rasterizer_cache.cpp +++ b/src/video_core/rasterizer_cache/rasterizer_cache.cpp @@ -29,24 +29,17 @@ #include "core/custom_tex_cache.h" #include "core/frontend/emu_window.h" #include "core/hle/kernel/process.h" -#include "core/memory.h" #include "core/settings.h" #include "video_core/pica_state.h" -#include "video_core/renderer_base.h" #include "video_core/renderer_opengl/gl_format_reinterpreter.h" +#include "video_core/rasterizer_cache/morton_swizzle.h" #include "video_core/rasterizer_cache/rasterizer_cache.h" #include "video_core/renderer_opengl/gl_state.h" -#include "video_core/renderer_opengl/gl_vars.h" #include "video_core/renderer_opengl/texture_downloader_es.h" #include "video_core/renderer_opengl/texture_filters/texture_filterer.h" -#include "video_core/utils.h" -#include "video_core/video_core.h" namespace OpenGL { -using SurfaceType = SurfaceParams::SurfaceType; -using PixelFormat = SurfaceParams::PixelFormat; - static constexpr std::array fb_format_tuples = {{ {GL_RGBA8, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8}, // RGBA8 {GL_RGB8, GL_BGR, GL_UNSIGNED_BYTE}, // RGB8 @@ -67,7 +60,7 @@ static constexpr std::array fb_format_tuples_oes = {{ }}; const FormatTuple& GetFormatTuple(PixelFormat pixel_format) { - const SurfaceType type = SurfaceParams::GetFormatType(pixel_format); + const SurfaceType type = GetFormatType(pixel_format); if (type == SurfaceType::Color) { ASSERT(static_cast(pixel_format) < fb_format_tuples.size()); if (GLES) { @@ -87,162 +80,6 @@ static constexpr auto RangeFromInterval(Map& map, const Interval& interval) { return boost::make_iterator_range(map.equal_range(interval)); } -template -static void MortonCopyTile(u32 stride, u8* tile_buffer, u8* gl_buffer) { - constexpr u32 bytes_per_pixel = SurfaceParams::GetFormatBpp(format) / 8; - constexpr u32 gl_bytes_per_pixel = CachedSurface::GetGLBytesPerPixel(format); - for (u32 y = 0; y < 8; ++y) { - for (u32 x = 0; x < 8; ++x) { - u8* tile_ptr = tile_buffer + VideoCore::MortonInterleave(x, y) * bytes_per_pixel; - u8* gl_ptr = gl_buffer + ((7 - y) * stride + x) * gl_bytes_per_pixel; - if constexpr (morton_to_gl) { - if constexpr (format == PixelFormat::D24S8) { - gl_ptr[0] = tile_ptr[3]; - std::memcpy(gl_ptr + 1, tile_ptr, 3); - } else if (format == PixelFormat::RGBA8 && GLES) { - // because GLES does not have ABGR format - // so we will do byteswapping here - gl_ptr[0] = tile_ptr[3]; - gl_ptr[1] = tile_ptr[2]; - gl_ptr[2] = tile_ptr[1]; - gl_ptr[3] = tile_ptr[0]; - } else if (format == PixelFormat::RGB8 && GLES) { - gl_ptr[0] = tile_ptr[2]; - gl_ptr[1] = tile_ptr[1]; - gl_ptr[2] = tile_ptr[0]; - } else { - std::memcpy(gl_ptr, tile_ptr, bytes_per_pixel); - } - } else { - if constexpr (format == PixelFormat::D24S8) { - std::memcpy(tile_ptr, gl_ptr + 1, 3); - tile_ptr[3] = gl_ptr[0]; - } else if (format == PixelFormat::RGBA8 && GLES) { - // because GLES does not have ABGR format - // so we will do byteswapping here - tile_ptr[0] = gl_ptr[3]; - tile_ptr[1] = gl_ptr[2]; - tile_ptr[2] = gl_ptr[1]; - tile_ptr[3] = gl_ptr[0]; - } else if (format == PixelFormat::RGB8 && GLES) { - tile_ptr[0] = gl_ptr[2]; - tile_ptr[1] = gl_ptr[1]; - tile_ptr[2] = gl_ptr[0]; - } else { - std::memcpy(tile_ptr, gl_ptr, bytes_per_pixel); - } - } - } - } -} - -template -static void MortonCopy(u32 stride, u32 height, u8* gl_buffer, PAddr base, PAddr start, PAddr end) { - constexpr u32 bytes_per_pixel = SurfaceParams::GetFormatBpp(format) / 8; - constexpr u32 tile_size = bytes_per_pixel * 64; - - constexpr u32 gl_bytes_per_pixel = CachedSurface::GetGLBytesPerPixel(format); - static_assert(gl_bytes_per_pixel >= bytes_per_pixel, ""); - gl_buffer += gl_bytes_per_pixel - bytes_per_pixel; - - const PAddr aligned_down_start = base + Common::AlignDown(start - base, tile_size); - const PAddr aligned_start = base + Common::AlignUp(start - base, tile_size); - const PAddr aligned_end = base + Common::AlignDown(end - base, tile_size); - - ASSERT(!morton_to_gl || (aligned_start == start && aligned_end == end)); - - const u32 begin_pixel_index = (aligned_down_start - base) / bytes_per_pixel; - u32 x = (begin_pixel_index % (stride * 8)) / 8; - u32 y = (begin_pixel_index / (stride * 8)) * 8; - - gl_buffer += ((height - 8 - y) * stride + x) * gl_bytes_per_pixel; - - auto glbuf_next_tile = [&] { - x = (x + 8) % stride; - gl_buffer += 8 * gl_bytes_per_pixel; - if (!x) { - y += 8; - gl_buffer -= stride * 9 * gl_bytes_per_pixel; - } - }; - - u8* tile_buffer = VideoCore::g_memory->GetPhysicalPointer(start); - - if (start < aligned_start && !morton_to_gl) { - std::array tmp_buf; - MortonCopyTile(stride, &tmp_buf[0], gl_buffer); - std::memcpy(tile_buffer, &tmp_buf[start - aligned_down_start], - std::min(aligned_start, end) - start); - - tile_buffer += aligned_start - start; - glbuf_next_tile(); - } - - const u8* const buffer_end = tile_buffer + aligned_end - aligned_start; - PAddr current_paddr = aligned_start; - while (tile_buffer < buffer_end) { - // Pokemon Super Mystery Dungeon will try to use textures that go beyond - // the end address of VRAM. Stop reading if reaches invalid address - if (!VideoCore::g_memory->IsValidPhysicalAddress(current_paddr) || - !VideoCore::g_memory->IsValidPhysicalAddress(current_paddr + tile_size)) { - LOG_ERROR(Render_OpenGL, "Out of bound texture"); - break; - } - MortonCopyTile(stride, tile_buffer, gl_buffer); - tile_buffer += tile_size; - current_paddr += tile_size; - glbuf_next_tile(); - } - - if (end > std::max(aligned_start, aligned_end) && !morton_to_gl) { - std::array tmp_buf; - MortonCopyTile(stride, &tmp_buf[0], gl_buffer); - std::memcpy(tile_buffer, &tmp_buf[0], end - aligned_end); - } -} - -static constexpr std::array morton_to_gl_fns = { - MortonCopy, // 0 - MortonCopy, // 1 - MortonCopy, // 2 - MortonCopy, // 3 - MortonCopy, // 4 - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, // 5 - 13 - MortonCopy, // 14 - nullptr, // 15 - MortonCopy, // 16 - MortonCopy // 17 -}; - -static constexpr std::array gl_to_morton_fns = { - MortonCopy, // 0 - MortonCopy, // 1 - MortonCopy, // 2 - MortonCopy, // 3 - MortonCopy, // 4 - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, // 5 - 13 - MortonCopy, // 14 - nullptr, // 15 - MortonCopy, // 16 - MortonCopy // 17 -}; - // Allocate an uninitialized texture of appropriate size and format for the surface OGLTexture RasterizerCacheOpenGL::AllocateSurfaceTexture(const FormatTuple& format_tuple, u32 width, u32 height) { @@ -264,7 +101,7 @@ OGLTexture RasterizerCacheOpenGL::AllocateSurfaceTexture(const FormatTuple& form if (GL_ARB_texture_storage) { // Allocate all possible mipmap levels upfront - auto levels = std::log2(std::max(width, height)) + 1; + const GLsizei levels = std::log2(std::max(width, height)) + 1; glTexStorage2D(GL_TEXTURE_2D, levels, format_tuple.internal_format, width, height); } else { glTexImage2D(GL_TEXTURE_2D, 0, format_tuple.internal_format, width, height, 0, @@ -293,7 +130,7 @@ static void AllocateTextureCube(GLuint texture, const FormatTuple& format_tuple, glActiveTexture(TextureUnits::TextureCube.Enum()); if (GL_ARB_texture_storage) { // Allocate all possible mipmap levels in case the game uses them later - auto levels = std::log2(width) + 1; + const GLsizei levels = std::log2(width) + 1; glTexStorage2D(GL_TEXTURE_CUBE_MAP, levels, format_tuple.internal_format, width, width); } else { for (auto faces : { @@ -418,10 +255,10 @@ static bool FillSurface(const Surface& surface, const u8* fill_data, u32 value_32bit = 0; GLfloat value_float; - if (surface->pixel_format == SurfaceParams::PixelFormat::D16) { + if (surface->pixel_format == PixelFormat::D16) { std::memcpy(&value_32bit, fill_data, 2); value_float = value_32bit / 65535.0f; // 2^16 - 1 - } else if (surface->pixel_format == SurfaceParams::PixelFormat::D24) { + } else if (surface->pixel_format == PixelFormat::D24) { std::memcpy(&value_32bit, fill_data, 3); value_float = value_32bit / 16777215.0f; // 2^24 - 1 } @@ -545,7 +382,7 @@ void CachedSurface::LoadGLBuffer(PAddr load_start, PAddr load_end) { return; if (gl_buffer.empty()) { - gl_buffer.resize(width * height * GetGLBytesPerPixel(pixel_format)); + gl_buffer.resize(width * height * GetBytesPerPixel(pixel_format)); } // TODO: Should probably be done in ::Memory:: and check for other regions too @@ -617,7 +454,7 @@ void CachedSurface::FlushGLBuffer(PAddr flush_start, PAddr flush_end) { if (dst_buffer == nullptr) return; - ASSERT(gl_buffer.size() == width * height * GetGLBytesPerPixel(pixel_format)); + ASSERT(gl_buffer.size() == width * height * GetBytesPerPixel(pixel_format)); // TODO: Should probably be done in ::Memory:: and check for other regions too // same as loadglbuffer() @@ -771,7 +608,7 @@ void CachedSurface::UploadGLTexture(Common::Rectangle rect, GLuint read_fb_ MICROPROFILE_SCOPE(OpenGL_TextureUL); - ASSERT(gl_buffer.size() == width * height * GetGLBytesPerPixel(pixel_format)); + ASSERT(gl_buffer.size() == width * height * GetBytesPerPixel(pixel_format)); u64 tex_hash = 0; @@ -786,7 +623,7 @@ void CachedSurface::UploadGLTexture(Common::Rectangle rect, GLuint read_fb_ // Load data from memory to the surface GLint x0 = static_cast(rect.left); GLint y0 = static_cast(rect.bottom); - std::size_t buffer_offset = (y0 * stride + x0) * GetGLBytesPerPixel(pixel_format); + std::size_t buffer_offset = (y0 * stride + x0) * GetBytesPerPixel(pixel_format); const FormatTuple& tuple = GetFormatTuple(pixel_format); GLuint target_tex = texture.handle; @@ -814,7 +651,7 @@ void CachedSurface::UploadGLTexture(Common::Rectangle rect, GLuint read_fb_ cur_state.Apply(); // Ensure no bad interactions with GL_UNPACK_ALIGNMENT - ASSERT(stride * GetGLBytesPerPixel(pixel_format) % 4 == 0); + ASSERT(stride * GetBytesPerPixel(pixel_format) % 4 == 0); if (is_custom) { if (res_scale == 1) { texture = owner.AllocateSurfaceTexture(GetFormatTuple(PixelFormat::RGBA8), @@ -873,7 +710,7 @@ void CachedSurface::DownloadGLTexture(const Common::Rectangle& rect, GLuint MICROPROFILE_SCOPE(OpenGL_TextureDL); if (gl_buffer.empty()) { - gl_buffer.resize(width * height * GetGLBytesPerPixel(pixel_format)); + gl_buffer.resize(width * height * GetBytesPerPixel(pixel_format)); } OpenGLState state = OpenGLState::GetCurState(); @@ -883,10 +720,10 @@ void CachedSurface::DownloadGLTexture(const Common::Rectangle& rect, GLuint const FormatTuple& tuple = GetFormatTuple(pixel_format); // Ensure no bad interactions with GL_PACK_ALIGNMENT - ASSERT(stride * GetGLBytesPerPixel(pixel_format) % 4 == 0); + ASSERT(stride * GetBytesPerPixel(pixel_format) % 4 == 0); glPixelStorei(GL_PACK_ROW_LENGTH, static_cast(stride)); std::size_t buffer_offset = - (rect.bottom * stride + rect.left) * GetGLBytesPerPixel(pixel_format); + (rect.bottom * stride + rect.left) * GetBytesPerPixel(pixel_format); // If not 1x scale, blit scaled texture to a new 1x texture and use that to flush if (res_scale != 1) { @@ -1084,7 +921,7 @@ bool RasterizerCacheOpenGL::BlitSurfaces(const Surface& src_surface, const Common::Rectangle& dst_rect) { MICROPROFILE_SCOPE(OpenGL_BlitSurface); - if (!SurfaceParams::CheckFormatsBlittable(src_surface->pixel_format, dst_surface->pixel_format)) + if (!CheckFormatsBlittable(src_surface->pixel_format, dst_surface->pixel_format)) return false; dst_surface->InvalidateAllWatcher(); @@ -1239,7 +1076,7 @@ Surface RasterizerCacheOpenGL::GetTextureSurface(const Pica::Texture::TextureInf params.width = info.width; params.height = info.height; params.is_tiled = true; - params.pixel_format = SurfaceParams::PixelFormatFromTextureFormat(info.format); + params.pixel_format = PixelFormatFromTextureFormat(info.format); params.res_scale = texture_filterer->IsNull() ? 1 : resolution_scale_factor; params.UpdateParams(); @@ -1411,7 +1248,7 @@ const CachedTextureCube& RasterizerCacheOpenGL::GetTextureCube(const TextureCube cube.texture.Create(); AllocateTextureCube( cube.texture.handle, - GetFormatTuple(CachedSurface::PixelFormatFromTextureFormat(config.format)), + GetFormatTuple(PixelFormatFromTextureFormat(config.format)), cube.res_scale * config.width); } @@ -1459,7 +1296,7 @@ SurfaceSurfaceRect_Tuple RasterizerCacheOpenGL::GetFramebufferSurfaces( const auto& config = regs.framebuffer.framebuffer; // update resolution_scale_factor and reset cache if changed - if ((resolution_scale_factor != VideoCore::GetResolutionScaleFactor()) | + if ((resolution_scale_factor != VideoCore::GetResolutionScaleFactor()) || (VideoCore::g_texture_filter_update_requested.exchange(false) && texture_filterer->Reset(Settings::values.texture_filter_name, resolution_scale_factor))) { resolution_scale_factor = VideoCore::GetResolutionScaleFactor(); @@ -1485,11 +1322,11 @@ SurfaceSurfaceRect_Tuple RasterizerCacheOpenGL::GetFramebufferSurfaces( SurfaceParams depth_params = color_params; color_params.addr = config.GetColorBufferPhysicalAddress(); - color_params.pixel_format = SurfaceParams::PixelFormatFromColorFormat(config.color_format); + color_params.pixel_format = PixelFormatFromColorFormat(config.color_format); color_params.UpdateParams(); depth_params.addr = config.GetDepthBufferPhysicalAddress(); - depth_params.pixel_format = SurfaceParams::PixelFormatFromDepthFormat(config.depth_format); + depth_params.pixel_format = PixelFormatFromDepthFormat(config.depth_format); depth_params.UpdateParams(); auto color_vp_interval = color_params.GetSubRectInterval(viewport_clamped); @@ -1693,7 +1530,7 @@ bool RasterizerCacheOpenGL::NoUnimplementedReinterpretations(const Surface& surf }; bool implemented = true; for (PixelFormat format : all_formats) { - if (SurfaceParams::GetFormatBpp(format) == surface->GetFormatBpp()) { + if (GetFormatBpp(format) == surface->GetFormatBpp()) { params.pixel_format = format; // This could potentially be expensive, // although experimentally it hasn't been too bad @@ -1701,8 +1538,8 @@ bool RasterizerCacheOpenGL::NoUnimplementedReinterpretations(const Surface& surf FindMatch(surface_cache, params, ScaleMatch::Ignore, interval); if (test_surface != nullptr) { LOG_WARNING(Render_OpenGL, "Missing pixel_format reinterpreter: {} -> {}", - SurfaceParams::PixelFormatAsString(format), - SurfaceParams::PixelFormatAsString(surface->pixel_format)); + PixelFormatAsString(format), + PixelFormatAsString(surface->pixel_format)); implemented = false; } } @@ -1751,9 +1588,8 @@ bool RasterizerCacheOpenGL::ValidateByReinterpretation(const Surface& surface, reinterpreter->second->Reinterpret(reinterpret_surface->texture.handle, src_rect, read_framebuffer.handle, tmp_tex.handle, tmp_rect, draw_framebuffer.handle); - SurfaceParams::SurfaceType type = - SurfaceParams::GetFormatType(reinterpreter->first.dst_format); + const SurfaceType type = GetFormatType(reinterpreter->first.dst_format); if (!texture_filterer->Filter(tmp_tex.handle, tmp_rect, surface->texture.handle, dest_rect, type, read_framebuffer.handle, draw_framebuffer.handle)) { diff --git a/src/video_core/rasterizer_cache/rasterizer_cache.h b/src/video_core/rasterizer_cache/rasterizer_cache.h index 47fde3904..58167210b 100644 --- a/src/video_core/rasterizer_cache/rasterizer_cache.h +++ b/src/video_core/rasterizer_cache/rasterizer_cache.h @@ -45,7 +45,7 @@ struct FormatTuple { constexpr FormatTuple tex_tuple = {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE}; -const FormatTuple& GetFormatTuple(SurfaceParams::PixelFormat pixel_format); +const FormatTuple& GetFormatTuple(PixelFormat pixel_format); struct HostTextureTag { FormatTuple format_tuple; @@ -205,15 +205,6 @@ struct CachedSurface : SurfaceParams, std::enable_shared_from_this gl_buffer; // Read/Write data in 3DS memory to/from gl_buffer diff --git a/src/video_core/rasterizer_cache/surface_params.cpp b/src/video_core/rasterizer_cache/surface_params.cpp index c74d25da1..fae3b4106 100644 --- a/src/video_core/rasterizer_cache/surface_params.cpp +++ b/src/video_core/rasterizer_cache/surface_params.cpp @@ -12,10 +12,11 @@ SurfaceParams SurfaceParams::FromInterval(SurfaceInterval interval) const { SurfaceParams params = *this; const u32 tiled_size = is_tiled ? 8 : 1; const u32 stride_tiled_bytes = BytesInPixels(stride * tiled_size); + PAddr aligned_start = - addr + Common::AlignDown(boost::icl::first(interval) - addr, stride_tiled_bytes); + addr + Common::AlignDown(boost::icl::first(interval) - addr, stride_tiled_bytes); PAddr aligned_end = - addr + Common::AlignUp(boost::icl::last_next(interval) - addr, stride_tiled_bytes); + addr + Common::AlignUp(boost::icl::last_next(interval) - addr, stride_tiled_bytes); if (aligned_end - aligned_start > stride_tiled_bytes) { params.addr = aligned_start; @@ -24,17 +25,19 @@ SurfaceParams SurfaceParams::FromInterval(SurfaceInterval interval) const { // 1 row ASSERT(aligned_end - aligned_start == stride_tiled_bytes); const u32 tiled_alignment = BytesInPixels(is_tiled ? 8 * 8 : 1); + aligned_start = - addr + Common::AlignDown(boost::icl::first(interval) - addr, tiled_alignment); + addr + Common::AlignDown(boost::icl::first(interval) - addr, tiled_alignment); aligned_end = - addr + Common::AlignUp(boost::icl::last_next(interval) - addr, tiled_alignment); + addr + Common::AlignUp(boost::icl::last_next(interval) - addr, tiled_alignment); + params.addr = aligned_start; params.width = PixelsInBytes(aligned_end - aligned_start) / tiled_size; params.stride = params.width; params.height = tiled_size; } - params.UpdateParams(); + params.UpdateParams(); return params; } @@ -158,6 +161,7 @@ bool SurfaceParams::CanTexCopy(const SurfaceParams& texcopy_params) const { end < texcopy_params.end) { return false; } + if (texcopy_params.width != texcopy_params.stride) { const u32 tile_stride = BytesInPixels(stride * (is_tiled ? 8 : 1)); return (texcopy_params.addr - addr) % BytesInPixels(is_tiled ? 64 : 1) == 0 && @@ -165,6 +169,7 @@ bool SurfaceParams::CanTexCopy(const SurfaceParams& texcopy_params) const { (texcopy_params.height == 1 || texcopy_params.stride == tile_stride) && ((texcopy_params.addr - addr) % tile_stride) + texcopy_params.width <= tile_stride; } + return FromInterval(texcopy_params.GetInterval()).GetInterval() == texcopy_params.GetInterval(); } diff --git a/src/video_core/rasterizer_cache/surface_params.h b/src/video_core/rasterizer_cache/surface_params.h index e5e5e56f3..354f12d14 100644 --- a/src/video_core/rasterizer_cache/surface_params.h +++ b/src/video_core/rasterizer_cache/surface_params.h @@ -7,11 +7,8 @@ #include #include #include -#include "common/assert.h" #include "common/math_util.h" -#include "core/hw/gpu.h" -#include "video_core/regs_framebuffer.h" -#include "video_core/regs_texturing.h" +#include "video_core/rasterizer_cache/pixel_format.h" namespace OpenGL { @@ -21,180 +18,8 @@ using Surface = std::shared_ptr; using SurfaceInterval = boost::icl::right_open_interval; struct SurfaceParams { -private: - static constexpr std::array BPP_TABLE = { - 32, // RGBA8 - 24, // RGB8 - 16, // RGB5A1 - 16, // RGB565 - 16, // RGBA4 - 16, // IA8 - 16, // RG8 - 8, // I8 - 8, // A8 - 8, // IA4 - 4, // I4 - 4, // A4 - 4, // ETC1 - 8, // ETC1A4 - 16, // D16 - 0, - 24, // D24 - 32, // D24S8 - }; - -public: - enum class PixelFormat { - // First 5 formats are shared between textures and color buffers - RGBA8 = 0, - RGB8 = 1, - RGB5A1 = 2, - RGB565 = 3, - RGBA4 = 4, - - // Texture-only formats - IA8 = 5, - RG8 = 6, - I8 = 7, - A8 = 8, - IA4 = 9, - I4 = 10, - A4 = 11, - ETC1 = 12, - ETC1A4 = 13, - - // Depth buffer-only formats - D16 = 14, - // gap - D24 = 16, - D24S8 = 17, - - Invalid = 255, - }; - - enum class SurfaceType { - Color = 0, - Texture = 1, - Depth = 2, - DepthStencil = 3, - Fill = 4, - Invalid = 5 - }; - - static constexpr unsigned int GetFormatBpp(PixelFormat format) { - const auto format_idx = static_cast(format); - DEBUG_ASSERT_MSG(format_idx < BPP_TABLE.size(), "Invalid pixel format {}", format_idx); - return BPP_TABLE[format_idx]; - } - unsigned int GetFormatBpp() const { - return GetFormatBpp(pixel_format); - } - - static std::string_view PixelFormatAsString(PixelFormat format) { - switch (format) { - case PixelFormat::RGBA8: - return "RGBA8"; - case PixelFormat::RGB8: - return "RGB8"; - case PixelFormat::RGB5A1: - return "RGB5A1"; - case PixelFormat::RGB565: - return "RGB565"; - case PixelFormat::RGBA4: - return "RGBA4"; - case PixelFormat::IA8: - return "IA8"; - case PixelFormat::RG8: - return "RG8"; - case PixelFormat::I8: - return "I8"; - case PixelFormat::A8: - return "A8"; - case PixelFormat::IA4: - return "IA4"; - case PixelFormat::I4: - return "I4"; - case PixelFormat::A4: - return "A4"; - case PixelFormat::ETC1: - return "ETC1"; - case PixelFormat::ETC1A4: - return "ETC1A4"; - case PixelFormat::D16: - return "D16"; - case PixelFormat::D24: - return "D24"; - case PixelFormat::D24S8: - return "D24S8"; - default: - return "Not a real pixel format"; - } - } - - static PixelFormat PixelFormatFromTextureFormat(Pica::TexturingRegs::TextureFormat format) { - return ((unsigned int)format < 14) ? (PixelFormat)format : PixelFormat::Invalid; - } - - static PixelFormat PixelFormatFromColorFormat(Pica::FramebufferRegs::ColorFormat format) { - return ((unsigned int)format < 5) ? (PixelFormat)format : PixelFormat::Invalid; - } - - static PixelFormat PixelFormatFromDepthFormat(Pica::FramebufferRegs::DepthFormat format) { - return ((unsigned int)format < 4) ? (PixelFormat)((unsigned int)format + 14) - : PixelFormat::Invalid; - } - - static PixelFormat PixelFormatFromGPUPixelFormat(GPU::Regs::PixelFormat format) { - switch (format) { - // RGB565 and RGB5A1 are switched in PixelFormat compared to ColorFormat - case GPU::Regs::PixelFormat::RGB565: - return PixelFormat::RGB565; - case GPU::Regs::PixelFormat::RGB5A1: - return PixelFormat::RGB5A1; - default: - return ((unsigned int)format < 5) ? (PixelFormat)format : PixelFormat::Invalid; - } - } - - static bool CheckFormatsBlittable(PixelFormat pixel_format_a, PixelFormat pixel_format_b) { - SurfaceType a_type = GetFormatType(pixel_format_a); - SurfaceType b_type = GetFormatType(pixel_format_b); - - if ((a_type == SurfaceType::Color || a_type == SurfaceType::Texture) && - (b_type == SurfaceType::Color || b_type == SurfaceType::Texture)) { - return true; - } - - if (a_type == SurfaceType::Depth && b_type == SurfaceType::Depth) { - return true; - } - - if (a_type == SurfaceType::DepthStencil && b_type == SurfaceType::DepthStencil) { - return true; - } - - return false; - } - - static constexpr SurfaceType GetFormatType(PixelFormat pixel_format) { - if ((unsigned int)pixel_format < 5) { - return SurfaceType::Color; - } - - if ((unsigned int)pixel_format < 14) { - return SurfaceType::Texture; - } - - if (pixel_format == PixelFormat::D16 || pixel_format == PixelFormat::D24) { - return SurfaceType::Depth; - } - - if (pixel_format == PixelFormat::D24S8) { - return SurfaceType::DepthStencil; - } - - return SurfaceType::Invalid; + return OpenGL::GetFormatBpp(pixel_format); } /// Update the params "size", "end" and "type" from the already set "addr", "width", "height" @@ -238,11 +63,11 @@ public: } u32 PixelsInBytes(u32 size) const { - return size * CHAR_BIT / GetFormatBpp(pixel_format); + return size * 8 / GetFormatBpp(); } u32 BytesInPixels(u32 pixels) const { - return pixels * GetFormatBpp(pixel_format) / CHAR_BIT; + return pixels * GetFormatBpp() / 8; } bool ExactMatch(const SurfaceParams& other_surface) const; diff --git a/src/video_core/renderer_opengl/gl_format_reinterpreter.cpp b/src/video_core/renderer_opengl/gl_format_reinterpreter.cpp index ff4f64110..04fae3f88 100644 --- a/src/video_core/renderer_opengl/gl_format_reinterpreter.cpp +++ b/src/video_core/renderer_opengl/gl_format_reinterpreter.cpp @@ -12,8 +12,6 @@ namespace OpenGL { -using PixelFormat = SurfaceParams::PixelFormat; - class RGBA4toRGB5A1 final : public FormatReinterpreterBase { public: RGBA4toRGB5A1() { diff --git a/src/video_core/renderer_opengl/gl_format_reinterpreter.h b/src/video_core/renderer_opengl/gl_format_reinterpreter.h index b422a6a0c..2efacde62 100644 --- a/src/video_core/renderer_opengl/gl_format_reinterpreter.h +++ b/src/video_core/renderer_opengl/gl_format_reinterpreter.h @@ -9,27 +9,27 @@ #include #include "common/common_types.h" #include "common/math_util.h" -#include "video_core/renderer_opengl/gl_resource_manager.h" -#include "video_core/rasterizer_cache/surface_params.h" +#include "video_core/rasterizer_cache/pixel_format.h" namespace OpenGL { class RasterizerCacheOpenGL; struct PixelFormatPair { - const SurfaceParams::PixelFormat dst_format, src_format; + const PixelFormat dst_format, src_format; + struct less { using is_transparent = void; - constexpr bool operator()(OpenGL::PixelFormatPair lhs, OpenGL::PixelFormatPair rhs) const { + constexpr bool operator()(PixelFormatPair lhs, PixelFormatPair rhs) const { return std::tie(lhs.dst_format, lhs.src_format) < std::tie(rhs.dst_format, rhs.src_format); } - constexpr bool operator()(OpenGL::SurfaceParams::PixelFormat lhs, - OpenGL::PixelFormatPair rhs) const { + + constexpr bool operator()(PixelFormat lhs, PixelFormatPair rhs) const { return lhs < rhs.dst_format; } - constexpr bool operator()(OpenGL::PixelFormatPair lhs, - OpenGL::SurfaceParams::PixelFormat rhs) const { + + constexpr bool operator()(PixelFormatPair lhs, PixelFormat rhs) const { return lhs.dst_format < rhs; } }; @@ -52,8 +52,8 @@ public: explicit FormatReinterpreterOpenGL(); ~FormatReinterpreterOpenGL(); - std::pair GetPossibleReinterpretations( - SurfaceParams::PixelFormat dst_format); + auto GetPossibleReinterpretations(PixelFormat dst_format) -> + std::pair; private: ReinterpreterMap reinterpreters; diff --git a/src/video_core/renderer_opengl/gl_rasterizer.cpp b/src/video_core/renderer_opengl/gl_rasterizer.cpp index 1d5dcbb14..a4eb373cc 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer.cpp +++ b/src/video_core/renderer_opengl/gl_rasterizer.cpp @@ -29,9 +29,6 @@ namespace OpenGL { -using PixelFormat = SurfaceParams::PixelFormat; -using SurfaceType = SurfaceParams::SurfaceType; - MICROPROFILE_DEFINE(OpenGL_VAO, "OpenGL", "Vertex Array Setup", MP_RGB(255, 128, 0)); MICROPROFILE_DEFINE(OpenGL_VS, "OpenGL", "Vertex Shader Setup", MP_RGB(192, 128, 128)); MICROPROFILE_DEFINE(OpenGL_GS, "OpenGL", "Geometry Shader Setup", MP_RGB(128, 192, 128)); @@ -1445,7 +1442,7 @@ bool RasterizerOpenGL::AccelerateDisplayTransfer(const GPU::Regs::DisplayTransfe src_params.stride = config.input_width; src_params.height = config.output_height; src_params.is_tiled = !config.input_linear; - src_params.pixel_format = SurfaceParams::PixelFormatFromGPUPixelFormat(config.input_format); + src_params.pixel_format = PixelFormatFromGPUPixelFormat(config.input_format); src_params.UpdateParams(); SurfaceParams dst_params; @@ -1455,7 +1452,7 @@ bool RasterizerOpenGL::AccelerateDisplayTransfer(const GPU::Regs::DisplayTransfe dst_params.height = config.scaling == config.ScaleXY ? config.output_height.Value() / 2 : config.output_height.Value(); dst_params.is_tiled = config.input_linear != config.dont_swizzle; - dst_params.pixel_format = SurfaceParams::PixelFormatFromGPUPixelFormat(config.output_format); + dst_params.pixel_format = PixelFormatFromGPUPixelFormat(config.output_format); dst_params.UpdateParams(); Common::Rectangle src_rect; @@ -1595,7 +1592,7 @@ bool RasterizerOpenGL::AccelerateDisplay(const GPU::Regs::FramebufferConfig& con src_params.height = config.height; src_params.stride = pixel_stride; src_params.is_tiled = false; - src_params.pixel_format = SurfaceParams::PixelFormatFromGPUPixelFormat(config.color_format); + src_params.pixel_format = PixelFormatFromGPUPixelFormat(config.color_format); src_params.UpdateParams(); Common::Rectangle src_rect; diff --git a/src/video_core/renderer_opengl/texture_filters/texture_filter_base.h b/src/video_core/renderer_opengl/texture_filters/texture_filter_base.h index 45a3e8a32..328d59d90 100644 --- a/src/video_core/renderer_opengl/texture_filters/texture_filter_base.h +++ b/src/video_core/renderer_opengl/texture_filters/texture_filter_base.h @@ -4,9 +4,9 @@ #pragma once +#include #include "common/common_types.h" #include "common/math_util.h" -#include "video_core/rasterizer_cache/surface_params.h" namespace OpenGL { diff --git a/src/video_core/renderer_opengl/texture_filters/texture_filterer.cpp b/src/video_core/renderer_opengl/texture_filters/texture_filterer.cpp index 204cb8b98..95db3866b 100644 --- a/src/video_core/renderer_opengl/texture_filters/texture_filterer.cpp +++ b/src/video_core/renderer_opengl/texture_filters/texture_filterer.cpp @@ -60,12 +60,13 @@ bool TextureFilterer::IsNull() const { bool TextureFilterer::Filter(GLuint src_tex, const Common::Rectangle& src_rect, GLuint dst_tex, const Common::Rectangle& dst_rect, - SurfaceParams::SurfaceType type, GLuint read_fb_handle, + SurfaceType type, GLuint read_fb_handle, GLuint draw_fb_handle) { // depth / stencil texture filtering is not supported for now - if (IsNull() || - (type != SurfaceParams::SurfaceType::Color && type != SurfaceParams::SurfaceType::Texture)) + if (IsNull() || (type != SurfaceType::Color && type != SurfaceType::Texture)) { return false; + } + filter->Filter(src_tex, src_rect, dst_tex, dst_rect, read_fb_handle, draw_fb_handle); return true; } @@ -85,4 +86,4 @@ std::vector TextureFilterer::GetFilterNames() { return ret; } -} // namespace OpenGL \ No newline at end of file +} // namespace OpenGL diff --git a/src/video_core/renderer_opengl/texture_filters/texture_filterer.h b/src/video_core/renderer_opengl/texture_filters/texture_filterer.h index fc0d784ac..4402d12fb 100644 --- a/src/video_core/renderer_opengl/texture_filters/texture_filterer.h +++ b/src/video_core/renderer_opengl/texture_filters/texture_filterer.h @@ -7,9 +7,7 @@ #include #include #include -#include -#include "common/common_types.h" -#include "common/math_util.h" +#include "video_core/rasterizer_cache/pixel_format.h" #include "video_core/renderer_opengl/texture_filters/texture_filter_base.h" namespace OpenGL { @@ -25,7 +23,7 @@ public: bool IsNull() const; // returns true if the texture was able to be filtered bool Filter(GLuint src_tex, const Common::Rectangle& src_rect, GLuint dst_tex, - const Common::Rectangle& dst_rect, SurfaceParams::SurfaceType type, + const Common::Rectangle& dst_rect, SurfaceType type, GLuint read_fb_handle, GLuint draw_fb_handle); static std::vector GetFilterNames();