Wednesday, May 02, 2007

DirectX Transform Experiences

1.I tried the Flip() using the DirectX transform filter

Execute() method of a transform filter is failed..
Now I am working with this...


1.Identify whether it is possible to work with DirectX transform filter

Just copy the input surface image to the output surface image.


C:\Program Files \ IE6_LIB\
dtbase.h - these two files have the CDXBaseNTo1 class
dtbase.cpp

Any number of input image and only one output image...

Working WorkProc() fn
-----------------------------------

HRESULT CDXTWipe::WorkProc( const CDXTWorkInfoNTo1& WI, BOOL* pbContinue )
{
HRESULT hr = NOERROR;

HDC hdc1;
HDC hdc2;

OutputDebugString("\n CDXTWipe::WorkProc() fn");
hr = InputSurface(0)->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&ppSurf);
if(ppSurf == NULL)
{
OutputDebugString("\n InputSurface(0)->GetDirectDrawSurface() failed");
return E_FAIL;
}
hr = OutputSurface()->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&ppSurfOut);

if(ppSurfOut == NULL)
{
OutputDebugString("\n OutputSurface()->GetDirectDrawSurface() failed");
return E_FAIL;
}
// hr = ppSurfOut->Flip((LPDIRECTDRAWSURFACE)&ppSurf,DDFLIP_DONOTWAIT);



ppSurf->GetDC(&hdc1);
ppSurfOut->GetDC(&hdc2);
BitBlt(hdc2,0,0,300,300,hdc1,0,0,SRCCOPY);
TextOut(hdc2,10,10,"Sundar",6);
OutputDebugString("\n End of CDXTWipe::OnExecute() fn");

return hr;

}



we are deriving our DirectX transform filter from CDXBaseNTo1 class..


it takes n number of input images and produce only one output. IDXSurface interface wrapped the IDirectDrawSurface interface.


We can retrieve the input interface in a CDXBaseNTo1 class derived class as follows

IDirectDrawSurface* g_pSurfIn;
InputInterface(0) ->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&g_pSurfIn);


we can retrieve the second surface interface (image) using

InputInterface(1)

OutputInterface() - used to retrieve output surface.


we can use DirectDraw or GDI mechanism to add effects to the filter....


we can query the DirectDrawSurface using the following from the IDXSurface interface.



IDirectDrawSurface* g_pSurfIn;
InputInterface(0) ->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&g_pSurfIn);

Afterwards...

HDC hdc1;
g_pSurfIn->GetDC( &hdc1); //Get the Device context from the IDirectDrawSurface and next use the GDI functions to change the image



CDXBaseNTo1 class has Execute() fn...

Actually from the client application, we call this method for executing the transform..

this will in turn calls the


OnInitInstData()
WorkProc()
OnFreeInstData()

CDXBaseNTo1 also has the OnExecute() fn.

These three functions are virtual functions, So the derived class can change the behavior of the execution.

OnExecute() fn is not called. I wasted my time to focus on it...

But During execution, it is not called.

Execute()
{
OnInitInstData() - Init instance data
WorkProc() - This will contains the transformation code.For RGB to Gray filter
-RGB to Gray conversion is done here.

OnFreeInstData() - instance data to be released
}



How can we get the IDXSurface width and height ?


The CDXBnds template class is used to simplify construction and manipulation of the DXBNDS structure.


CDXDBnds InBounds(InputSurface(0), hr);
SIZE m_InputSize;


if (SUCCEEDED(hr))
{
InBounds.GetXYSize(m_InputSize);
}
m_InputSize has width and height of the inputSurface 0


we can identify whether the DirectDrawSurface can be flipped or not using the

GetFlipStatus() fn of the IDirectDrawSurface interface.


IDXSurface* g_pInSurfA;
IDXSurface* g_pInSurfB;




Error in IDXTransform:: Setup () fn:
------------------------------------------------------



Actually I developed the filter from the

CDXBaseNTo1 class.
In that filter

m_ulMaxInputs = 2; //These two are the members of CDXBaseNTo1 class
m_ulNumInRequired = 2;

while calling the IDXTransform interface method
Setup() fn used to pass the argument to the filter.

IUnknown* In[1];
IUnknown* Out[1];
In[0] = g_pInSurfA;
//In[1] = g_pInSurfB;
Out[0]= g_pOutSurf;
hr = g_pWipeTrans->Setup( In, 1, Out, 1, 0 );
//one input and one output


Even though I set it, the Setup() fn failed.

I changed the values as follows :

m_ulMaxInputs = 1;
m_ulNumInRequired = 1;


How can we do the DirectX transform filters :
Within DirectX transform filters we can do transform in the following ways :

1.GDI
2.GDI+
3.OpenCV
4.DirectDraw
5.Direct3D


How can we use t the the Device context from the IDXSurface ?
follow these three steps to use the device context from IDXSurface:

1.Get the DirectDraw Surface from the valid IDXSurface
2.Get the Device context from the DirectDraw Surface.
3.After processing release Device context using DirectDraw Surface.


Check this Process in the following Code :

IDirectDrawSurface* ppSurf, *ppSurfOut;
SIZE m_OutputSize;

HRESULT CDXTWipe::OnInitInstData( CDXTWorkInfoNTo1 &WorkInfo, ULONG &ulNumBandsToDo)
{
HRESULT hr = NOERROR;



//1. Get the DirectDraw Surface from the valid IDXSurface
hr = InputSurface(0)->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&ppSurf);
if(ppSurf == NULL)
{
OutputDebugString("\n InputSurface(0)->GetDirectDrawSurface() failed");
return E_FAIL;
}
hr = OutputSurface()->GetDirectDrawSurface(IID_IDirectDrawSurface,(void**)&ppSurfOut);

if(ppSurfOut == NULL)
{
OutputDebugString("\n OutputSurface()->GetDirectDrawSurface() failed");
return E_FAIL;
}

CDXDBnds outBnds(OutputSurface(),hr); // To get the output surface's width and height

if(SUCCEEDED(hr))
{
outBnds.GetXYSize(m_OutputSize);
}

return hr;

}

HRESULT WorkProc()
{
HRESULT hr = S_OK;

//2.Get the Device Context from the DirectDrawSurface

ppSurf->GetDC(&hdcInput);
ppSurfOut->GetDC(&hdcOutput);

//Processing

BitBlt(hdcOutput,0,0,m_OutputSize.cx,m_OutputSize.cy,hdcInput,0,0,SRCCOPY);
TextOut(hdcOutput,10,10,"Sundar",6);

// 3.After processing release Device context using DirectDraw Surface.
//release DC
ppSurf->ReleaseDC(hdcInput);
ppSurfOut->ReleaseDC(hdcOutput);

return hr;

}

No comments: