Skip to main content
GameDev.net gamedev.net
🔒 Locked

D3D9 questions

Started by vbovio Mar 28, 2008 at 4:21 PM 3 replies 1.5k views
Original Post
vbovio
vbovio
Hi, I have 4 questions for Direct3D 9 gurus: 1. How do I draw directly a memory bitmap to back buffer (like glDrawPixels) ? 2. How do I read from back buffer to a memory bitmap (like glReadPixels) ? 3. How do I upload a memory bitmap to a texture (like glTexImage2D) ? 4. How do I upload an area of the back buffer to a texture (like glCopyTexSubImage2D) ? * I refer to memory bitmap as a simple C array of uints. based on the research I have done, I think I know how to do the 4, I just want to know if I'm right or not or if there are better ways, this is what I know so far: 1. get the back buffer from the device, lock it, and write to it from memory. 2. get the back buffer from the device, lock it, and read from it to memory. 3. lock the texture, and write to it from memory. 4. get the back buffer from the device, lock it, lock the texture, and read from the back buffer to the texture. I have read that locking the back buffer hits performance, so are my answers ok, or are better ways ? Thanks!
Evil Steve
Evil Steve
Quote:
Original post by vbovio
1. How do I draw directly a memory bitmap to back buffer (like glDrawPixels) ?
As you said, Lock it and then write to it. Although that's an extremely expensive operation to do (And probably is in OpenGL). You'd be better off locking a texture, and then rendering that texture to the backbuffer, or rendering a list of point primitives.

Quote:
Original post by vbovio
2. How do I read from back buffer to a memory bitmap (like glReadPixels) ?
Again, it's very expensive to do, but your method is correct.

Quote:
Original post by vbovio
3. How do I upload a memory bitmap to a texture (like glTexImage2D) ?
I'm not sure what glTexImage2D does exactly, but you probably want to do as you described. Alternatively, there's various D3DXCreateTextureFrom* and D3DXLoadTextureFrom* functions that may be useful. Take a look in the SDK help index for those functions.

Quote:
Original post by vbovio
4. How do I upload an area of the back buffer to a texture (like glCopyTexSubImage2D) ?
Also very expensive to do, but your method seems reasonable. Alternatively, use render-to-texture to render directly into the texture surface.

Quote:
Original post by vbovio
I have read that locking the back buffer hits performance, so are my answers ok, or are better ways ?
Yup. Locking the backbuffer is extremely bad for performance. First, it causes the CPU and GPU to synchronise, then for the backbuffer to be transferred across the AGP / PCI-E bus (Which is only optimised for sending data from CPU -> GPU), then if the lock wasn't read only, you have to send it all back to the GPU again.

What exactly are you trying to do here? There's frequently a different way to go about it that in OpenGL.
vbovio
vbovio
Evil Steve:

I'm writing a small engine for 2D games, I already have the OpenGL port, now I'm trying to do what I already have using D3D9.

for the questions,

1. I just want it for testing (not to be used inside a rendering loop).
2. I want it to save files (screenshots), I know DX has functions for it, but I have already my own code for bitmaps, and I don't want to link against d3dx9.
3. glTexImage2D creates a texture and also uploads the content from memory to the texture.

so far, I think I'll use the methods I said for 1, 2 and 3.

4. here I do care for something that does not hit performance, so there is no glCopyTexSubImage2D equivalent in D3D9 ?, glCopyTexSubImage2D is fast in OpenGL AFAIK.. can you give me a small example of a render to texture example in D3D9 ??

Thanks for your reply!

MJP
MJP
I've never done it myself, but I think you can use IDirect3DDevice9::StretchRect to copy a portion of the backbuffer to a texture. However this does require that the texture is created in D3DPOOL_DEFAULT, which means it will be resident in system memory and you won't be able to lock it. There are also some restrictions for StretchRect, so you could read the documentation carefully.

ET3D
ET3D
You can use IDirect3DDevice9::UpdateSurface to copy from a system memory surface to the back buffer.

You should use GetRenderTargetData to get the back buffer into system memory, at which point you can lock the memory surface and save your data. It'd be faster than using a lockable back buffer.

StretchRect will allow you to copy from the back buffer to a render target texture.

Frankly, for a cross platform 2D game I'd suggest that you look at SDL.

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.