Stellen Sie sich ein 2D-Kachelraster und eine ungefähre Koordinatenkugel vor, die auf dem Spieler zentriert ist und die Sichtlinie darstellt. Ziel ist es, die Sichtlinie über Hindernisse (dh Mauern) hinaus zu blockieren.
Es ist relativ einfach festzustellen, ob eine einzelne Zelle im Sichtbereich sichtbar ist: Wirf mit Bresenham einen Strahl vom Spieler auf die Zielzelle - wenn eine der überlappenden Zellen zwischen dem Spieler und dem Ziel ein Hindernis ist, die Zielzelle ist nicht sichtbar.
Mein erster Gedanke war nun, alle Gitterzellen in der Sichtlinie zu durchlaufen - aber das scheint mir ineffizient zu sein. Wenn der Player beispielsweise neben einer Wand steht und Sie feststellen, dass die Zelle hinter der Wand nicht sichtbar ist, können Sie feststellen, dass alle Zellen auf dem Strahl danach nicht mehr sichtbar sind.
Es wurde auch erwogen, einen Strahl auf jede Zelle entlang des Umfangs der Sichtkugel zu werfen und jede Zelle entlang jedes Strahls zu iterieren - aber dann würde ich einige Zellen mehr als einmal verarbeiten.
Gibt es einen effizienteren Weg, dies zu tun?
Während das Iterieren von ~ 50 Zellen pro Runde eine relativ einfache Berechnung ist, strebe ich nach Geschwindigkeit - das Ziel ist es, beim automatischen Spielen einige Runden pro Sekunde fahren zu können. Je effizienter ich das machen kann, desto besser.
quelle
Antworten:
Sie können versuchen, "Schattenbögen" zu werfen, um größere Bereiche gleichzeitig abzudecken. Während die eigentlichen Details ein wenig involviert sind, hat Eric Lippert eine sehr ausführliche Erklärung (mit Live-Silverlight-Demo) unter http://blogs.msdn.com/b/ericlippert/archive/2011/12/12/shadowcasting-in -c-part-one.aspx .
quelle
Ich habe den von Jimmy vorgeschlagenen Algorithmus implementiert.
Video des Codes in Aktion hier: https://youtu.be/lIlPfwlcbHo
quelle