Skip to content

Commit

Permalink
Add OpenGL ES compatibility
Browse files Browse the repository at this point in the history
  • Loading branch information
Joe authored and garbear committed Mar 20, 2023
1 parent 7acfe38 commit b380fc3
Show file tree
Hide file tree
Showing 5 changed files with 131 additions and 60 deletions.
158 changes: 102 additions & 56 deletions xbmc/cores/RetroPlayer/rendering/VideoRenderers/RPRendererOpenGLES.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include "cores/RetroPlayer/buffers/RenderBufferPoolOpenGLES.h"
#include "cores/RetroPlayer/rendering/RenderContext.h"
#include "cores/RetroPlayer/rendering/RenderVideoSettings.h"
#include "cores/RetroPlayer/shaders/gl/ShaderPresetGL.h"
#include "utils/GLUtils.h"
#include "utils/log.h"

Expand Down Expand Up @@ -48,6 +49,9 @@ CRPRendererOpenGLES::CRPRendererOpenGLES(const CRenderSettings& renderSettings,
std::shared_ptr<IRenderBufferPool> bufferPool)
: CRPBaseRenderer(renderSettings, context, std::move(bufferPool))
{
// Initialize CRPBaseRenderer
m_shaderPreset.reset(new SHADER::CShaderPresetGL(m_context));

glGenBuffers(1, &m_mainIndexVBO);
glGenBuffers(1, &m_mainVertexVBO);
glGenBuffers(1, &m_blackbarsVertexVBO);
Expand Down Expand Up @@ -245,7 +249,29 @@ void CRPRendererOpenGLES::Render(uint8_t alpha)

const uint32_t color = (alpha << 24) | 0xFFFFFF;

glBindTexture(m_textureTarget, renderBuffer->TextureID());
RenderBufferTextures* rbTextures;
const auto it = m_RBTexturesMap.find(renderBuffer);
if (it != m_RBTexturesMap.end())
{
rbTextures = it->second.get();
}
else
{
// We can't copy or move CGLTexture, so construct source/target in-place
rbTextures = new RenderBufferTextures{{// source texture
static_cast<unsigned int>(renderBuffer->GetWidth()),
static_cast<unsigned int>(renderBuffer->GetHeight()),
GL_RGB, renderBuffer->TextureID()},
{// target texture
static_cast<unsigned int>(m_context.GetScreenWidth()),
static_cast<unsigned int>(m_context.GetScreenHeight())}};
m_RBTexturesMap.emplace(renderBuffer, rbTextures);
}

const auto sourceTexture = &rbTextures->source;
const auto targetTexture = &rbTextures->target;

glBindTexture(m_textureTarget, sourceTexture->getMTexture());

GLint filter = GL_NEAREST;
if (GetRenderSettings().VideoSettings().GetScalingMethod() == SCALINGMETHOD::LINEAR)
Expand All @@ -255,63 +281,83 @@ void CRPRendererOpenGLES::Render(uint8_t alpha)
glTexParameteri(m_textureTarget, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(m_textureTarget, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);

m_context.EnableGUIShader(GL_SHADER_METHOD::TEXTURE_NOALPHA);
Updateshaders();

GLubyte colour[4];
GLubyte idx[4] = {0, 1, 3, 2}; // Determines order of triangle strip
struct PackedVertex
if (m_bUseShaderPreset)
{
float x, y, z;
float u1, v1;
} vertex[4];

GLint vertLoc = m_context.GUIShaderGetPos();
GLint loc = m_context.GUIShaderGetCoord0();
GLint uniColLoc = m_context.GUIShaderGetUniCol();

// Setup color values
colour[0] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::R, color);
colour[1] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::G, color);
colour[2] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::B, color);
colour[3] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::A, color);

for (unsigned int i = 0; i < 4; i++)
const CPoint destPoints[4] = {m_rotatedDestCoords[0], m_rotatedDestCoords[1],
m_rotatedDestCoords[2], m_rotatedDestCoords[3]};

targetTexture->CreateTextureObject();

SHADER::CShaderTextureGL source(*sourceTexture);
SHADER::CShaderTextureGL target(*targetTexture);
if (!m_shaderPreset->RenderUpdate(destPoints, &source, &target))
{
m_shadersNeedUpdate = false;
m_bUseShaderPreset = false;
}
}
else
{
// Setup vertex position values
vertex[i].x = m_rotatedDestCoords[i].x;
vertex[i].y = m_rotatedDestCoords[i].y;
vertex[i].z = 0.0f;
m_context.EnableGUIShader(GL_SHADER_METHOD::TEXTURE_NOALPHA);

GLubyte colour[4];
GLubyte idx[4] = {0, 1, 3, 2}; // Determines order of triangle strip
struct PackedVertex
{
float x, y, z;
float u1, v1;
} vertex[4];

GLint vertLoc = m_context.GUIShaderGetPos();
GLint loc = m_context.GUIShaderGetCoord0();
GLint uniColLoc = m_context.GUIShaderGetUniCol();

// Setup color values
colour[0] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::R, color);
colour[1] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::G, color);
colour[2] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::B, color);
colour[3] = UTILS::GL::GetChannelFromARGB(UTILS::GL::ColorChannel::A, color);

for (unsigned int i = 0; i < 4; i++)
{
// Setup vertex position values
vertex[i].x = m_rotatedDestCoords[i].x;
vertex[i].y = m_rotatedDestCoords[i].y;
vertex[i].z = 0.0f;
}

// Setup texture coordinates
vertex[0].u1 = vertex[3].u1 = rect.x1;
vertex[0].v1 = vertex[1].v1 = rect.y1;
vertex[1].u1 = vertex[2].u1 = rect.x2;
vertex[2].v1 = vertex[3].v1 = rect.y2;

glBindBuffer(GL_ARRAY_BUFFER, m_mainVertexVBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(PackedVertex) * 4, &vertex[0], GL_STATIC_DRAW);

glVertexAttribPointer(vertLoc, 3, GL_FLOAT, 0, sizeof(PackedVertex),
reinterpret_cast<const GLvoid*>(offsetof(PackedVertex, x)));
glVertexAttribPointer(loc, 2, GL_FLOAT, 0, sizeof(PackedVertex),
reinterpret_cast<const GLvoid*>(offsetof(PackedVertex, u1)));

glEnableVertexAttribArray(vertLoc);
glEnableVertexAttribArray(loc);

glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_mainIndexVBO);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(GLubyte) * 4, idx, GL_STATIC_DRAW);

glUniform4f(uniColLoc, (colour[0] / 255.0f), (colour[1] / 255.0f), (colour[2] / 255.0f),
(colour[3] / 255.0f));
glDrawElements(GL_TRIANGLE_STRIP, 4, GL_UNSIGNED_BYTE, 0);

glDisableVertexAttribArray(vertLoc);
glDisableVertexAttribArray(loc);

glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);

m_context.DisableGUIShader();
}

// Setup texture coordinates
vertex[0].u1 = vertex[3].u1 = rect.x1;
vertex[0].v1 = vertex[1].v1 = rect.y1;
vertex[1].u1 = vertex[2].u1 = rect.x2;
vertex[2].v1 = vertex[3].v1 = rect.y2;

glBindBuffer(GL_ARRAY_BUFFER, m_mainVertexVBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(PackedVertex) * 4, &vertex[0], GL_STATIC_DRAW);

glVertexAttribPointer(vertLoc, 3, GL_FLOAT, 0, sizeof(PackedVertex),
reinterpret_cast<const GLvoid*>(offsetof(PackedVertex, x)));
glVertexAttribPointer(loc, 2, GL_FLOAT, 0, sizeof(PackedVertex),
reinterpret_cast<const GLvoid*>(offsetof(PackedVertex, u1)));

glEnableVertexAttribArray(vertLoc);
glEnableVertexAttribArray(loc);

glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_mainIndexVBO);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(GLubyte) * 4, idx, GL_STATIC_DRAW);

glUniform4f(uniColLoc, (colour[0] / 255.0f), (colour[1] / 255.0f), (colour[2] / 255.0f),
(colour[3] / 255.0f));
glDrawElements(GL_TRIANGLE_STRIP, 4, GL_UNSIGNED_BYTE, 0);

glDisableVertexAttribArray(vertLoc);
glDisableVertexAttribArray(loc);

glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);

m_context.DisableGUIShader();
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,11 @@
#include "cores/RetroPlayer/buffers/BaseRenderBufferPool.h"
#include "cores/RetroPlayer/buffers/video/RenderBufferSysMem.h"
#include "cores/RetroPlayer/process/RPProcessInfo.h"
#include "guilib/TextureGL.h"

#include <atomic>
#include <map>
#include <memory>
#include <stdint.h>
#include <vector>

Expand All @@ -24,6 +27,8 @@ namespace KODI
{
namespace RETRO
{
class CRenderBufferOpenGLES;

class CRendererFactoryOpenGLES : public IRendererFactory
{
public:
Expand Down Expand Up @@ -76,6 +81,14 @@ class CRPRendererOpenGLES : public CRPBaseRenderer
GLuint m_blackbarsVertexVBO;
GLenum m_textureTarget = GL_TEXTURE_2D;
float m_clearColour = 0.0f;

struct RenderBufferTextures
{
CGLTexture source;
CGLTexture target;
};

std::map<CRenderBufferOpenGLES*, std::unique_ptr<RenderBufferTextures>> m_RBTexturesMap;
};
} // namespace RETRO
} // namespace KODI
2 changes: 2 additions & 0 deletions xbmc/cores/RetroPlayer/shaders/gl/ShaderLutGL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,8 +67,10 @@ std::unique_ptr<IShaderTexture> CShaderLutGL::CreateLUTTexture(RETRO::CRenderCon
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_LOD, 0.0);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_LOD, MAX_FLOAT);

#ifndef HAS_GLES
GLfloat blackBorder[4] = {0.0f, 0.0f, 0.0f, 0.0f};
glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, blackBorder);
#endif

if (lut.mipmap)
textureGL->SetMipmapping();
Expand Down
14 changes: 10 additions & 4 deletions xbmc/cores/RetroPlayer/shaders/gl/ShaderPresetGL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include "ShaderPresetGL.h"

#include "ServiceBroker.h"
#include "ShaderUtilsGL.h"
#include "cores/RetroPlayer/rendering/RenderContext.h"
#include "cores/RetroPlayer/shaders/ShaderPresetFactory.h"
#include "cores/RetroPlayer/shaders/ShaderUtils.h"
Expand Down Expand Up @@ -175,7 +176,7 @@ bool CShaderPresetGL::Update()

if (!ReadPresetFile(m_presetPath))
{
CLog::Log(LOGERROR, "%s - couldn't load shader preset %s or the shaders it references",
CLog::Log(LOGERROR, "{} - couldn't load shader preset {} or the shaders it references",
__func__, m_presetPath.c_str());
return false;
}
Expand Down Expand Up @@ -304,17 +305,22 @@ bool CShaderPresetGL::CreateShaderTextures()
return false;
}

auto wrapType = CShaderUtilsGL::TranslateWrapType(WRAP_TYPE_BORDER);

glBindTexture(GL_TEXTURE_2D, texture->getMTexture());
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapType);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapType);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, wrapType);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_FUNC, GL_NEVER);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_LOD, 0.0);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_LOD, MAX_FLOAT);

#ifndef HAS_GLES
GLfloat blackBorder[4] = {0.0f, 0.0f, 0.0f, 0.0f};
glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, blackBorder);
#endif

m_pShaderTextures.emplace_back(new CShaderTextureGL(*texture));
m_pShaders[shaderIdx]->SetSizes(prevSize, scaledSize);
Expand Down
4 changes: 4 additions & 0 deletions xbmc/cores/RetroPlayer/shaders/gl/ShaderUtilsGL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,11 @@ GLint CShaderUtilsGL::TranslateWrapType(WRAP_TYPE wrap)
break;
case WRAP_TYPE_BORDER:
default:
#ifdef HAS_GLES
glWrap = GL_CLAMP_TO_EDGE;
#else
glWrap = GL_CLAMP_TO_BORDER;
#endif
break;
}

Expand Down

0 comments on commit b380fc3

Please sign in to comment.