Jump to content
  • Advertisement
Sign in to follow this  
ms291052

ID3DXFont and Depth

This topic is 4833 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

Is there any way to specify a Z coordinate at which ID3DXFont renders? I imagine it's in screen space and thus would use Z coords in the set [0.0, 1.0) but I can't find any way to do it since the only positional argument is a RECT. Anyone have any ideas? Thanks, ms

Share this post


Link to post
Share on other sites
Advertisement
Since all the transforms are handled through the font's ID3DXSprite interface, you could try using ID3DXSprite::SetTransform() before drawing text. However, the ID3DXFont interface might set its own transforms before drawing text, meaning that your transform would be erased. I think I used the SetTransform() method when I made a sprite engine, though, and it worked for setting the Z depth of the sprites. I used D3DXMatrixTranslation(mat,0,0,zdepth); to generate the matrix and passed it into SetTransform().

If using SetTransform() doesn't work, well, the only way to draw your text in a specific Z order would be to sort it yourself, and draw from back to front.

Share this post


Link to post
Share on other sites
Quote:
Original post by Drakex
Since all the transforms are handled through the font's ID3DXSprite interface, you could try using ID3DXSprite::SetTransform() before drawing text. However, the ID3DXFont interface might set its own transforms before drawing text, meaning that your transform would be erased. I think I used the SetTransform() method when I made a sprite engine, though, and it worked for setting the Z depth of the sprites. I used D3DXMatrixTranslation(mat,0,0,zdepth); to generate the matrix and passed it into SetTransform().

If using SetTransform() doesn't work, well, the only way to draw your text in a specific Z order would be to sort it yourself, and draw from back to front.


Using ID3DXSprite::SetTransform() does indeed work for ID3DXFont.

Share this post


Link to post
Share on other sites
Actually SetTransform doesn't help since I'm working in screen space (Pretransformed [RHW] coordinates). I managed to hack together a little solution where it draws the text to a texture with a purple (0xFFFF00FF) background and white text. Then I can use ID3DXSprite to render the texture, remove the purple with colorkeying, then use the modulation color parameter of ID3DXSprite::Draw to make it the right color. And of course ID3DXSprite::Draw takes a 3D position that includes a nice Z component.

Thanks for the input guys, and if anyone has any other suggestions, please post a reply!

Share this post


Link to post
Share on other sites
Quote:
Original post by ms291052
Actually SetTransform doesn't help since I'm working in screen space (Pretransformed [RHW] coordinates). I managed to hack together a little solution where it draws the text to a texture with a purple (0xFFFF00FF) background and white text. Then I can use ID3DXSprite to render the texture, remove the purple with colorkeying, then use the modulation color parameter of ID3DXSprite::Draw to make it the right color. And of course ID3DXSprite::Draw takes a 3D position that includes a nice Z component.

Thanks for the input guys, and if anyone has any other suggestions, please post a reply!


Why should it matter that you're in screen space? Unless you specify otherwise, calling ID3DXSprite::Begin() automatically switches to "screen space" mode anyway. SetTransform() works perfectly fine, here's a snippet:


void nxt::Direct3D::DrawText(const float x, const float y, const std::string& text, const nxt::Color& color, const float depth) const
{
D3DXMATRIX positionMatrix;
D3DXMatrixTranslation(&positionMatrix, x, y, depth);
m_d3dSprite->SetTransform(&positionMatrix);

m_d3dFont[m_fontID]->DrawText(m_d3dSprite, text.c_str(), -1, NULL, DT_LEFT | DT_NOCLIP, ToD3DColor(color));
}




The valid values for the z coordinate (the depth) are [0, 1], with 0 being the closest and 1 being the farthest.

EDIT: Also, make sure ID3DXSprite::Begin() is being passed D3DXSPRITE_SORT_DEPTH_FRONTTOBACK and not being passed D3DXSPRITE_SORT_TEXTURE. D3DXSPRITE_SORT_TEXTURE seems to ignore the z coordinates specified and gives every texture their own seemingly random depth.

Share this post


Link to post
Share on other sites
Here's my text class's Render method:


void Render()
{
Point AbsPos = GetAbsPosition(); //Gets the absolute position of this text object
LPD3DXSPRITE sprite;
D3DXCreateSprite(m_pD3D->m_pd3dDevice, &sprite); //Create a sprite

D3DXMATRIX m; //Setup the transforms
D3DXMatrixTranslation(&m, AbsPos.x, AbsPos.y, m_Z);
sprite->SetTransform(&m);

RECT r = {0, 0, 800, 600}; //The whole window, just to test
m_pD3D->GetFont()->DrawText(sprite, m_Caption.c_str(), -1, &r, DT_LEFT, color); //Draw
sprite->Release(); //Cleanup
}



I know I create and release the sprite every frame and all that; this is just a prototype to see if it works. When I do this the text still appears on top of everything else, including opaque objects with a lower z-value. When I use the render-to-texture method it works just fine.

I was under the impression that the whole point of RHW coords is that they are pre-transformed and thus aren't affected by any other transforms. Am I incorrect?

Please correct me if I've done something wrong with the above code, but I'm afraid it simply doesn't seem to go to any depth value other than 0.0.

Thanks for your help, load_bitmap_file, and further suggestions are, of course, appreciated.

ms

Share this post


Link to post
Share on other sites
Quote:
When I do this the text still appears on top of everything else, including opaque objects with a lower z-value


Wait.. so you want to draw the text interleaved with (or behind) 3D objects? I'm not sure if that's entirely possible with ID3DXFont. You can certainly change the overall rendering order (by rendering text first, and then rendering objects), but to render text in a 3D scene, I don't know if that's possible with ID3DXFont.

What exactly are you aiming to do?

Share this post


Link to post
Share on other sites


Quote:
Original post by Drakex
Quote:
When I do this the text still appears on top of everything else, including opaque objects with a lower z-value


Wait.. so you want to draw the text interleaved with (or behind) 3D objects? I'm not sure if that's entirely possible with ID3DXFont. You can certainly change the overall rendering order (by rendering text first, and then rendering objects), but to render text in a 3D scene, I don't know if that's possible with ID3DXFont.

What exactly are you aiming to do?


If what Drakex says is correct, i.e. drawing text behind other 3d objects then I don't think the SetTransform() isn't going to work unless all the objects are between [0, 1] on the z-axis, and assuming you're working in 3d, they won't be. I guess you'd have to call the draw to the text first and then the other stuff manually sorted outself as Drakex said.

If you're not working with 3d, then try calling sprite->Begin(D3DXSPRITE_ALPHABLEND | D3DXSPRITE_SORT_DEPTH_FRONTTOBACK) before you draw the text.

That's all I can think of right now.

Share this post


Link to post
Share on other sites
Well darn, I had simply forgotten to call Begin and End. With them it seems to work pretty well. Thank you to everyone for your help, especially load_bitmap_file.


By the way, this is all for a HUD type of thing, so it's in no way interleaved with 3D objects, but it is interleaved with many layers of 2D objects in a fashion that is approaching almost GUI-ness.

Thanks again,

ms

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

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

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!