//The following code demonstrates how to recompress an MP4 file: //
#define MAKE_MEDIA_PATH(pFileName) (TEXT("C:\\LEADTOOLS Media Foundation\\Media\\")TEXT(pFileName))
// include the LEAD Multimedia TOOLKIT header
#include "ltmf.h"
#include "resource.h"
#include <tchar.h>
#include <stdio.h>
#include <assert.h>
HINSTANCE g_hInstance; // application instance handle
IltmfConvert* g_pConvert; // convert object's interface pointer
// user defined message id used for conversion events
#define WM_CONVERTNOTIFY (WM_USER + 1000)
//
// ConvertDlgProc
// starts the conversion process and provides status feedback
//
// controls:
// IDC_CONVERTSTATUS - static control used for status messages
// IDC_CONVERTPROGRESS - static control used for conversion progress
// IDC_USERABORT - button control used to abort the conversion or exit the dialog
BOOL CALLBACK ConvertDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
TCHAR sz[256];
BSTR bstr1;
HRESULT hr;
long streams;
switch (msg)
{
case WM_INITDIALOG:
// assign the notification window
g_pConvert->SetNotifyWindow((long) hwnd, WM_CONVERTNOTIFY);
// set the abort button text
SetDlgItemText(hwnd, IDC_USERABORT, _T("Abort"));
// start the conversion
hr = g_pConvert->StartConvert();
if(FAILED(hr))
{
bstr1 = ltmfGetErrorText(hr);
_stprintf(sz, _T("%ls"), bstr1);
SysFreeString(bstr1);
UpdateWindow(GetDlgItem(hwnd, IDC_CONVERTSTATUS));
SetDlgItemText(hwnd, IDC_USERABORT, _T("Exit"));
MessageBeep(0);
}
g_pConvert->get_UnrenderedStreams(&streams);
if(streams != 0)
MessageBox(hwnd, _T("Not all the streams could be rendered."), _T("Convert"), MB_ICONEXCLAMATION | MB_OK);
return TRUE;
break;
case WM_DESTROY:
// reset the notification window
g_pConvert->SetNotifyWindow((long) NULL, 0);
#ifdef _DEBUG
{
long state, err, pc;
double start, end, dur;
TCHAR sz[1024];
// get the current state
g_pConvert->get_State(&state);
// get the current state
g_pConvert->get_ConvertError(&err);
// get the amount converted
g_pConvert->get_PercentComplete(&pc);
// get the start
g_pConvert->get_SelectionStart(&start);
// get the end
g_pConvert->get_SelectionEnd(&end);
// get the duration
g_pConvert->get_Duration(&dur);
_stprintf(sz, _T("state = %d, error = 0x%.8X, complete = %d complete"), lParam);
SetDlgItemText(hwnd, IDC_CONVERTPROGRESS, sz);
UpdateWindow(GetDlgItem(hwnd, IDC_CONVERTPROGRESS));
break;
}
#endif
return TRUE;
break;
}
return FALSE;
}
//
// SetAudioType
// Set the audio type into the target format if:
//
void SetAudioType(IltmfTargetFormat* pTargetFormat)
{
// get target audio formats
IltmfTargetAudioFormats* pTargetAudioFormats;
pTargetFormat->get_AudioFormats(&pTargetAudioFormats);
long v = -1;
pTargetAudioFormats->get_Selection(&v);
if (v < 0)
{
pTargetAudioFormats->Release();
return;
}
IltmfTargetAudioFormat* pTargetAudioFormat;
pTargetAudioFormats->Item(v, &pTargetAudioFormat);
pTargetAudioFormats->Release();
// get target audio types collection
IltmfTargetAudioTypes* pTargetAudioTypes;
pTargetAudioFormat->get_AudioTypes(&pTargetAudioTypes);
pTargetAudioFormat->Release();
long lCount = 0;
pTargetAudioTypes->get_Count(&lCount);
for ( long lIndex = 0 ; lIndex < lCount ; lIndex++)
{
// get target audio type of index
IltmfTargetAudioType* pTargetAudioType;
pTargetAudioTypes->Item(lIndex, &pTargetAudioType);
long nAvgBytesPerSecond;
long nBitsPerSample;
long nNumChannels;
long nSamplesPerSecond;
pTargetAudioType->get_AudioAvgBytesPerSecond(&nAvgBytesPerSecond);
pTargetAudioType->get_AudioBitsPerSample(&nBitsPerSample);
pTargetAudioType->get_AudioNumChannels(&nNumChannels);
pTargetAudioType->get_AudioSamplesPerSecond(&nSamplesPerSecond);
// set the audio type into the target format if:
// AudioAvgBytesPerSecond == 24000 (192 kbps)
// AudioBitsPerSample == 16
// AudioNumChannels == 2 (stereo)
// AudioSamplesPerSecond == 44100 Hz
if (nAvgBytesPerSecond == 24000 &&
nBitsPerSample == 16 &&
nNumChannels == 2 &&
nSamplesPerSecond == 44100 )
{
pTargetFormat->SetAudioType(pTargetAudioType);
pTargetAudioType->Release();
break;
}
pTargetAudioType->Release();
}
pTargetAudioTypes->Release();
}
//
// SetMP4Recompression
// sets up H264 target video format, AAC target audio format, and MP4 file output
//
// hwndParent = parent window for target format property dialog boxes
//
HRESULT SetMP4Recompression(HWND hwndParent)
{
long index;
VARIANT_BOOL f;
BSTR bstr;
// set output format to MP4
g_pConvert->put_TargetFormat(ltmfConvert_TargetFormat_MP4);
#ifdef _DEBUG
{
long v;
g_pConvert->get_TargetFormat(&v);
assert(v == ltmfConvert_TargetFormat_MP4);
}
#endif
// get target format
IltmfTargetFormats* pTargetFormats;
IltmfTargetFormat* pTargetFormat;
g_pConvert->get_TargetFormats(&pTargetFormats);
long v;
pTargetFormats->get_Selection(&v);
pTargetFormats->Item(v, &pTargetFormat);
pTargetFormats->Release();
// get target video formats
IltmfTargetVideoFormats* pTargetVideoFormats;
pTargetFormat->get_VideoFormats(&pTargetVideoFormats);
// select the H264 target video format
bstr = SysAllocString(L"{34363248-0000-0010-8000-00AA00389B71}");
pTargetVideoFormats->Find(bstr, &index);
SysFreeString(bstr);
if(index < 0)
{
// video target format isn't registered
pTargetFormat->Release();
pTargetVideoFormats->Release();
return E_FAIL;
}
pTargetVideoFormats->put_Selection(index);
pTargetVideoFormats->Release();
// set Video bit rate to 500 KB
pTargetFormat->put_VideoBitrate(500000);
// set Video EncodeQuality to 10
pTargetFormat->put_VideoEncodeQuality(10);
// set Video Frame Width to 320
pTargetFormat->put_VideoFrameWidth(320);
// set Video Frame Height to 240
pTargetFormat->put_VideoFrameHeight(240);
// set Video Frame Rate to 30.0 fps
pTargetFormat->put_VideoFrameRate(30.0);
#ifdef _DEBUG
{
long v;
pTargetFormat->get_VideoBitrate(&v);
assert(v == 500000);
pTargetFormat->get_VideoEncodeQuality(&v);
assert(v == 10);
pTargetFormat->get_VideoFrameWidth(&v);
assert(v == 320);
pTargetFormat->get_VideoFrameHeight(&v);
assert(v == 240);
double d;
pTargetFormat->get_VideoFrameRate(&d);
assert(d == 30.0);
}
#endif
// get target audio formats
IltmfTargetAudioFormats* pTargetAudioFormats;
pTargetFormat->get_AudioFormats(&pTargetAudioFormats);
// select the AAC target audio format
bstr = SysAllocString(L"{00001610-0000-0010-8000-00AA00389B71}");
pTargetAudioFormats->Find(bstr, &index);
SysFreeString(bstr);
if(index < 0)
{
// audio target format isn't registered
pTargetFormat->Release();
pTargetAudioFormats->Release();
return E_FAIL;
}
pTargetAudioFormats->put_Selection(index);
pTargetAudioFormats->Release();
// set Audio Avg Bytes Per Second to 12000 (96 Kbps)
pTargetFormat->put_AudioAvgBytesPerSecond(12000) ;
// set Audio Bits Per Sample to 16
pTargetFormat->put_AudioBitsPerSample(16);
// set Audio Channels number to 2 (stereo)
pTargetFormat->put_AudioNumChannels(2);
// set Audio samples per second to 44100 (44.1 KHz)
pTargetFormat->put_AudioSamplesPerSecond(44100);
#ifdef _DEBUG
{
long v;
pTargetFormat->get_AudioAvgBytesPerSecond(&v);
assert(v == 12000);
pTargetFormat->get_AudioBitsPerSample(&v);
assert(v == 16);
pTargetFormat->get_AudioNumChannels(&v);
assert(v == 2);
pTargetFormat->get_AudioSamplesPerSecond(&v);
assert(v == 44100);
}
#endif
pTargetFormat->Release();
// set target format properties
g_pConvert->HasDialog(ltmfConvert_Dlg_TargetFormat, &f);
if(f)
g_pConvert->ShowDialog(ltmfConvert_Dlg_TargetFormat, (long) hwndParent);
return S_OK;
}
//
// RecompressFile
// recompresses a file using the MP4 target format
//
// pszSource = source file path
// pszTarget = target file path
//
HRESULT RecompressFile(LPCTSTR pszSource, LPCTSTR pszTarget)
{
HRESULT hr;
BSTR bstr;
#ifndef _UNICODE
WCHAR wsz[MAX_PATH];
#endif
// set source file
#ifdef _UNICODE
bstr = SysAllocString(pszSource);
#else
swprintf(wsz, L"%hs", pszSource);
bstr = SysAllocString(wsz);
#endif
hr = g_pConvert->put_SourceFile(bstr);
SysFreeString(bstr);
if(FAILED(hr))
return hr;
// set target file
#ifdef _UNICODE
bstr = SysAllocString(pszTarget);
#else
swprintf(wsz, L"%hs", pszTarget);
bstr = SysAllocString(wsz);
#endif
hr = g_pConvert->put_TargetFile(bstr);
SysFreeString(bstr);
if(FAILED(hr))
return hr;
// setup AVI recompression
hr = SetMP4Recompression(NULL);
if(FAILED(hr))
return hr;
// do conversion
hr = (HRESULT) DialogBox(g_hInstance, (LPCTSTR)IDD_CONVERTDLG, NULL, ConvertDlgProc);
return hr;
}
int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
HRESULT hr;
g_hInstance = hInstance;
// initialize COM library
hr = CoInitialize(NULL);
if(FAILED(hr))
goto error;
// create the convert object
hr = CoCreateInstance(CLSID_ltmfConvert, NULL, CLSCTX_INPROC_SERVER, IID_IltmfConvert, (void**) &g_pConvert);
if(FAILED(hr))
goto error;
hr = RecompressFile(MAKE_MEDIA_PATH("source.MP4"), MAKE_MEDIA_PATH("target.MP4"));
if(FAILED(hr))
goto error;
error:
// cleanup
if(g_pConvert)
g_pConvert->Release();
CoUninitialize();
return 0;
}