Get 'unmanaged compointer' from Direct3D surface

Miky_Mike

Member
Joined
Aug 5, 2009
Messages
8
Programming Experience
5-10
Hello,

I have a problem getting an 'unmanaged compointer' from a Direct3D surface.

The DirectShow.net VMR9 object can show bitmaps onto the video, and uses a reference to the bitmap. This can be GDI (a hDC), but also a 'unmanaged compointer' to the surface. I want to use Direct3D because there a more features that I can use.

I C# there is something like:
unmanagedSurface = surface.GetObjectByValue(DxMagicNumber);

I have searched for many houres on the internet for a solution... I have tried some Interop.Marshal stuff... but nothing worked :(

I know that there is a SlimDX library, but I prefer the Microsoft Direct3D.

Is there anybody here who knows how to use the direct3D surface in combination with the DirectShow.net VMR9/IVMRMixerBitmap9 objects???

I'm using the DirectShow.net 2005 and the Microsoft DirectX9 SDK

Mike
 
The problem is solved for me by using the SlimDX managed library. It works perfect in combination with the DirectShow.net managed library.

May be the code is interresting for others, here are some code snippets:

'--------------------------------------
Declarations:
Imports DirectShowLib
Imports SlimDX.Direct3D9

Private D3d As Direct3D = Nothing
Private D3Ddevice As Device = Nothing
Private presentParams As PresentParameters = Nothing
Private MySurface As Surface = Nothing 'Loaded with the aplha bitmap
Private unmanagedSurface As IntPtr = IntPtr.Zero

'--------------------------------------
'Direct 3D Variables (SlimDX)
D3d = New Direct3D()
presentParams = New PresentParameters()
presentParams.Windowed = True
presentParams.SwapEffect = SwapEffect.Discard
D3Ddevice = New Device(D3d, 0, _
DeviceType.Hardware, _
hLocalControlHandle, _
CreateFlags.HardwareVertexProcessing, _
presentParams)

MySurface = Surface.CreateOffscreenPlain(D3Ddevice, iWidth, iHeight, Format.A8R8G8B8, Pool.SystemMemory)
unmanagedSurface = MySurface.ComPointer

'--------------------------------------
'Add image (f.e. bitmap) to the Surface
Dim ReturnData As VMR9AlphaBitmap = Nothing

'Draw onto the surface...
Dim lrect As Rectangle = New Rectangle(0, 0, iWidth, iHeight)

'Lock / define drawing rectangle...
Dim d3drect As SlimDX.DataRectangle = MySurface.LockRectangle(lrect, LockFlags.None)
Dim bmpd As BitmapData = lBitmap.LockBits(lrect, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb)
Dim Size As Integer = bmpd.Stride * bmpd.Height
Dim TempArray(Size - 1) As Byte

'Copy the bitmap data into an byte array using Copy...
Marshal.Copy(bmpd.Scan0, TempArray, 0, Size)

'Write the byte array data to the surface...
d3drect.Data.Write(TempArray, 0, Size)

'Unlock the drawing area...
MySurface.UnlockRectangle()

lrect = Nothing
d3drect = Nothing
bmpd = Nothing

'--------------------------------------
ReturnData.dwFlags = VMR9AlphaBitmapFlags.EntireDDS
ReturnData.pDDS = unmanagedSurface
ReturnData.rDest = New NormalizedRect(0, 0, 1.0, 1.0)
ReturnData.fAlpha = 1.0

'--------------------------------------
hr = m_MixerBitmap.SetAlphaBitmap(ReturnData)
DsError.ThrowExceptionForHR(hr)

May be is there a more efficient way to overcome the dubble copy in the code...

Mike
 
Back
Top