Use ltmmMemory for Memory Conversion Example for C++
1. |
Create a convert object, source and target objects: |
// creat a convert object, source and target memory objects
CoCreateInstance(CLSID_ltmmConvert,
NULL,
CLSCTX_INPROC_SERVER,
IID_IltmmConvert,
(void**) &pConvert);
CoCreateInstance(CLSID_ltmmMemory,
NULL,
CLSCTX_INPROC_SERVER,
IID_IltmmMemory,
(void**) &source);
CoCreateInstance(CLSID_ltmmMemory,
NULL,
CLSCTX_INPROC_SERVER,
IID_IltmmMemory,
(void**) &target);
// set notify window
pConvert->SetNotifyWindow((long)m_hWnd, WM_CONVERTNOTIFY);
2. |
Setup the source object, preload it with data: |
// Set the buffer size
source->put_BufferSize (fl);
SAFEARRAY sa;
VARIANT var;
// pass data from the arr BYTE array...
memset(&sa, 0, sizeof(sa));
sa.cbElements = sizeof(unsigned char);
sa.cDims = 1;
sa.fFeatures = (FADF_AUTO | FADF_FIXEDSIZE);
sa.pvData = arr; //data to fill
sa.rgsabound[0].cElements = fl;
VariantInit(&var);
V_VT(&var) = (VT_ARRAY | VT_UI1);
V_ARRAY(&var) = &sa;
source->SetData (0, fl, var);
// Set input memory object
pConvert->put_SourceStream (source);
// Set output memory object
pConvert->put_TargetStream (target);
// Set recompression
SetAVIRecompression(NULL, pConvert);
// Start conversion
pConvert->StartConvert ();
3. |
Handle the notification window to plot the data and save it to a file : |
LRESULT OnConvertNotify(WPARAM wParam, LPARAM lParam)
{
switch(wParam)
{
case ltmmConvert_Notify_Complete:
{
// Indicates a successful completion of the conversion process.
HANDLE hFile = NULL;
// write the data to a file
hFile = CreateFile(TARGET, // open file name
GENERIC_WRITE, // open for writing
FILE_SHARE_READ, // share for reading
NULL, // no security
CREATE_ALWAYS, // re-create the file
FILE_ATTRIBUTE_NORMAL, // normal file
NULL); // no attr. template
long fl = 0;
unsigned long lBytesWritten;
IltmmMemory *pTarget = NULL;
VARIANT varData;
unsigned char *pBuffer = NULL;
SAFEARRAY sa;
pConvert->get_TargetStream ((IUnknown**)&pTarget);
if(!pTarget)
break;
pTarget->get_BufferSize (&fl);
VariantInit(&varData);
// pass data
memset(&sa, 0, sizeof(sa));
sa.cbElements = sizeof(unsigned char);
sa.cDims = 1;
sa.fFeatures = (FADF_AUTO | FADF_FIXEDSIZE);
sa.pvData = new UCHAR[fl];
sa.rgsabound[0].cElements = fl;
V_VT(&varData) = (VT_ARRAY | VT_UI1);
V_ARRAY(&varData) = &sa;
//
// To lock the buffer for synchronization, use the following
// line instead of the line below :
// pTarget->LockBuffer (&varData);
// or
// pTarget->LockRegion (0, fl, &varData);
// You may also use the GetData() function
// To get the data without allocating a SAFEARRAY :
// pTarget->GetData (0, fl, &varData);
//
pTarget->CopyData (0, fl, &varData);
SafeArrayAccessData(V_ARRAY(&varData), (void**)&pBuffer);
// to manipulate the buffer bytes directly without a buffer pointer
// use the SetByte method, for example to change the first two
// bytes in the buffer :
// pTarget->SetByte(0, 0x10);
// pTarget->SetByte(1, 0x13);
WriteFile(hFile, pBuffer, fl, &lBytesWritten, NULL);
// Plot data on screen
string dataPlot;
char data[20];
short sData;
for(int i=0; i<fl ; i++)
{
pTarget->GetByte (i, &sData);
dataPlot += "0x";
dataPlot += ltoa(sData, data, 16);
dataPlot += " ";
}
OutputText(dataPlot);
// if LockBuffer() or LockRegion() is used, Unloack() must be called :
// pTarget->Unlock ();
SafeArrayUnaccessData(V_ARRAY(&varData));
VariantClear(&varData);
CloseHandle(hFile);
pTarget->Release();
}
break;
}
return 0;
}
//
// SetAVIRecompression
// sets up LEAD video compression, MP3 audio compression, and AVI file output
//
// hwndParent = parent window for compressor property dialog boxes
//
HRESULT SetAVIRecompression(HWND hwndParent, IltmmConvert *pConvert)
{
ltmmCompressors* pCompressors;
long index;
VARIANT_BOOL f;
BSTR bstr;
// select the LEAD video compressor
pConvert->get_VideoCompressors (&pCompressors);
bstr = SysAllocString(L"@device:sw:{33D9A760-90C8-11D0-BD43-00A0C911CE86}\LEAD
MCMP/MJPEG Codec A COmpressor combined with a DECompressor, or encoder and a decoder, which allows you to both compress and decompress that same data.COmpressor Also known as an encoder, this is a module or algorithm to compress data. Playing that data back requires a decompressor, or decoder. combined with a DECompressor, or encoder Also known as compressor, this is a module or algorithm to compress data. Playing that data back requires a decompressor, or decoder. and a decoder Also known as a decompressor, this is a module or algorithm to decompress data., which allows you to both compress and decompress that same data. (2.0)");
pCompressors->Find (bstr, &index);
SysFreeString(bstr);
if(index < 0)
{
// compressor isn't registered
pCompressors->Release ();
return E_FAIL;
}
pCompressors->put_Selection (index);
pCompressors->Release();
// select the MP3 audio video compressor
pConvert->get_AudioCompressors (&pCompressors);
bstr = SysAllocString(L"@device:cm:{33D9A761-90C8-11D0-BD43-00A0C911CE86}\\85MPEG Layer-3");
pCompressors->Find (bstr, &index);
SysFreeString(bstr);
if(index < 0)
{
// compressor isn't registered
pCompressors->Release ();
return E_FAIL;
}
pCompressors->put_Selection (index);
pCompressors->Release();
// set output format to AVI
pConvert->put_TargetFormat (ltmmConvert_TargetFormat_Avi);
// set video compressor properties
pConvert->HasDialog (ltmmConvert_Dlg_VideoCompressor, &f);
if(f)
pConvert->ShowDialog (ltmmConvert_Dlg_VideoCompressor, (long) hwndParent);
// set audio compressor properties
pConvert->HasDialog (ltmmConvert_Dlg_AudioCompressor, &f);
if(f)
pConvert->ShowDialog(ltmmConvert_Dlg_AudioCompressor, (long) hwndParent);
return S_OK;
}