The following code demonstrates how to grap samples from the capture object and feed them to the play object. It is intended to demonstrate the basic function set that would be required to remote the playback of media samples.
// define helper macros for using the interfaces under C
#ifndef COBJMACROS
#define COBJMACROS
#endif
// include the LEAD Multimedia TOOLKIT header
#include "ltmm.h"
#include <tchar.h>
#include <stdio.h>
#include <math.h>
#include <assert.h>
#define UNUSED_PARAMETER(x) (void) (x)
#define SZ_WNDCLASS_PLAY _T("PLAY WNDCLASS")
#define WM_PLAYNOTIFY (WM_USER + 1000)
HINSTANCE g_hInstance; // application instance handle
HWND g_hwndPlay; // video frame window
IltmmPlay* g_pPlay; // play object interface pointer
IltmmCapture* g_pCapture; // capture object interface pointer
IltmmSampleTarget* g_pTarget; // target object, used with capture
IltmmSampleSource* g_pSource; // source object, used with play
//
// PlayWndProc
// video frame window procedure
//
LRESULT CALLBACK PlayWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case WM_CREATE:
g_hwndPlay = hwnd;
// window is the video window frame
IltmmPlay_put_VideoWindowFrame(g_pPlay, (long) hwnd);
// assign the media source
IltmmPlay_put_SourceObject(g_pPlay, (IUnknown*) g_pSource);
#ifdef _DEBUG
{
IUnknown* punk;
IltmmPlay_get_SourceObject(g_pPlay, &punk);
assert(punk != NULL);
if(punk)
IUnknown_Release(punk);
}
#endif
return 0;
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return DefWindowProc(hwnd, message, wParam, lParam);
}
int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
MSG msg;
HRESULT hr;
WNDCLASSEX wcex;
IltmmDevices* pDevices;
VARIANT var;
IltmmMediaTypeDisp* pMediaType;
BSTR bstr;
long index;
IltmmCompressors* pCompressors;
UNUSED_PARAMETER(lpCmdLine);
UNUSED_PARAMETER(hPrevInstance);
g_hInstance = hInstance;
// initialize the COM library
hr = CoInitialize(NULL);
if(FAILED(hr))
goto error;
// register the video frame window class
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = PlayWndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = g_hInstance;
wcex.hIcon = NULL;
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH) (COLOR_APPWORKSPACE + 1);
wcex.lpszMenuName = NULL;
wcex.lpszClassName = SZ_WNDCLASS_PLAY;
wcex.hIconSm = NULL;
if(!RegisterClassEx(&wcex))
goto error;
// create the play object
hr = CoCreateInstance(&CLSID_ltmmPlay, NULL, CLSCTX_INPROC_SERVER, &IID_IltmmPlay, (void**) &g_pPlay);
if(FAILED(hr))
goto error;
// create the capture object
hr = CoCreateInstance(&CLSID_ltmmCapture, NULL, CLSCTX_INPROC_SERVER, &IID_IltmmCapture, (void**) &g_pCapture);
if(FAILED(hr))
goto error;
// create the target object
hr = CoCreateInstance(&CLSID_ltmmSampleTarget, NULL, CLSCTX_INPROC_SERVER, &IID_IltmmSampleTarget, (void**) &g_pTarget);
if(FAILED(hr))
goto error;
// create the source object
hr = CoCreateInstance(&CLSID_ltmmSampleSource, NULL, CLSCTX_INPROC_SERVER, &IID_IltmmSampleSource, (void**) &g_pSource);
if(FAILED(hr))
goto error;
// do not use preview
IltmmCapture_put_Preview(g_pCapture, VARIANT_FALSE);
// select the first video device
IltmmCapture_get_VideoDevices(g_pCapture, &pDevices);
IltmmDevices_put_Selection(pDevices, 0);
IUnknown_Release(pDevices);
// select the LEAD video compressor
IltmmCapture_get_VideoCompressors(g_pCapture, &pCompressors);
bstr = SysAllocString(L"@device:sw:{33D9A760-90C8-11D0-BD43-00A0C911CE86}\\LEAD MCMP/MJPEG Codec (2.0)");
IltmmCompressors_Find(pCompressors, bstr, &index);
SysFreeString(bstr);
IltmmCompressors_put_Selection(pCompressors, index);
IUnknown_Release(pCompressors);
// set the capture output object
IltmmCapture_put_TargetObject(g_pCapture, (IUnknown*) g_pTarget);
#ifdef _DEBUG
{
IUnknown* punk;
IltmmCapture_get_TargetObject(g_pCapture, &punk);
assert(punk != NULL);
if(punk)
IUnknown_Release(punk);
}
#endif
// start running
hr = IltmmCapture_StartCapture(g_pCapture, ltmmCapture_Mode_Video);
if(FAILED(hr))
goto error;
// retreive the video media type
IltmmSampleTarget_GetConnectedMediaType(g_pTarget, &pMediaType);
// could just assign the media type to the source object,
// but let us get the portable type instead
IltmmMediaTypeDisp_GetPortableType(pMediaType, &var);
// have the portable type, so do not need this anymore
IUnknown_Release(pMediaType);
// create a new media type
CoCreateInstance(&CLSID_ltmmMediaType, NULL, CLSCTX_INPROC_SERVER, &IID_IltmmMediaTypeDisp, (void**) &pMediaType);
// initialize it with the portable type
IltmmMediaTypeDisp_SetPortableType(pMediaType, var);
// assign it to the source object
IltmmSampleSource_SetMediaType(g_pSource, pMediaType);
#ifdef _DEBUG
{
IltmmMediaTypeDisp* punk;
IltmmSampleSource_GetMediaType(g_pSource, &punk);
assert(punk != NULL);
if(punk)
IUnknown_Release(punk);
}
#endif
// release the media type
IUnknown_Release(pMediaType);
// done with portable type
VariantClear(&var);
// create the video frame window
if(!CreateWindow(SZ_WNDCLASS_PLAY, _T("Play"), WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, g_hInstance, NULL))
goto error;
ShowWindow(g_hwndPlay, nCmdShow);
UpdateWindow(g_hwndPlay);
// process until done
for(;;)
{
if(PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE))
{
if(!GetMessage(&msg, NULL, 0, 0))
break;
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else
{
IltmmMediaSampleDisp* pSample;
// fetch a sample
hr = IltmmSampleTarget_GetSample(g_pTarget, 1000, &pSample);
if(FAILED(hr))
break;
// deliver it
hr = IltmmSampleSource_DeliverSample(g_pSource, 1000, pSample);
IUnknown_Release(pSample);
if(FAILED(hr))
goto error;
}
}
IltmmCapture_StopCapture(g_pCapture);
IltmmSampleSource_DeliverEndOfStream(g_pSource, 1000);
IltmmPlay_Stop(g_pPlay);
error:
if(g_pSource)
IUnknown_Release(g_pSource);
if(g_pTarget)
IUnknown_Release(g_pTarget);
if(g_pCapture)
IUnknown_Release(g_pCapture);
if(g_pPlay)
IUnknown_Release(g_pPlay);
CoUninitialize();
return 0;
}
Help Collections
Raster .NET | C API | C++ Class Library | HTML5 JavaScript
Document .NET | C API | C++ Class Library | HTML5 JavaScript
Medical .NET | C API | C++ Class Library | HTML5 JavaScript
Medical Web Viewer .NET
Multimedia
Direct Show .NET | C API | Filters
Media Foundation .NET | C API | Transforms
Supported Platforms
.NET, Java, Android, and iOS/macOS Assemblies
Imaging, Medical, and Document
C API/C++ Class Libraries
Imaging, Medical, and Document
HTML5 JavaScript Libraries
Imaging, Medical, and Document