'Callback for Decklink Duo 2

I am a Electrical Engineering student and for first code in my internship I have to write something that captures and saves image and video from a DeckLink Duo 2 card using exclusively the SDK for it, that being my first "real code", unlike the mostly basic stuff we write in the university.

At the moment I am trying to merely set the basic functions for capture and happen to be having trouble instantiating the Callback object and its logic.

Code reads as follows:

#include "DeckLinkAPI.h"
#include <stdio.h>
#include <list>
#include <map>
#include <string>
#include <conio.h>
#include "platform.h"

int     main(int argc, char** argv)
{
    IDeckLinkIterator*              deckLinkIterator;
    IDeckLinkAPIInformation*        deckLinkAPIInformation;
    IDeckLink*                      deckLink;
    IDeckLinkProfileAttributes*     deckLinkAttributes = NULL;
    int                             numDevices = 0;
    uint32_t                        printFlags = 0;
    HRESULT                         result;
    IDeckLinkInput*                 deckLinkInput = NULL;
    IDeckLinkDisplayModeIterator*   displayModeIterator = NULL;
    IDeckLinkDisplayMode*           displayMode = NULL;
    IDeckLinkInputCallback*         deckLinkInputCallback = NULL;


    IDeckLinkVideoInputFrame*   videoFrame;
    IDeckLinkAudioInputPacket*  audioPacket = NULL;

    char nome;
    long width, height;

    // Initialize COM on this thread
    result = CoInitializeEx(NULL, COINIT_MULTITHREADED);
    if (FAILED(result))
    {
        fprintf(stderr, "Initialization of COM failed - result = %08x.\n", result);
        (void)_getch();
        return 1;
    }


    // Create an IDeckLinkIterator object to enumerate all DeckLink cards in the system
    result = GetDeckLinkIterator(&deckLinkIterator);
    if (result != S_OK)
    {
        fprintf(stderr, "A DeckLink iterator could not be created.  The DeckLink drivers may not be installed.\n");
        (void)_getch();
        return 1;
    }

    // Enumerate all cards in this system

    while (deckLinkIterator->Next(&deckLink) == S_OK)
    {

        dlstring_t deviceNameString;

        // Increment the total number of DeckLink cards found
        // Incrementa o total de PORTAS Declink encontradas
        numDevices++;
        if (numDevices > 1) 
        {
            printf("\n\n");
        }

        // Query the DeckLink for its input interface
        result = deckLink->QueryInterface(IID_IDeckLinkInput, (void**)&deckLinkInput);
        if (result != S_OK)
        {
            fprintf(stderr, "Could not obtain the IDeckLinkInput interface - result = %08x\n", result);
            (void)_getch();
            return 0;
        }

        result = deckLinkInput->GetDisplayModeIterator(&displayModeIterator);
        if (result != S_OK)
        {
            fprintf(stderr, "Could not obtain the video output display mode iterator - result = %08x\n", result);
            (void)_getch();
            return 0;
        }

        result = deckLinkInput->EnableVideoInput(bmdModeHD1080p6000, bmdFormat8BitYUV, bmdVideoInputFlagDefault);
        if (result != S_OK)
        {
            fprintf(stderr, "Nao pode habilitar o input - result = %08x\n", result);
            (void)_getch();
            return 0;
        }


//Bad stuff apparently starts to happen here
        result = deckLinkInput->SetCallback(deckLinkInputCallback);
        if (result != S_OK)
        {
            fprintf(stderr, "nao foi possivel definir o callback do decklinkinput - result = %08x\n", result);
            (void)_getch();
            return 0;
        }
        

        result = deckLinkInput->StartStreams();
        if (result != S_OK)
        {
            fprintf(stderr, "Nao foi possivel iniciar a captura - result = %08x\n", result);
            (void)_getch();
            return 0;
        }


        result = deckLinkInputCallback->VideoInputFrameArrived(videoFrame, audioPacket);
        if (result != S_OK)
        {
            fprintf(stderr, "Nao esta chegando frames do input - result = %08x\n", result);
            (void)_getch();
            return 0;
        }

        /// AQUI DEVE SER INSERIDO, ALGO PARA CAPTURAR O FRAME E SALVAR OU COMO FOTO OU COMO VIDEO


        result = deckLinkInput->StopStreams();
        if (result != S_OK)
        {
            fprintf(stderr, "Nao foi possivel finalizar a captura - result = %08x\n", result);
            (void)_getch();
            return 0;
        }

        displayModeIterator->Release();

        // Release the IDeckLink instance when we've finished with it to prevent leaks
        deckLink->Release();
    }

    deckLinkIterator->Release();

    // Uninitalize COM on this thread
    // Encerra a COM desta thread
    CoUninitialize();

    // Wait for any key press before exiting
    (void)_getch();

    // If no DeckLink cards were found in the system, inform the user
    // Se nenhuma porta for encontrada, informa ao usuario.
    if (numDevices == 0) {
        printf("No Blackmagic Design devices were found.\n");
        printf("\n");
    }

    return 0;
}

I see I have to use QueryInterface to obtain IDeckLinkInput from IDeckLink, but the logic behind the Callback eludes me: how can I initialize IDeckLinkInputCallback? At least from the documentation I understand that I don't need to use QueryInterface to obtain it — and trying to do so only returned me an error. My idea was to then use the deckLinkInputCallback as an argument for the SetCallback method to see if I could obtain something and it really doesn't affect anything, regardless of whether I initialize it as NULL or not. It's clear my understanding of the callback is still far from ideal. When I get to VideoInputFrameArrived, the object deckLinkInputCallback is NULL and videoFrame doesn't receive anything either. The documentation is, most of the time, sadly vague.

Also, I saw examples of the callback using the argument of the function as "this" but the compiler says it only works with static functions.

What am I getting wrong with the logic here? Thank you.



Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source