Seite 1 von 1

Managed Direct X Projection/View

Verfasst: 13.01.2014, 21:29
von BeRsErKeR
Hallo ich hoffe hier kennt sich jemand mit managed DirectX aus. ich benutze das jetzt zum ersten Mal und hab nun auch ein paar Sachen auf den Bildschirm gezaubert. Der grundlegende Teil sieht wie folgt aus:

Code: Alles auswählen

device.Clear(ClearFlags.Target, Color.FromArgb(0, 0, 0, 0), 1.0f, 0);
device.RenderState.ZBufferEnable = false;
device.RenderState.Lighting = false;
device.RenderState.CullMode = Cull.None;
device.Transform.Projection = Matrix.OrthoLH(this.Width, this.Height, 0, 1);
device.BeginScene();

render();

device.EndScene();
device.Present();
Die Methode render() ist von mir. In ihr wird per device.DrawUserPrimitives mit dem Typ PrimitiveType.TriangleList ein Viereck gezeichnet. Das funktioniert in der linken oberen Ecke problemlos.

Nun aber erstmal eine andere Frage. Egal was ich für die Projection-Matrix einstelle, das Viereck erscheint immer mit der gleichen Größe an der gleichen Stelle. Auch wenn ich die View- oder World-Matrix ändere, ändert sich am Ergebnis absolut gar nichts. Und ich verstehe nicht so recht wieso. Auch wenn ich z.B. farPane und nearPane auf völlig komische Werte setze und die Matrix unendlich etc enthält, wird alles schön angezeigt. Wahrscheinlich mach ich also was falsch bzw. diese Matrizen werden gar nicht verwendet. In Tutorials war das aber angeblich der Fall.

Die zweite Frage (falls diese sich nicht aus dem ersten Problem ergibt) ist folgende: Basierend auf der Fenstergröße (entspricht der Bildschirmauflösug) platziere ich das Viereck in einer der 4 Bildschirmecken.

UpperLeft: X=0, Y=0
UpperRight: X=WindowWidth-RectWidth, Y=0
LowerLeft: X=0, Y=WindowHeight-RectHeight
LowerRight: X=WindowWidth-RectWidth, Y=WindowHeight-RectHeight

Wie gesagt in der oberen linken Ecke ist alles ok. Recht oben ist das Viereck zu weit links, sodass geschätzt 4-10 Pixel rechts noch frei sind. Im Debugger stimmen die Angaben aber auf den Pixel genau bis zum Rand, daher vermute ich hier fast eine falsche Projektion. Am linken unteren Rand ist die Y-Position viel zu groß. Das Viereck verschwindet zu ca 2/3 im Bildschirmrand. Kurioserweise sieht man ab und an mal die korrekte Position für ein paar Millisekunden und dann springt es an die falsche Position und bleibt da.

Bis auf obigen Code gibt es eigentlich nur noch die Methode render():

Code: Alles auswählen

private void render()
{
            Color color = Color.Red;
            Rectangle rect = new Rectangle(x, y, 200, 60);
            CustomVertex.TransformedColored[] vertexes = new CustomVertex.TransformedColored[6];

            int alpha = (int)(255.0f * (float)(100 - Data.Transparency) * 0.01f);
            color = Color.FromArgb(alpha, color);

            vertexes[0].Position = new Vector4(rect.Left, rect.Top, 0, 1.0f);
            vertexes[0].Color = color.ToArgb();

            vertexes[1].Position = new Vector4(rect.Right - 1, rect.Top, 0, 1.0f);
            vertexes[1].Color = color.ToArgb();

            vertexes[2].Position = new Vector4(rect.Left, rect.Bottom - 1, 0, 1.0f);
            vertexes[2].Color = color.ToArgb();

            vertexes[3].Position = new Vector4(rect.Left, rect.Bottom - 1, 0, 1.0f);
            vertexes[3].Color = color.ToArgb();

            vertexes[4].Position = new Vector4(rect.Right - 1, rect.Bottom - 1, 0, 1.0f);
            vertexes[4].Color = color.ToArgb();

            vertexes[5].Position = new Vector4(rect.Right - 1, rect.Top, 0, 1.0f);
            vertexes[5].Color = color.ToArgb();

            device.VertexFormat = CustomVertex.TransformedColored.Format;
            device.DrawUserPrimitives(PrimitiveType.TriangleList, 2, vertexes);
}
Die Variablen x und y kommen von woanders aber haben dort immer die Werte (0, 0), (1280-200, 0), (0, 1024-60) oder (1280-200, 1024-60). Das passt also. Und zwar immer. Die Werte ändern sich nie, außer wenn ich sie halt selbst ändere.

Hat jemand eine Idee? Liegt es eventuell an DrawUserPrimitives?

Re: Managed Direct X Projection/View

Verfasst: 13.01.2014, 21:53
von Niki
Man, ist das lang her mit der alten DX Version, aber da klingelt was im Hinterkopf. Ich weiß aber nicht ob das bei der Managed DirectX Version so ist.

Wenn ich das richtig sehe, dann benutzt du TL Vertices. Die musste man glaube ich damals von Hand transformieren. Zumindest habe ich da so eine sehr sehr wage Erinnerung.

Re: Managed Direct X Projection/View

Verfasst: 13.01.2014, 22:10
von Niki
Ja, ok, ich scheine recht zu haben. Musste erst mal googeln um festzustellen, dass CustomVertex.TransformedColored ein Standard Format in Managed DirectX ist. In der Doku steht:
Describes a custom vertex format structure that contains transformed vertices and color information.
Damit sagst du dem System "Hey, meine Vertices sind schon transformiert", wodurch deine Vertices nicht durch die Transformations-Pipeline durchgehen (und auch nicht durch die Lighting Pipeline). Deshalb kannst du die Matrizen setzen wie du willst und es ändert sich nichts, weil die Matrizen nicht zum Einsatz kommen.

Wenn ich mich recht entsinne, dann war bei dieser Art Vertex noch nicht mal garantiert das die von der Hardware geclippt werden.

Re: Managed Direct X Projection/View

Verfasst: 13.01.2014, 22:17
von Spiele Programmierer
Naja, so alt ist die Version auch nicht. Ist auch bloß Dx9, was gerade erst am veralten ist.

Bei mir ist es allerdings auch sehr lange her. Als ich damals von VBA nach VB.Net umgestiegen bin, habe ich eine zeitlang Managed DirectX verwendet. Ich bin mir ziemlich sicher, dass man da nichts selber transformieren musste.

Ich glaube, du musst eine eigene Struktur anlegen und mit den VertexFormats-Flags angeben, welche Werte in der Struktur stecken.
EDIT: Oder einfach Positioncolored nutzen.

Re: Managed Direct X Projection/View

Verfasst: 13.01.2014, 22:23
von Niki
Spiele Programmierer hat geschrieben:Ich bin mir ziemlich sicher, dass man da nichts selber transformieren musste.
Korrekt, wenn man einen anderen Vertex-Typ nimmt. Das ist noch dieses alte System ohne Shader wo man zwischen normalen Vertices, L Vertices, und TL Vertices unterschieden hat. "T" steht dabei für "already Transformed" und "L" für "already Lit". Und für CustomVertex.TransformedColored sagt ja schon das Wort "Transformed" aus, dass die Vertices bereits transformiert sind. Lösung ist also, wie du sagst, ein anderes Vertex-Format zu benutzen.

EDIT: Hier ist auch noch eine Antwort von Tom Miller (MS Managed DirectX):
http://microsoft.public.win32.programme ... ranslating

Re: Managed Direct X Projection/View

Verfasst: 14.01.2014, 01:49
von xq
Frage von mir: Bist du dir sicher, eine völlig veraltete und nicht mehr supportete Technologie zu verwenden? Verwende anstelle ManagedDirectX doch SlimDX oder SharpDx, beide Bibliotheken sind aktuell und werden afaik gut gepflegt. Mit DirectX 9 sehe ich kein Problem, aber Managed DirectX wurde ja afaik von Microsoft mit .NET 2.0 gekippt.

Grüße
Felix

Re: Managed Direct X Projection/View

Verfasst: 16.01.2014, 19:31
von BeRsErKeR
@Niki und Spiele Programmierer: Vielen Dank. Nun wird mir einiges klar. Ich bin leider leichtsinnig davon ausgegangen, dass sich die Vertex-Typen nur darin unterscheiden, welche Werte sie anbieten (also Farbe, Position, Normalen, etc). Dass es schon vortransformierte Vertex-Typen gibt, kam mir nicht in den Sinn. Auch wenn es, wie ihr gesagt habt, der Name ja schon sagt.

@MasterQ32: Hmm ich hab lange nichts grafisches mehr gemacht bzw. meist vorhandene Sachen wie SFML (C++) benutzt. Bin da nicht so up-to-date. Es ist aber eh nur ein sehr kleines Projekt und mir reicht es ein paar Vierecke + Schrift auf den Bildschirm zu zaubern. Ich werd mir aber auch SlimDX und SharpDX (die Namen hab ich bei den Problemrecherchen schon entdeckt) mal angucken. Danke für den Hinweis.