Accessing Surface Memory Directly (Direct3D 9)

rouke

New member
Joined
Nov 27, 2008
Messages
2
As explained in the SDK it is possible to draw bit by bit into a surface.
Still orientating on Directx, Im trying to do so.

Short summary on my intents:

*Make a surface using CreateOffscreenPlainSurface
*Lock this surface
*Modify the bytes using pointer given by LockRect
*Unlock the surface
*Copying this surface into the backbuffer using UpdateSurface

Some things Im aware of:

*Its perhaps also possible to acces the backbuffer directly, but one step at a time for me.
*I need to lear a lot about DirectX, thats why Im here, hoping to learn from you :-)
*currently as a start Im only making and copying a grey surface, when that succeeds Ill be plotting individual pixels.

My question:

*When I run my program, I get no errors but the screen remains black, in stead of greyish, what I think, or would like it to be.
Can someone help me out figuring what I did wrong?



Globals:

Code:
LPDIRECT3D9         g_pD3D = NULL; // Used to create the D3DDevice
LPDIRECT3DDEVICE9   g_pd3dDevice = NULL; // Our rendering device

LPDIRECT3DSURFACE9 	g_p2DSurface; // the pixelplotting surface
 
int g_width; // is assigned the value of d3dpp.BackBufferWidth resp. Height
int g_height;

CreateOffscreenPlainSurface (done in InitD3D)

Code:
g_pd3dDevice->CreateOffscreenPlainSurface(	d3dpp.BackBufferWidth,
												d3dpp.BackBufferHeight,
												d3dpp.BackBufferFormat,
												D3DPOOL_DEFAULT,
												&g_p2DSurface,
												NULL);




My adaptation of Render() and were I think all essential information/error should be.

Code:
VOID Render()
{
    if( NULL == g_pd3dDevice )
        return;

    // Clear the backbuffer to a blue color
	
    g_pd3dDevice->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 0, 0 ), 1.0f, 0 );

    // Begin the scene
    if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
    {
    
	// Rendering of scene objects can happen here
	
	//Creating a rectangle which is to be locked	
	D3DLOCKED_RECT rectLock = {0};

	//Locking the drawing surface
	g_p2DSurface->LockRect(&rectLock,NULL,D3DLOCK_DONOTWAIT | D3DLOCK_NOSYSLOCK );

	//The place where pixels are to be altered, byte by byte.
	BYTE* pBits;
	//Adressing the surface bytebuffer
	pBits = (BYTE*)rectLock.pBits;
	
	//Looping through all the pixels in the surface
	for (DWORD y=0;y<g_height;++y)
	{
	for (DWORD x=0;x<g_width;++x)
	{
	DWORD index= (x*4)+(y*rectLock.Pitch/4);
	pBits[index]   = (BYTE)128;// Blue
	pBits[index+1] = (BYTE)128;// Green
	pBits[index+2] = (BYTE)128;// Red
	pBits[index+3] = (BYTE)128;// Alpha
	}
	}

	g_p2DSurface->UnlockRect();
	
	IDirect3DSurface9* pBackbuffer;

	g_pd3dDevice->GetBackBuffer(0,0,D3DBACKBUFFER_TYPE_MONO,&pBackbuffer);
	
	g_pd3dDevice->UpdateSurface(g_p2DSurface,NULL,pBackbuffer,NULL);
	

        // End the scene
        g_pd3dDevice->EndScene();
    }

    // Present the backbuffer contents to the display
    g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
}
 
Last edited by a moderator:
nevermind :-)

Found out that StretchRect instead of UpdateSurface does the job!

@moderator: This thread can be deleted, thanks anyways, sorry for the mess ;-)
 
Back
Top