Ich versuche, bewegungsunabhängige Sprites in einem 2D-Spiel auflösungsunabhängig zu rendern. Mein Plan ist es, in einem festen Koordinatensystem in meiner Welt zu arbeiten (z. B. 960 x 540) und diese mithilfe der orthografischen Projektion nach oben oder unten zu skalieren, um sie an das Ansichtsfenster anzupassen. Ich mache Letterboxing, um verschiedene Seitenverhältnisse zu handhaben.
Gemäß den meisten Tutorials kann ich beliebige Abmessungen für den Ansichtsstumpf verwenden, aber ich habe festgestellt, dass dies in vielen Fällen zu dem Problem führt, dass ich im Ansichtsfenster Subpixelwerte verwende. Beispielsweise endet ein Scheitelpunkt bei (62,62) in einem Koordinatensystem von 960 x 540 bei (51.6666667,51.6666667) in einem Ansichtsfenster mit den Abmessungen 800 x 450.
Dabei sind mir zwei Arten von Problemen aufgefallen:
- Die Texturabtastung ändert sich ständig für Objekte, die sich in Bewegung befinden, je nachdem, wo sich die Scheitelpunkte in Bezug auf ein Pixelzentrum befinden
- Meine Objekte werden aufgrund von Rundungen von Zeit zu Zeit horizontal oder vertikal um ein Pixel gedehnt
Was ist die beste Vorgehensweise, um dies zu vermeiden (unter Wahrung der Unabhängigkeit der Auflösung in Bezug auf Bewegungsgeschwindigkeiten usw.)? Und wo wäre der beste Ort, um dies anzugehen? Bevor Sie die Scheitelpunkte an die Shader oder in den Scheitelpunkt-Shader übergeben?
quelle
Antworten:
Um zu Ihrer Hauptfrage zu gelangen, ob die Scheitelpunkte vor oder während des Shaders beeinflusst werden sollen, wird die Verwendung eines Shaders bevorzugt. Wenn Sie wissen, wie eine Routine geschrieben wird, die das Ansichtsfenster und das Koordinatensystem berücksichtigt, wird die Verwendung eines Shaders bevorzugt, da viele Sprites parallel angepasst werden können. Außerdem wird sichergestellt, dass die "kosmetischen" Koordinaten von den Koordinaten im Spiel im CPU-Code getrennt bleiben, sodass das eine das andere nicht beeinflusst.
Sie können dies entweder im Vertex- oder im Pixel-Shader tun. Im Pixel-Shader ist es möglich, Texel zu verschieben, um sie an die Pixel auf dem Display zu binden.
In DirectX9 musste ich dies mit HLSL tun, um die Eigenart zu umgehen, dass sich die Texelecken bei 0,5, 0,5 relativ zum Pixel befanden , sodass gestochen scharfe Texturen halb verschwommen aussehen. Wenn Sie dies korrigieren, wird die physische Position der Texel geändert, ohne dass die Scheitelpunkte verschoben werden.
In Ihrem Fall variiert der Versatz von Bild zu Bild. Übergeben Sie daher die wahren Koordinaten des Sprites an den Shader, um den Dezimalversatz zu berechnen. Denken Sie daran, die Texturabtastung zu klemmen, um ein Umwickeln der Texturen zu vermeiden.
quelle
Ich denke, ich würde zwei Koordinatensätze speichern.
DISPLAY POSITION
undTRUE POSITION
.Auf diese Weise können Sie Sprites mit abgerundeten Koordinaten zeichnen, um Verzerrungen zu vermeiden, die durch die feste Größe Ihres Ansichtsbereichs verursacht werden.
Auf diese Weise können Sie aber auch den genauen Standort beibehalten, ohne Ihre Spiellogik zu beeinflussen. Aufgrund der Art der Subpixel denke ich auch, dass Sie nicht einmal Diskrepanzen zwischen der Ansicht und der Spielelogik bemerken werden.
quelle