Problems with the D3DXMatrixOrthoLH...

Started by
4 comments, last by Poncho 16 years, 11 months ago
Hi, I am trying to program a kind of a Minimap using a camera placed on the top of my scene, this camera renders its view onto a texture that I later, in the minimap render function, place on a quad. This quad will be rendered on the screen on top of the scene… I think you know what I mean. Anyways, I thought I´d use a Orthogonal projection matrix to render the minimap quad on top of my scene, but it did not work properly. First I have problems putting the quad on the screen and if I move the main camera, the quad stay on its original place on the world and not on its place on the screen, I mean, it turns around with the rest of the geometry... Is that explanation clear??? The code: The orthogonal matrix:

D3DXMatrixOrthoLH ( &m_mtOrthogonal, 
                    ( float )xDesc.Width, ( float)xDesc.Height, 
                    0.5f, 1000.0f );


And this is the render function:

  
void cMinimap::Render( void )
{
	UINT		uiPasses;

	m_pEfx->SetTexture( "Texture0", m_pMinimap );
	m_pEfx->SetTechnique( "Minimap" );
	m_pDevice->SetVertexDeclaration( m_pDeclaration );
	m_pDevice->SetStreamSource( 0, m_pMiniVB, 0, sizeof( MyVertices ) );

	m_pEfx->SetMatrix( "g_mWorld", &m_mtIdentity  );
	m_pEfx->SetMatrix( "g_mProjection", &m_mtOrthogonal );

	m_pEfx->Begin( &uiPasses, 0 );

	for( UINT i = 0; i < uiPasses; i++ )
	{
		m_pEfx->BeginPass( i );
		m_pDevice->DrawPrimitive( D3DPT_TRIANGLESTRIP, 0, 2 ); 
		m_pEfx->EndPass();

	}
	m_pEfx->End();
}



Can anybody help me??? TIA Poncho [Edited by - Poncho on May 6, 2007 8:39:09 AM]
Advertisement
Your method is a little confused. If I understand right, you need to perform two passes per frame, each rendering the scene from a different viewpoint:

1. At initialisation-time, create world-view and projection matrices that look down on the terrain from afar. These will never need to be changed.

2. At run-time, update the mini-map texture. That is, render the scene to a render-texture using the transformation stack as created above.

3. Render the scene as normal, to the back-buffer.

4. Render the mini-map texture on top of this, using pre-transformed geometry.

Understand that, without any LOD or occlusion culling, this will double the load on the vertex-processing pipeline, so don't be surprised to see a performance hit.

Admiral
Ring3 Circus - Diary of a programmer, journal of a hacker.
Hi Admiral,
Yes, you understood it all right!
These are exactly the steps I do to render the scene and the minimap - but the performance hit here is not an issue! – Although, I am open for improvement suggestions :)
But, back to my problem: that is just the displaying the minimap – I thought if I use an Orthogonal projection, my quad would be displayed on top of everything, as a GUI element, I mean, not being part of the whole transformations thing, you know, just like people do 2D using 3D stuff. But just the Orthogonal is not enough. Do you have an idea how to get that?

Orthogonal projections are often used for 2D graphics, but not because they cause geometry to appear in front of the rest of the scene (in general, they don't). If you want a batch to be rendered without depth-testing, you should disable the Z-buffer (SetRenderState(D3DRS_ZENABLE, false)).

But here, I think the problem is a little more fundamental. GUIs are usually draw using pre-transformed geometry. If your vertex declaration (or FVF) specifies that the geometry has already been transformed, the projection matrix doesn't even come into the picture.

If you're using the FFP, specify the D3DFVF_XYZRHW flag; vertex declarations require the D3DDECLUSAGE_POSITIONT flag. Don't forget to change the vertex coordinates accordingly. Google 'transformed vertices' if you're confused.

Admiral
Ring3 Circus - Diary of a programmer, journal of a hacker.
You could also use a ID3DXSprite to display your texture. All you have to do is create the texture (in your case your scene rendered texture), and draw it on a fixed 2D coordinate on the screen. (i.e. 100, 100) and no matter where your main camera moves, your map will always be displayed at the specified coordinate. (like in most games).

If you need a more specific info on sprites let me know.
There is nothing that can't be solved. Just people that can't solve it. :)
Hello DesignerX,
Thanx for the idea but I just figured out an easy way to do it!
I just have to tell DirectX that my coordinates are already transformed, like that the whole stuff don’t go thru the pipeline and therefore not transformed. So simple like that:
In the vertex definition you just have to specify D3DDECLUSAGE_POSITIONT to your position vector and you are ready to rock!
I was completely wrong when I thought just the Orthogonal projection would do it alone – anyway it is working now…

This topic is closed to new replies.

Advertisement