MythTV  master
mythopengltonemap.cpp
Go to the documentation of this file.
1 // MythTV
2 #include "mythlogging.h"
4 #include "mythopengltonemap.h"
5 
6 #define LOC QString("Tonemap: ")
7 
8 #ifndef GL_SHADER_STORAGE_BUFFER
9 #define GL_SHADER_STORAGE_BUFFER 0x90D2
10 #endif
11 #ifndef GL_ALL_BARRIER_BITS
12 #define GL_ALL_BARRIER_BITS 0xFFFFFFFF
13 #endif
14 #ifndef GL_SHADER_IMAGE_ACCESS_BARRIER_BIT
15 #define GL_SHADER_IMAGE_ACCESS_BARRIER_BIT 0x00000020
16 #endif
17 #ifndef GL_STREAM_COPY
18 #define GL_STREAM_COPY 0x88E2
19 #endif
20 #ifndef GL_WRITE_ONLY
21 #define GL_WRITE_ONLY 0x88B9
22 #endif
23 
25 {
26  if (Render)
27  {
28  Render->IncrRef();
29  m_render = Render;
30  m_extra = Render->extraFunctions();
31  }
32 
33  if (ColourSpace)
34  {
35  ColourSpace->IncrRef();
36  m_colourSpace = ColourSpace;
38  }
39 }
40 
42 {
43  if (m_render)
44  {
46  if (m_storageBuffer)
47  m_render->glDeleteBuffers(1, &m_storageBuffer);
48  delete m_shader;
49  delete m_texture;
51  m_render->DecrRef();
52  }
53 
54  if (m_colourSpace)
56 }
57 
58 void MythOpenGLTonemap::UpdateColourSpace(bool PrimariesChanged)
59 {
60  (void)PrimariesChanged;
61  OpenGLLocker locker(m_render);
62  if (m_shader)
63  {
66  }
67 }
68 
70 {
71  return m_texture;
72 }
73 
74 MythVideoTexture* MythOpenGLTonemap::Map(vector<MythVideoTexture *> &Inputs, QSize DisplaySize)
75 {
76  size_t size = Inputs.size();
77  if (!size || !m_render || !m_extra)
78  return nullptr;
79 
80  OpenGLLocker locker(m_render);
81  bool changed = m_outputSize != DisplaySize;
82 
83  if (!m_texture || changed)
84  if (!CreateTexture(DisplaySize))
85  return nullptr;
86 
87  changed |= (m_inputCount != size) || (m_inputType != Inputs[0]->m_frameFormat) ||
88  (m_inputSize != Inputs[0]->m_size);
89 
90  if (!m_shader || changed)
91  if (!CreateShader(size, Inputs[0]->m_frameFormat, Inputs[0]->m_size))
92  return nullptr;
93 
94  if (!m_storageBuffer)
95  {
96  m_render->glGenBuffers(1, &m_storageBuffer);
97  if (!m_storageBuffer)
98  {
99  LOG(VB_GENERAL, LOG_ERR, LOC + "Failed to allocate storage buffer");
100  return nullptr;
101  }
103  struct dummy { float a[2] {0.0F}; uint32_t b {0}; uint32_t c {0}; uint32_t d {0}; } buffer;
104  m_render->glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(dummy), &buffer, GL_STREAM_COPY);
105  m_render->glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0);
106  }
107 
109  for (size_t i = 0; i < size; ++i)
110  {
111  m_render->ActiveTexture(GL_TEXTURE0 + static_cast<GLuint>(i));
112  if (Inputs[i]->m_texture)
113  Inputs[i]->m_texture->bind();
114  else
115  m_render->glBindTexture(Inputs[i]->m_target, Inputs[i]->m_textureId);
116  }
117 
118  m_extra->glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 0, m_storageBuffer);
119  m_extra->glMemoryBarrier(GL_ALL_BARRIER_BITS);
120  m_extra->glBindImageTexture(0, m_texture->m_textureId, 0, GL_FALSE, 0, GL_WRITE_ONLY, QOpenGLTexture::RGBA16F);
121  m_extra->glDispatchCompute((static_cast<GLuint>(m_texture->m_size.width()) + 1) >> 3,
122  (static_cast<GLuint>(m_texture->m_size.height()) + 1) >> 3, 1);
124  m_extra->glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 0, 0);
125  return m_texture;
126 }
127 
128 bool MythOpenGLTonemap::CreateShader(size_t InputSize, VideoFrameType Type, QSize Size)
129 {
130  delete m_shader;
131  m_shader = nullptr;
132  m_inputSize = Size;
133 
134  QString source = (m_render->isOpenGLES() ? "#version 310 es\n" : "#version 430\n");
135  if (format_is_420(Type) || format_is_422(Type) || format_is_444(Type))
136  source.append("#define YV12\n");
137  if (m_render->isOpenGLES() && ColorDepth(Type) > 8)
138  source.append("#define UNSIGNED\n");
139  source.append(GLSL430Tonemap);
140 
142  if (m_shader)
143  {
144  m_inputCount = InputSize;
145  m_inputType = Type;
147  for (size_t i = 0; i < InputSize; ++i)
148  m_shader->setUniformValue(QString("texture%1").arg(i).toLatin1().constData(), static_cast<GLuint>(i));
149  LOG(VB_GENERAL, LOG_INFO, QString("Created tonemapping compute shader (%1 inputs)")
150  .arg(InputSize));
151  UpdateColourSpace(false);
152  return true;
153  }
154 
155  return false;
156 }
157 
159 {
160  delete m_texture;
161  m_texture = nullptr;
162  m_outputSize = Size;
163  GLuint textureid = 0;
164  m_render->glGenTextures(1, &textureid);
165  if (!textureid)
166  return false;
167 
168  m_texture = new MythVideoTexture(textureid);
171  m_texture->m_target = QOpenGLTexture::Target2D;
172  m_texture->m_size = Size;
173  m_texture->m_totalSize = m_render->GetTextureSize(Size, m_texture->m_target != QOpenGLTexture::TargetRectangle);
175  m_extra->glBindTexture(m_texture->m_target, m_texture->m_textureId);
176  m_extra->glTexStorage2D(m_texture->m_target, 1, QOpenGLTexture::RGBA16F,
177  static_cast<GLsizei>(Size.width()), static_cast<GLsizei>(Size.height()));
178  m_render->SetTextureFilters(m_texture, QOpenGLTexture::Linear);
179  return m_texture != nullptr;
180 }
MythOpenGLTonemap::m_inputSize
QSize m_inputSize
Definition: mythopengltonemap.h:39
MythOpenGLTonemap::m_texture
MythVideoTexture * m_texture
Definition: mythopengltonemap.h:37
GL_WRITE_ONLY
#define GL_WRITE_ONLY
Definition: mythopengltonemap.cpp:21
format_is_444
static bool format_is_444(VideoFrameType Type)
Definition: mythframe.h:98
MythRenderOpenGL::GetTextureSize
QSize GetTextureSize(const QSize &Size, bool Normalised)
Definition: mythrenderopengl.cpp:650
ReferenceCounter::DecrRef
virtual int DecrRef(void)
Decrements reference count and deletes on 0.
Definition: referencecounter.cpp:125
MythVideoTexture::m_frameType
VideoFrameType m_frameType
Definition: mythvideotexture.h:49
MythOpenGLTonemap::m_colourSpace
VideoColourSpace * m_colourSpace
Definition: mythopengltonemap.h:34
MythRenderOpenGL::CreateComputeShader
QOpenGLShaderProgram * CreateComputeShader(const QString &Source)
Definition: mythrenderopengl.cpp:1549
format_is_420
static bool format_is_420(VideoFrameType Type)
Definition: mythframe.h:86
d
static const uint16_t * d
Definition: iso6937tables.cpp:1025
arg
arg(title).arg(filename).arg(doDelete))
LOG
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
Definition: mythlogging.h:23
GL_ALL_BARRIER_BITS
#define GL_ALL_BARRIER_BITS
Definition: mythopengltonemap.cpp:12
MythOpenGLTonemap::m_inputCount
size_t m_inputCount
Definition: mythopengltonemap.h:38
GL_SHADER_IMAGE_ACCESS_BARRIER_BIT
#define GL_SHADER_IMAGE_ACCESS_BARRIER_BIT
Definition: mythopengltonemap.cpp:15
MythRenderOpenGL::SetShaderProgramParams
void SetShaderProgramParams(QOpenGLShaderProgram *Program, const QMatrix4x4 &Value, const char *Uniform)
Definition: mythrenderopengl.cpp:1605
MythOpenGLTonemap::m_storageBuffer
GLuint m_storageBuffer
Definition: mythopengltonemap.h:36
MythOpenGLTonemap::GetTexture
MythVideoTexture * GetTexture(void)
Definition: mythopengltonemap.cpp:69
MythOpenGLTonemap::Map
MythVideoTexture * Map(vector< MythVideoTexture * > &Inputs, QSize DisplaySize)
Definition: mythopengltonemap.cpp:74
mythlogging.h
MythRenderOpenGL::kVertexSize
static const GLuint kVertexSize
Definition: mythrenderopengl.h:127
MythGLTexture::m_vbo
QOpenGLBuffer * m_vbo
Definition: mythrenderopengl.h:65
mythopenglcomputeshaders.h
mythopengltonemap.h
MythOpenGLTonemap::CreateTexture
bool CreateTexture(QSize Size)
Definition: mythopengltonemap.cpp:158
MythOpenGLTonemap::~MythOpenGLTonemap
~MythOpenGLTonemap() override
Definition: mythopengltonemap.cpp:41
MythRenderOpenGL::makeCurrent
void makeCurrent()
Definition: mythrenderopengl.cpp:558
VideoColourSpace::GetPrimaryMatrix
QMatrix4x4 GetPrimaryMatrix(void)
Definition: videocolourspace.cpp:472
MythRenderOpenGL::CreateVBO
QOpenGLBuffer * CreateVBO(int Size, bool Release=true)
Definition: mythrenderopengl.cpp:1207
MythRenderOpenGL::ActiveTexture
void ActiveTexture(GLuint ActiveTex)
Definition: mythrenderopengl.cpp:694
MythOpenGLTonemap::m_outputSize
QSize m_outputSize
Definition: mythopengltonemap.h:41
GLSL430Tonemap
static const QString GLSL430Tonemap
Definition: mythopenglcomputeshaders.h:12
MythGLTexture::m_target
GLenum m_target
Definition: mythrenderopengl.h:73
MythRenderOpenGL::doneCurrent
void doneCurrent()
Definition: mythrenderopengl.cpp:566
MythOpenGLTonemap::CreateShader
bool CreateShader(size_t InputSize, VideoFrameType Type, QSize Size)
Definition: mythopengltonemap.cpp:128
GL_TEXTURE0
#define GL_TEXTURE0
Definition: mythrenderopengldefs.h:9
MythRenderOpenGL
Definition: mythrenderopengl.h:95
VideoColourSpace
VideoColourSpace contains a QMatrix4x4 that can convert YCbCr data to RGB.
Definition: videocolourspace.h:18
MythVideoTexture::m_frameFormat
VideoFrameType m_frameFormat
Definition: mythvideotexture.h:50
ColorDepth
int ColorDepth(int Format)
Return the color depth for the given MythTV frame format.
Definition: mythframe.cpp:808
MythGLTexture::m_totalSize
QSize m_totalSize
Definition: mythrenderopengl.h:67
MythGLTexture::m_textureId
GLuint m_textureId
Definition: mythrenderopengl.h:61
GL_STREAM_COPY
#define GL_STREAM_COPY
Definition: mythopengltonemap.cpp:18
MythOpenGLTonemap::UpdateColourSpace
void UpdateColourSpace(bool PrimariesChanged)
Definition: mythopengltonemap.cpp:58
MythOpenGLTonemap::MythOpenGLTonemap
MythOpenGLTonemap(MythRenderOpenGL *Render, VideoColourSpace *ColourSpace)
Definition: mythopengltonemap.cpp:24
MythGLTexture::m_size
QSize m_size
Definition: mythrenderopengl.h:66
VideoColourSpace::Updated
void Updated(bool PrimariesChanged)
MythRenderOpenGL::SetTextureFilters
void SetTextureFilters(MythGLTexture *Texture, QOpenGLTexture::Filter Filter, QOpenGLTexture::WrapMode Wrap=QOpenGLTexture::ClampToEdge)
Definition: mythrenderopengl.cpp:671
MythOpenGLTonemap::m_inputType
VideoFrameType m_inputType
Definition: mythopengltonemap.h:40
LOC
#define LOC
Definition: mythopengltonemap.cpp:6
format_is_422
static bool format_is_422(VideoFrameType Type)
Definition: mythframe.h:92
VideoFrameType
VideoFrameType
Definition: mythframe.h:25
MythVideoTexture
Definition: mythvideotexture.h:21
ReferenceCounter::IncrRef
virtual int IncrRef(void)
Increments reference count.
Definition: referencecounter.cpp:101
GL_SHADER_STORAGE_BUFFER
#define GL_SHADER_STORAGE_BUFFER
Definition: mythopengltonemap.cpp:9
MythOpenGLTonemap::m_shader
QOpenGLShaderProgram * m_shader
Definition: mythopengltonemap.h:35
MythOpenGLTonemap::m_render
MythRenderOpenGL * m_render
Definition: mythopengltonemap.h:32
MythOpenGLTonemap::m_extra
QOpenGLExtraFunctions * m_extra
Definition: mythopengltonemap.h:33
MythRenderOpenGL::EnableShaderProgram
bool EnableShaderProgram(QOpenGLShaderProgram *Program)
Definition: mythrenderopengl.cpp:1581
FMT_RGBA32
@ FMT_RGBA32
Definition: mythframe.h:39
OpenGLLocker
Definition: mythrenderopengl.h:253