Jump to content
  • Advertisement

Archived

This topic is now archived and is closed to further replies.

Jiia

32bit Image to Primary Display

This topic is 5127 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

What would be the absolute fastest method of transferring a finished 32-bit screen buffer to the primary display? My game has its own graphics engine which always runs in 32 bit mode. It allows me to be unconstrained by video card features or hardware configurations, and I don''t have to worry about writing all of the drawing routines in 16 and 32 bit modes. However, when the primary display mode supports 32 bit mode, I make sure my pixel format matches the display format. So they will be the same exact format in that situation. Right now, I''m tranferring my custom display to a DirectDraw 7 back buffer, then flipping it to the primary. Would using a Direct3D 9 backbuffer have any advantages or disadvantages? Would it be the same? If I draw my game onto my custom back buffer without copying it to the screen, I can go crazy, getting about 400-600 FPS (note that the refresh rate would hold it at 85fps). However, when I lock the back buffer, without drawing a single thing onto my image, just copying my image to the video-memory back buffer knocks it down to 40fps! I''m talking about a blank screen with a 2Ghz Pentium 4. It''s not acceptable. I know my problem is copying System Memory to Video Memory, per pixel, but I don''t know how to improve it. Is there a such thing as system memory primary displays? How would that work exactly? Does anyone have any other ideas / advice? Thanks!

Share this post


Link to post
Share on other sites
Advertisement
You may want to check whether you''re locking with WRITEONLY or DISCARD set (I don''t remember which apply). If you''re not, it may be locking, reading back from the card, then when you unlock it copies back.


If you are, you should still realize that as a result of the lock, the memory is considered "dirty" (DirectX doesn''t know whether it''s been updated or not) so it gets sent back to the video card anyway. Even if you don''t change anything.

The fastest way I know of is to simply use memcpy if possible. You can''t have a system memory primary display (as the video card wouldn''t have access to it).

Sorry, it''s late and I''m more-or-less stream-of-consciousing out things that pop into my head while I''m typing, so hopefully most of this is useful (and little of it is not).

Good luck


Josh

Share this post


Link to post
Share on other sites
This is the two different methods of copying 32-bit data to 32-bit data (Setup.XRes & Setup.YRes are the screen resolution):
// memcpy version ///////////////////////

LONG Span = Setup.XRes * sizeof(ULONG); // screen width * 4

ULONG *Src = Page->Bits; // my custom image

BYTE *Des = (BYTE*) SurfaceDesc.lpSurface; // DD back buffer

LONG y = Setup.YRes;
while(y--)
{
memcpy(Des,Src,Span);
Src += Setup.XRes;
Des += SurfaceDesc.lPitch;
}

// my version /////////////////////////


ULONG *Src = Page->Bits;
ULONG *Des = (ULONG*) SurfaceDesc.lpSurface;
LONG ExSpan = (SurfaceDesc.lPitch>>2) - Setup.XRes;
LONG y = Setup.YRes;
LONG x;
while(y--)
{
x = Setup.XRes;
while(x--)
{
*Des = *Src;
Src++;
Des++;
}
Des += ExSpan; // Any Extra Pitch

}
There was no noticable difference between them. 40fps both ways.

Here is my locking code:
if(Setup.nBackBuffers < 1)
{
// Lock the primary surface

if(PrimeSurface->Lock(NULL,&SurfaceDesc,DDLOCK_SURFACEMEMORYPTR|DDLOCK_WRITEONLY,NULL) != DD_OK)
{
// handle surface lost...

}
}
else
{
// Lock the back surface

if(BackSurface->Lock(NULL,&SurfaceDesc,DDLOCK_NOSYSLOCK|DDLOCK_SURFACEMEMORYPTR|DDLOCK_WRITEONLY,NULL) != DD_OK)
{
// handle surface lost..

}
}
One thing I would like to ask about is the DDLOCK_NOSYSLOCK flag. This flag prevents the whole system from being paused while the lock is in progress, right? Would it actually be more effecient to allow it to lock?

Thanks for the help, Drilian!

Share this post


Link to post
Share on other sites
My answer is simple, as I am also doing more or less the same is you, programming a 2d software only engine.

I did try using directdraw, and it was not very fast, though faster than you. And using DDraw''s Blt function is faster than copying yourself the data.

However, I discovered this: GDI is faster. Use GDI''s BitBlt to copy your back buffer to your vidcard memory buffer, it will blow you away

In my case, the timings to copy a frame looked like that, my resolution is 800x600x32.

Using my mmx copy routine: 8~10 ms
Using Draw''s Blt: ~7 ms
Using GDI: 2~3 ms

Calculate as you might, these differences make up for many more FPS

Share this post


Link to post
Share on other sites

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!