0

I'm trying to use BlackMagic Decklink SDK to display a video from a Decklink card into a QtQuick application. I successfully managed to do the same using QWidgets, so the video stream aquisition part is working.

When using QWidgets (more specifically QOpenGLWidget), basically all we have to do is to create a subclass of QOpenGLWidget and override initializeGL & paintGL like this:

void DeckLinkOpenGLWidget::initializeGL()
{
    if (m_deckLinkScreenPreviewHelper != nullptr)
    {
        m_mutex.lock();
        m_deckLinkScreenPreviewHelper->InitializeGL();
        m_mutex.unlock();
    }
}

void DeckLinkOpenGLWidget::paintGL()
{
    m_mutex.lock();
    glLoadIdentity();

    glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
    glClear(GL_COLOR_BUFFER_BIT);

    m_deckLinkScreenPreviewHelper->PaintGL();
    m_mutex.unlock();
}

When doing the same in a custom renderer with QtQuick, nothing happens. I suppose I have to write my program & shaders, but I've no idea of what it needs. When using a shader coloring each pixel in a color, a square of that color is painted, so I guess I'm no to far (but could be wrong...).

Here's some code:

void VideoViewRenderer::initializeGL()
{
    QOpenGLFunctions::initializeOpenGLFunctions();

    const char* vertexShaderSource = "#version 330 core\n"
                                     "layout (location = 0) in vec3 aPos;\n"
                                     "void main()\n"
                                     "{\n"
                                     "   gl_Position = vec4(aPos.x, aPos.y, aPos.z, 1.0);\n"
                                     "}\n";

    const char* fragmentShaderSource = "#version 330 core\n"
                                       "out vec4 FragColor;\n"
                                       "void main()\n"
                                       "{\n"
                                       "   FragColor = vec4(0.6f, 0.0f, 0.0f, 1.0f);\n"
                                       "}\n";

    m_program = new QOpenGLShaderProgram();
    m_program->addCacheableShaderFromSourceCode(QOpenGLShader::Vertex,vertexShaderSource);
    m_program->addCacheableShaderFromSourceCode(QOpenGLShader::Fragment, fragmentShaderSource);
    m_program->link();

    m_mutex.lock();
    m_deckLinkScreenPreviewHelper->InitializeGL();
    m_mutex.unlock();
}

void VideoViewRenderer::paintGL()
{
    m_program->bind();

    glLoadIdentity();
    glClearColor(0.0f, 0.4f, 0.0f, 0.0f);
    glViewport(0, 0, m_viewportSize.width(), m_viewportSize.height());
    glClear(GL_COLOR_BUFFER_BIT);

    m_mutex.lock();
    m_deckLinkScreenPreviewHelper->PaintGL();
    m_mutex.unlock();

    m_program->release();
}

How am I supposed to update my shaders?

Daniel A. White
  • 187,200
  • 47
  • 362
  • 445
Tim Autin
  • 6,043
  • 5
  • 46
  • 76

1 Answers1

1

The easiest way to solve this problem is to render two triangles forming a square on the screen instead of points. Set those triangles to be textured and dynamically change the texture buffer contents with data from Decklink card.

Please see this thread for more information on using video frames in opengl: How to input video (frames) into a GLSL shader

  • Yes that would probably work, but i'd like to reuse at the maximum the DeckLink SDK, rather than having to write my own shaders and deal with the different video formats & other settings (my experience with video is very limited). I took a look at BlackMagic shaders I didn't understood most of it... I very likely just have a couple of methods to call :/ – Tim Autin May 29 '19 at 21:42
  • I haven't seen BlackMagic shaders, I had worked with Decklink SDK few years ago, and no shaders there. However, if you have those shaders maybe you should try to load them directly into rendering object. I see in your code that you're calling " m_deckLinkScreenPreviewHelper->PaintGL();" Could you post what's inside? – maciek_karaszewski Jun 02 '19 at 11:45
  • Nope, I don't have access to PaintGL's code, only the headers. All I have are the sample codes, for instance: https://github.com/HalfdanJ/VideoSuiteUtilities/blob/master/libs/Blackmagic%20DeckLink%20SDK%209.6.4/Win/Samples/LoopThroughWithOpenGLCompositing/OpenGLComposite.cpp This sample is not running on my machine, I don't know what it does. But I'd prefer to go the other way: find what is QOpenGLWidget doing that makes things work. – Tim Autin Jun 03 '19 at 15:52