Java Schlangenbewegung bei Snake

elg

Cadet 4th Year
Registriert
März 2010
Beiträge
72
Hey!

ich bin noch ein ziemlicher anfänge in java.
habe gestern abend mal angefangen mir ein paar gedanken zu machen über eine mögliche implementierung von Snake.
anstatt mir erstmal eine grobe struktur auszudenken hab ich das quasi "on the fly" gemacht :D (ich weiss das das nicht gut ist).

nun stehe ich vor einem logischen problem.
ich habe die "schlange" als HashMap<Integer, int[]> implementiert.
nun wollte ich eine methode "move()" anfangen doch beim durchdenken hänge ich immer bei dem selbem problem.
durch tastendruck auf die richtungstasten soll die "direction" der schlange geändert werden.
move() soll dann immer in einem bestimmten zeitinterwall aufgerufen werden (vielleicht über einen Timer)
jedoch ist es ja bei snake so, dass die schlange wenn sie sagen wir 10 teile hat und sich zunächst nach rechts bewegt, bei richtungsänderung nach oben eine "ecke" bildet.
ich dachte daran vielleicht die koordinaten dieser "ecke" in einem zweistelligen array zu speichern und in der move() methode entsprechend darauf einzugehen. jedoch kann es bei einer 10 teile langen schlange theoretisch ja auch zu 5 solcher ecken kommen oder?

hat jemand eine geschickte idee damit umzugehen?

lg
 
du brauchst doch nur die position des ersten elements bestimmen, ansonsten übernimmt jedes nachfolgende element bei jedem schritt den platz des vorherigen.
 
oh man!
da hätte ich echt auch selbst drauf kommen können :D

vielen dank!
 
Um einen Punkt zu speichern würde ich die Klasse java.awt.Point benutzen.

Für jeden Teil der Schlange einen solchen Point benutzen und alle in einer ArrayList speichern. Bei jedem Schritt musst du dann aus der ArrayList den ersten rausschmeissen und und hinten einen einfügen (Für alle denen es auffällt: Ja, genausorum würde ich es machen, da die ArrayList die Elemente dann nicht verschieben muss, wenn ein neues Element dazukommt).
 
Wenn ich du wäre, würde ich mich nicht an mein Delphi-Beispiel von gestern halten, sondern die Schlange als Liste (nicht Array) von XY-Koordinaten speichern.
Dann kannst du das letzte Element immer auf die neue Position des ersten Elements setzen, es hinten von der Liste abschneiden und vorne wieder anfügen. Dadurch sparst du es dir, alle Elemente einzeln durchzugehen und erzielst trotzdem den gewünschten Effekt. Nur halt mit weniger Aufwand.

Da mein Java etwas eingestaubt ist, bekommst du hier eine Kurze Pseudocode-Erklärung:

Listenelemente:
X:Integer;
Y:Integer;
Next:Pointer auf ein Listenelement;

Die Schlange enthält ein Zeiger auf das erste Körperglied (Den Kopf der Schlange).

In der Move-Funktion, machst du folgendes:
1. Das Letzte Element ermitteln:
Code:
Element1 sei "Kopf der Schlange".
solange Element1.Next nicht "NULL" ist: 
  Element1 sei Element1.Next
2. Seine Position ändern:
Code:
Element1.X sei "Kopf der Schlange".X+1
Element1.Y sei "Kopf der Schlange".Y
3. Das Element vorne Anfügen:
Code:
Element1.Next sei "Kopf der Schlange"
"Kopf der Schlange" sei Element1
4. Das Element am Ende entfernen
Code:
solange Element1.Next ungleich "kopf der Schlange": Element1 sei Element1.Next
Element1.Next sei "NULL"

Ich nehme aber mal an, dass Java wie jede halbwegs vernünftige Programmeirsprache schon eine passende Listen-Klasse mitbringt, die das für dich macht.
 
Ich hab es jetz mal so gemacht:
erst ab dem zweiten schlangenelement alles eins nach vorne verschieben.
dann das erste element in die passende richtung schieben.

private void move() {
for(int i = 1; i<theSnake.size(); i++){
theSnake.put(i+1, theSnake.get(i));
}
if(direction == 1){
theSnake.put(1, new int[]{theSnake.get(2)[0], theSnake.get(2)[1]-1});
}
if(direction == 2){
theSnake.put(1, new int[]{theSnake.get(2)[0]+1, theSnake.get(2)[1]});
}
if(direction == 3){
theSnake.put(1, new int[]{theSnake.get(2)[0], theSnake.get(2)[1]+1});
}
if(direction == 4){
theSnake.put(1, new int[]{theSnake.get(2)[0]-1, theSnake.get(2)[1]});
}
}
 
Dieses Vorgehen funktioniert nicht. In der for-Schleife reichst du nämlich das erste Element nur nach hinten durch und überschreibst dabei alle anderen Elemente.

Mein Vorschlag oben (ArrayList) ist übrigens nicht der sinnvollste. Sinnvoller wäre die LinkedList. Da kannst du z.B. sagen, dass das erste (oder wahlweise auch das letzte) Element entfernt werden soll. danach kannst du dann einfach hinten (oder wahlweise vorne) einfach eins einfügen.
 
Zurück
Oben