c++visual-studio-2022ms-media-foundation

Problem displaying wallpaper video using media foundation


I am working on a project to display videos on the desktop wallpaper but SetDeskWallpaper isn't fast enough and is too hard to sync music with it. I tried vlc, turns out you can't install their sdk anymore or you never could in the first place soo that's useless.

My current attempt is to use media foundation, but I get the error you can see below.

I need to display the video on the wallpaper (including audio).
I need it to run on windows 11
I need it to work in 2025
I need it to be c++ code
I need it to be compatible with Visual Studio 2022
I am also looking for alternatives to my current script because ai is a complete and utter lie

The code:

#include <mfapi.h>
#include <mfidl.h>
#include <mfobjects.h>
#include <mfplay.h>
#include <mferror.h>
#include <mfreadwrite.h>
#include <propvarutil.h>
#include <windows.h>
#include <iostream>

#pragma comment(lib, "mfplat.lib")
#pragma comment(lib, "mfuuid.lib")
#pragma comment(lib, "mfreadwrite.lib")
#pragma comment(lib, "mfplay.lib")

// Define a custom window procedure to handle video rendering window
LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
    if (uMsg == WM_DESTROY)
    {
        PostQuitMessage(0);
        return 0;
    }
    return DefWindowProc(hwnd, uMsg, wParam, lParam);
}

int main()
{
    // Initialize COM and Media Foundation
    HRESULT hr = CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
    if (FAILED(hr)) {
        std::cout << "CoInitializeEx failed with error " << hr << std::endl;
        return -1;
    }

    hr = MFStartup(MF_VERSION);
    if (FAILED(hr)) {
        std::cout << "MFStartup failed with error " << hr << std::endl;
        CoUninitialize();
        return -1;
    }

    // Create the media source
    IMFSourceResolver* pSourceResolver = NULL;
    IUnknown* pSource = NULL;
    IMFMediaSource* pMediaSource = NULL;
    hr = MFCreateSourceResolver(&pSourceResolver);
    if (FAILED(hr)) {
        std::cout << "MFCreateSourceResolver failed with error " << hr << std::endl;
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    MF_OBJECT_TYPE objectType = MF_OBJECT_INVALID;
    hr = pSourceResolver->CreateObjectFromURL(
        L"C:\\Users\\username\\Downloads\\video.webm",
        MF_RESOLUTION_MEDIASOURCE,
        NULL,
        &objectType,
        &pSource);

    if (FAILED(hr)) {
        std::cout << "CreateObjectFromURL failed with error " << hr << std::endl;
        pSourceResolver->Release();
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    hr = pSource->QueryInterface(IID_PPV_ARGS(&pMediaSource));
    if (FAILED(hr)) {
        std::cout << "QueryInterface failed with error " << hr << std::endl;
        pSource->Release();
        pSourceResolver->Release();
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    // Create a Media Session for playback
    IMFAttributes* pAttributes = NULL;
    IMFMediaSession* pMediaSession = NULL;
    hr = MFCreateAttributes(&pAttributes, 1);
    if (FAILED(hr)) {
        std::cout << "MFCreateAttributes failed with error " << hr << std::endl;
        pMediaSource->Release();
        pSource->Release();
        pSourceResolver->Release();
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    hr = MFCreateMediaSession(pAttributes, &pMediaSession);
    if (FAILED(hr)) {
        std::cout << "MFCreateMediaSession failed with error " << hr << std::endl;
        pAttributes->Release();
        pMediaSource->Release();
        pSource->Release();
        pSourceResolver->Release();
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    // Setup for video rendering
    HWND hwnd = CreateWindowEx(0, L"STATIC", L"Video Player", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
        0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN),
        NULL, NULL, NULL, NULL);

    if (!hwnd) {
        std::cout << "Failed to create window" << std::endl;
        pMediaSession->Release();
        pAttributes->Release();
        pMediaSource->Release();
        pSource->Release();
        pSourceResolver->Release();
        MFShutdown();
        CoUninitialize();
        return -1;
    }

    // Fullscreen the window to cover the desktop
    ShowWindow(hwnd, SW_MAXIMIZE);

    // At this point, you would add rendering logic for the video using Media Foundation video display interfaces

    // Start playback, render video to window, and loop until user closes the window

    // Cleanup
    if (pMediaSession) pMediaSession->Release();
    if (pAttributes) pAttributes->Release();
    if (pMediaSource) pMediaSource->Release();
    if (pSource) pSource->Release();
    if (pSourceResolver) pSourceResolver->Release();
    MFShutdown();
    CoUninitialize();

    return 0;
}

The error I get:

Error   LNK2019 unresolved external symbol MFCreateMediaSession 
referenced in function main Test    C:
\Users\username\source\repos\Test\Test\main.obj 1       

Solution

  • Your error is a linker error.

    As you can see in the MFCreateMediaSession documentation,
    you need to link with Mf.lib.

    In VS2022 this can be done by opening project properties -> Linker -> Input, then add Mf.lib in Additional Dependencies.

    enter image description here

    Alternatively, you can link the library by adding a #pragma in one of the sources:

    #pragma comment(lib, "mf.lib")