2011-09-12 3 views
0

J'utilise managed DirectX pour essayer de dessiner une texture et un morceau de texte à l'écran en utilisant un Sprite. Malheureusement, si je place le texte et la texture dans le même sprite, la texture écrase (décompose?) Le texte sans tenir compte de l'ordre des commandes de dessin.Managed DirectX: Spécification de la profondeur (ordre Z) des sprites contenant la texture et le texte

Puisque je vais éventuellement vouloir intercaler des textures et du texte, comment puis-je spécifier un ordre Z pour ces sprites. Chaque couche doit-elle être dans un sprite distinct?

Voici le code actuel:

m_device.BeginScene(); 
m_device.Clear(ClearFlags.Target, Color.Black, 1.0f, 0); 
m_sprite.Begin(SpriteFlags.SortTexture | SpriteFlags.AlphaBlend); 

// Switching the order of following two statements doesn't change the Z-Order! 
m_sprite.Draw(m_texture, Vector3.Empty, new Vector3(0, 0, 0), 
       Color.White.ToArgb()); 
m_d3dFont.DrawText(m_sprite, m_text, x, y, color); 

m_sprite.End(); 
m_device.EndScene(); 
m_device.Present(); 

Remarque: L'utilisation du SpriteFlags.SortDepthBackToFront ou SpriteFlags.SortDepthBackToFront ne change pas le comportement. Ceci est probablement un malentendu conceptuel de ma part, mais si le code est utile, j'accepterai avec gratitude les échantillons dans DirectX non managé en utilisant C++ ou tout autre langage.

Merci beaucoup d'avance!

+0

La méthode Draw a-t-elle une surcharge qui prend un argument layerDepth? Comme le fait SpriteBatch de XNA, je pense que l'image-objet de DirectX gérée aurait l'un ou l'autre. – tafa

+0

Merci pour le commentaire. Ni Sprite.Draw ni Font.DrawText ont un argument de profondeur de calque. Le deuxième Vector3 dans le Sprite.Draw spécifie une position 3d, mais en faisant le Z négatif, la texture n'apparaît pas du tout, et la rendre positive ne change pas le comportement de l'overdraw. –

Répondre

2

Si vous souhaitez modifier l'ordre Z du rendu, vous devez définir la valeur Z dans la commande Dessiner. Si vous mettez le tout à 0, vous aurez toutes sortes de bizarreries. Votre plus gros problème est que DrawText ne vous permet pas de définir un Z-Depth qui est toutes sortes d'ordures.

Ainsi, votre seule chance est d'utiliser ID3DXSprite :: SetTransform. Vous devez décaler uniquement la coordonnée Z pour la position de commande z correspondante. Ainsi, vous pouvez définir vos transformations (en supposant que vous utilisez des matrices du monde d'identité) comme suit (C++ par exemple)

D3DXMATRIX mat(1.0f, 0.0f, 0.0f, 0.0f, 
       0.0f, 1.0f, 0.0f, 0.0f, 
       0.0f, 0.0f, 1.0f, 0.0f, 
       0.0f, 0.0f, zOrder, 1.0f); 
m_Sprite->SetTransform(&mat); 

Vous portez ensuite sur le passage d'une position (0, 0, 0) pour le rendu et le texte gagnera aussi la profondeur correcte pour l'ordre z.

Espérons que ça aide.

+0

Merci. Cela était assez proche pour permettre de définir la profondeur des sprites pour les textures et le texte. J'ajouterai bientôt une réponse qui fournit un exemple de code. Point mineur - pour la matrice de transformation, on veut traduire l'ordre z plutôt que l'échelle. Je l'ai fait avec Matrice t = Microsoft.DirectX.Matrix.Identité; t.Translate (0, 0, zOrder); –

+0

@Tom West: Désolé vous avez complètement raison .. c'était une erreur stupide de ma part. Je vais éditer ma réponse :) – Goz

0

Voici la réponse que je (l'affiche) allé avec:

Goz a fourni la plupart des informations nécessaires pour résoudre le problème. Essentiellement, pour les textures, vous pouvez spécifier l'ordre z en utilisant le troisième paramètre du second Verctor3. L'expérimentation a montré que (1) l'ordre z va de 0.0 à 1.0, 0.0 étant le plus proche et 1.0 étant le plus éloigné. Tout ce qui sort de cette plage n'apparaît pas du tout.

Pour le texte, car il n'y a aucune possibilité de spécifier le z dans l'appel, vous devez utiliser la suggestion de Goz d'une matrice de transformation.

Finalement, voici à peu près le code que j'ai utilisé.

m_device.BeginScene(); 
m_device.Clear(ClearFlags.Target, Color.Black, 1.0f, 0); 
m_sprite.Begin(SpriteFlags.SortDepthFrontToBack | SpriteFlags.SortTexture | SpriteFlags.AlphaBlend); 

// The "1.0f" is the z-order of texture1. This places it at the very back. 
m_sprite.Draw(m_texture1, Vector3.Empty, new Vector3(0, 0, 1.0f), 
      Color.White.ToArgb()); 

// The text1 is placed at z-order 0.8f, in order to place it in front of texture1 
Microsoft.DirectX.Matrix t = Microsoft.DirectX.Matrix.Identity; 
t.Translate(new Vector3(0, 0, 0.8f)); 
m_sprite.Transform = t; 
m_d3dFont.DrawText(m_sprite, m_text1, 200, 200, color1); 
m_sprite.Transform = Microsoft.DirectX.Matrix.Identity; 


// The "0.6f" is the z-order of texture2. This places it at the very back. 
m_sprite.Draw(m_texture2, Vector3.Empty, new Vector3(220, 220, 0.6f), 
       Color.White.ToArgb()); 

// The text2 is placed at z-order 0.4f, in order to place it in front of texture2 
t = Microsoft.DirectX.Matrix.Identity; 
t.Translate(new Vector3(0, 0, 0.4f)); 
m_sprite.Transform = t; 
m_d3dFont.DrawText(m_sprite, m_text2, 240, 240, color2); 
m_sprite.Transform = Microsoft.DirectX.Matrix.Identity; 

m_sprite.End(); 
m_device.EndScene(); 
m_device.Present(); 
Questions connexes