Alternative to grabpixmap?

BlitzMax Forums/BlitzMax Programming/Alternative to grabpixmap?

Sanctus(Posted 2010) [#1]
Hey guys.
I'm on the verge of finishing my first commercial game as a Indie. Right now I'm spending time improving there and there and trying to make it as nice as possible.
Anyway, when you clicked on Main Menu it just returned you there and that wasn't very nice. I thought it would be a nice idea to actually ask if that was wanted. So how else to do it besides a dialog right?
Now... for a dialog to work everything in the background is supposed to be frozen.
My plan was to take a "screen-shot" with grabpixmap and then enter a while loop where that's drawn and the dialog is drawn and updated until something has to be returned. It works very nice but I think grabpixmap is very slow. The game freezes for like a second when the dialog should appear.
Is there any alternative to this? Rendering everything to a texture is kind of taking it too far if I have to modify all the rendering code.
Thanks guys.


TWH(Posted 2010) [#2]
You could make everything in your game freeze... Pause the game in other words and then draw your dialogue on top. But that's probably too much work.

Another option could perhaps be to lower the amount of data grabpixmap has to ...grab by rendering at a low resolution. 320x240 or something like that, and then stretch that image. It wouldn't be that pretty.


Sanctus(Posted 2010) [#3]
Well the dialog covers like 1/4 of the screen so a smart thing would be to drab more smaller chunks and put them on the final pixmap but... not sure if that would be a good idea.

And yes... actually freezing the game is not that nice since I'm mostly an adept of "nice code" or at least try to be and this would be pretty much hard-coded.


Sanctus(Posted 2010) [#4]
Well I found a solution with OpenGL:

screenShot = CreatePixmap(GraphicsWidth(), GraphicsHeight(), PF_RGBA8888)
glReadPixels(0, 0, GraphicsWidth(), GraphicsHeight(), GL_RGBA, GL_UNSIGNED_BYTE, screenShot.pixels)
screenShot = YFlipPixmap(screenShot)

I'd say it's 30 times faster(I'm getting an average of 30 ms upon calling this). Now to find something for DX.

EDIT:
from d3d7max2D:

surf.GetDC Varptr destdc
BitBlt destdc,0,0,width,height,srcdc,x,y,ROP_SRCCOPY
surf.ReleaseDC destdc
renderSurf.ReleaseDC srcdc

I'm shocked. I don't know much about directx but I know that using DC and BitBlt is like milking a dead cow. There has to be a better solution to this.


Jesse(Posted 2010) [#5]
I tried your approach before and left it behind for that same reason. the way I do it now is, I have all of my program in object types. my types are separated in create, update and display. when I want to pause the program and send control to a window, my main types skip the update process and just use the draw part of the object while the new window gets full control.
it is fully functional on a tile map editor I am working. posted here:

http://www.blitzmax.com/Community/posts.php?topic=90330

In your case, I suspect it might be a bit late for that.


ImaginaryHuman(Posted 2010) [#6]
I am most shocked that you're finding GrabPixmap to be 30 times slower than your proposed OpenGl solution... because essentially GrabPixmap also calls glReadPixels(). Is it really that must faster?

An alternative which will be way faster than either, for GL, is to call glCopyTexSubImage2D() ... copies the backbuffer into an existing texture.


slenkar(Posted 2010) [#7]
my OpenGL max2d renderer uses glCopyTexSubImage2D()
http://blitzbasic.com/codearcs/codearcs.php?code=2612