Einzelnen Beitrag anzeigen

ichbins

Registriert seit: 9. Jul 2005
Ort: Hohenaltheim
1.001 Beiträge
 
Delphi 2005 Personal
 
#11

Re: NOOB!!!^^

  Alt 25. Apr 2006, 18:36
Du solltest es nicht so machen dass du ein Image hast, dass du um zehn nach oben verschiebst oder so. Damit verlierst du irgendwann die Kontrolle. Verwende ein Array, in dem du den Status aller Felder speicherst, also ob es leer ist, oder ob ein Schlangenkopf drin ist, oder ein Futter, oder ein Schlangenschwanz.


Arrays sind eine Art Listen, in denen du numeriert Daten speichern kannst.

Damit du dein zweidimensionales Spielfeld speichern kannst, brauchst du auch ein zweidimensionales Array:

Delphi-Quellcode:

var
  array2d:array [0..100 {der x-Wert des Arrays geht von null bis hundert}, 0..100 {der y-Wert auch}] of integer {in jedem Feld des Arrays kannst du einen Integer-Wert speichern};


//Beispiele des Zugriffs:

array2d[7,8]:=9; //ins Feld mit der x-Koordinate 7 und der y-Koordinate 8 im Array
label1.caption:=inttostr(array2d[15,16])); //den Wert in den Koordinaten x:15/y:16 des Arrays auslesen und im Label ausgeben
Arrays verhalten sich genauso wie "normale" Variablentypen, nur dass sie eben noch zusätzlich eine Angabe der Koordinaten innerhalb des Arrays brauchen.

Auf die einzelnen Elemente kannst du dann gut in for-Schleifen zugreifen:
Delphi-Quellcode:
var
  a:array [1..100,1..100] of string;
  x,y:integer;
begin
  for x:=0 to 100 do
    for y:=0 to 100 do
      a[x,y]:='Hallo';
end;
dieser Code setzt in jedes der 100x100 Felder des Arrays den Text 'Hallo', so dass dieser dann 10000 mal innerhalb des Arrays gespeichert ist.


Ich hoffe das war einigermaßen verständlich



jetzt sollst du dein komplettes Spielfeld speichern in einem solchen Array:

Delphi-Quellcode:
var
  spielfeld:array[1..64,1..48 {Spielfeld besteht aus 64x48 Feldern}] of integer; {die Inhalte der einzelnen Felder des Spielfeldes speicherst du als Integer-Werte (0 = Leeres Feld, 1 = Futter, 2 = Schlangenkopf, 3 = Schwanz)}


Als nächstes solltest du dann eine Prozedur schreiben (am besten nimmst du einen neuen Timer, stellst das Intervall so niedrig wie möglich und schreibst den Code dann in die Timer.Click), welche das Spielfeld, über das du genaue Informationen im Array gespeichert hast, auf den Canvas zeichnet. Zuerst musst du in der form.create vier Bilder in tbitmap-Variablen laden, eines für 'Leer', eines für 'Kopf' etc. Die sieht dann etwa so aus:

Delphi-Quellcode:
var
  x,y:integer;
  feldtyp:integer;
begin
  for x:=1 to 64 do begin //alle Horizontalen Reihen nacheinander durchgehen und darstellen
    for y:=1 to 48 do begin //für jede Horizontale Reihe von oben nach unten in dieser Reihe alle Felder durchlaufen
      //und diese Felder dann aktualisieren bzw. den Inhalt des Arrays bei diesen Koordinaten dort anzeigen
      feldtyp:=spielfeld[x,y] //den Wert des Spielfeldarrays bei den gegebenen Koordinaten auslesen
      //und dann das entsprechende Bitmap an den Koordinaten auf dem Canvas ablegen:
      case feldtyp of
        0: form1.canvas.draw(leer,x*16,y*16);
        1: form1.canvas.draw(kopf,x*16,y*16);
        2: form1.canvas.draw(schwanz,x*16,y*16);
        3: form1.canvas.draw(futter,x*16,y*16);
      end;
    end;
  end;
end;
Leer, Kopf, Schwanz und Futter sind hier natürlich die in der form.create geladenen Bitmap-Variablen.

Die Koordinaten, an denen das Bitmap abgelegt wird, werden berechnet, indem der x- und y-Wert mit 16 multipliziert werden, also verwende ich hier eine Größe der einzelnen Felder von 16x16 Pixeln. Du musst die Bitmap-Dateien natürlich entsprechend anpassen oder eine andere Größe verwenden.




Jetzt zur Bewegung:


du solltest vielleicht noch ein Array machen, in dem die Ausrichtung der einzelnen Elemente, also Schwanzteile etc. gespeichert wird. Die Ausrichtung speicherst du auch für jedes Kästchen auf dem Bildschirm.

Mach noch einen Timer, und immer wenn der schlägt, dann wird die Schlange bewegt. Das wird schon schwieriger *g*
Du musst einfach nur auf die Spielfeldvariable zugreifen, und diese entsprechend verändern. Also einfach mal mit einer For-Schleife durchsuchen und z.B. nach einem Kopf-Feld suchen. Wenn du eins gefunden hast, dann setzt du das Feld eins weiter vorne auch auf Kopf. Das alte setzt du auf Leer. Wenn im Umkreis um das alte Feld (4 möglichkeiten) ein Schwanzteil ist, welches in die Richtung dieses Feldes zeigt, dann musst du dieses auf dieses Feld setzen und das Feld, auf dem es früher war, löschen. Damit schreitest du solange fort und ziehst die Schlange Teil für Teil so lange nach vorne bis du das Ende erreichst, also kein Feld mehr findest, das in die Richtung des geräumten zeigt.


Wenn der Kopf der Schlange beim Vorrücken auf ein Futterteilchen stößt, dann machst du es so, dass du das letzte Teil der Schlange, bei dem du hinten ankommst, nicht mehr nachziehst, sondern diese Bewegungsrunde lang einfach 'liegen' lässt, also zwar das alte vorschiebst, allerdings das alte nicht durch einen freien Raum ersetzt sondern durch ein einfaches Schwanzteil ersetzt. Und schon ist die Schlange um ein Schwanzteil länger.

Dann erzeugst du an einer mit ramdom ausgewählten Stelle im Array ein neues Futterteilchen. Achte aber darauf dass du nicht versehentlich eines der Schwanzteile überschreibst:

Delphi-Quellcode:
var
  x,y:integer;
begin
  randomize; //evtl. auch in der form.create erledigbar
  x:=random(64)+1;
  y:=random(48)+1; //zufallskoordinaten zuweisen
  while spielfeld[x,y]<>0 //solange das Spielfeld mit den x- und ykoordinaten ungleich Null, also kein freies Feld ist,
  begin
    x:=random(64)+1;
    y:=random(48)+1; //neue Koordinaten erzeugen
  end;

  //jetzt kannst du mit absoluter Sicherheit sagen dass die Koordinaten ein freies Feld anzeigen, da du ja so lange neue erzeugt hast, bis das Feld frei war.

  //deshalb kannst du jetzt ein Futterteilchen an den Koordinaten erzeugen:
  spielfeld[x,y]:=3;
end;



Ich würde dir auch auf jenden Fall meinen Snake-Klon ans Herz legen, da werden alle Tipps, die ich dir soeben gegeben habe, umgesetzt. Der Code ist dabei.
Michael Enßlin
Ich, der ich weiß, mir einzubilden, dass ich weiß, nichts zu wissen, weiß, dass ich nichts weiß.
Sokrates
  Mit Zitat antworten Zitat