   save screenshot without D3DXSaveSurfaceToFile()
  I try to save data of backbuffer surface to file, but met some problems with copying data from locked surface to buffer.There no compile and runtime errors, but saved screenshot has garbage.Is there any source code in internet that describes the solution? Here is my code:LPDIRECT3DSURFACE9 backbufsurf;lpDevice->CreateOffscreenPlainSurface (WinW, WinH, D3DFMT_A8R8G8B8, D3DPOOL_SCRATCH, &backbufsurf, NULL);lpDevice->GetFrontBufferData (0, backbufsurf);D3DLOCKED_RECT rect;uint8* data = new uint8[WinW * WinH * 3];backbufsurf->LockRect (&rect, NULL, D3DLOCK_NO_DIRTY_UPDATE|D3DLOCK_NOSYSLOCK|D3DLOCK_READONLY);// copy data from ARGB8 surface buffer to RGB bitmap buffer:for (int i=0; i<WinH; i++)for (int j=0; j<WinW; j++)for (int k=0; k<3; k++)data[i*WinW*3 + j*3 + k] = *((uint8*)rect.pBits + i*WinH*4 + j*4 + k);backbufsurf->UnlockRect();backbufsurf->Release();SaveBitmap (fileName, data, WinW, WinH, 24); // the function writes raw data to file, works well in another situations   
  Are you using the Debug Runtimes? Any relevant output? Are you actually checking the return values for all these functions (You really should be)? It wouldn't surprise me at all if D3DPOOL_SCRATCH wasn't a valid pool for the surface passed to GetFrontBufferData(), causing it to fail...   ;  GetFrontBufferData needs a valid pointer to a surface. backbufsurf is undefined when you make the call.Try:IDirect3dSurface9 backbufsurf;GetFrontBufferData(0,&backbufsurf);;Quote:Original post by BuckeyeGetFrontBufferData needs a valid pointer to a surface. backbufsurf is undefined when you make the call.Try:IDirect3dSurface9 backbufsurf;GetFrontBufferData(0,&backbufsurf);CreateOffscreenPlainSurface() creates the surface. And secondly, you can't create a IDirect3dSurface9 like that, it's an abstract class.   ;  There are no errors or any DX debug output messages. So the problem is probably in copying pixels data here:data[i*WinW*3 + j*3 + k] = *((uint8*)rect.pBits + i*WinH*4 + j*4 + k);   ;Quote:Original post by brigadirThere are no errors or any DX debug output messages. So the problem is probably in copying pixels data here:data[i*WinW*3 + j*3 + k] = *((uint8*)rect.pBits + i*WinH*4 + j*4 + k);Yep, that looks wrong. You're not using the pitch at all. You probably want something like:for(int y=0; y<WinH; ++y){   memcpy(data + y*WinW, (uint8*)rect.pBits + rect.Pitch*y, WinW*4);}That copies data into the "data" array, assuming "data" is an array of WinW*WinH unsigned ints.Is there a particular reason you're not using D3DXSaveSurfaceToFile for this?   ;  I've tried in such a way.The buffer for bitmap must contain 24-bit pixels, so I need to exclude each forth byte (alpha channel) from surface buffer.   ;Quote:Original post by brigadirI've tried in such a way.The buffer for bitmap must contain 24-bit pixels, so I need to exclude each forth byte (alpha channel) from surface buffer.In that case, something like:uint8* pDest = data;for(int y=0; y<WinH; ++y){   uint32* pSource = (uint32*)((uint8*)rect.pBits + rect.Pitch*y);   for(int x=0; x<WinW; ++x)   { uint32 source = *pSource++; *pDest++ = (source&0x000000ff)>>0; *pDest++ = (source&0x0000ff00)>>8; *pDest++ = (source&0x00ff0000)>>16;   }}Untested, but shows the basic idea.Also, a little off topic - are you accounting for the DWORD alignment on bitmap scanlines? Yet another reason to use D3DXSaveSurfaceToFile instead of reinventing the wheel...   ;  The problem solved.Really, I ignore pitch. Thank you for help.Working code:for (int i=0; i<WinH; i++)for (int j=0; j<WinW; j++)for (int k=0; k<3; k++){int src_offset = i*rect.Pitch + j*4 + k;int dst_offset = (WinH-i-1)*WinW*3 + j*3 + k;data[dst_offset] = *((uint8*)rect.pBits + src_offset);}   ;Quote:Original post by brigadirThe problem solved.Really, I ignore pitch. Thank you for help.Working code:for (int i=0; i<WinH; i++)for (int j=0; j<WinW; j++)for (int k=0; k<3; k++){int src_offset = i*rect.Pitch + j*4 + k;int dst_offset = (WinH-i-1)*WinW*3 + j*3 + k;data[dst_offset] = *((uint8*)rect.pBits + src_offset);}"Working" so long as you don't use "data" as the pixel data in the BMP without correctly aligning it.Your code probably "just works" because the current width you have happens to make the scanline end on a multiple of 4 bytes, but if your backbuffer is e.g. 2px wide, or an odd number of pixels wide (I know it's unlikely, but if you have a resizable window it's entirely possible), your scanline is 6 bytes and you'll have a corrupt BMP.Again; why are you re-inventing the wheel? D3DXSaveSurfaceToFile solves all these problems for you.   