Tic Tac Toe Spiel Probleme?

Übersicht BlitzBasic Beginners-Corner

Neue Antwort erstellen

 

bruce85

Betreff: Tic Tac Toe Spiel Probleme?

BeitragFr, Jun 09, 2006 1:15
Antworten mit Zitat
Benutzer-Profile anzeigen
hallo,
ich bin grad dabei en Tic Tac Toe Spiel zu schreiben, alles funktioniert soweit, aber wie Prüfe ich ob 3 in einer Reihe Richtig sind?
z.B.

[0] [X] [X]
[0] [0] [X]
[X] [0] [0]

oder

[0] [0] [X]
[X] [0] [X]
[X] [0] [0]

also ich habe ein Bild geladen mit 3 Frames, also: Frame0 = Leeres Feld, Frame1 = Kreis und Frame2 = Quadrat, und ich möchte Prüfen ob 3 gleiche Frame nebeneinander sind oder untereinander, ich habe ja die Felder mit Types erstellt, hier mal mein Code:

Code: [AUSKLAPPEN]
Graphics 350,250,16,2
SetBuffer BackBuffer()

AppTitle "Tic Tac Toe"

;Feld Laden
Global stein = LoadAnimImage("stein.png",50,50,0,3)
MaskImage stein,255,0,255

Type steine
  Field stein_x
  Field stein_y
  Field stein_frames = 0 ;0 für Leeres Feld
End Type

;insgesamt 9 Felder erstellen
;3 Felder nach rechts und 3 Felder nach Unten
For i=1 To 3
  For j=1 To 3
    s.steine = New steine
    s\stein_x = s\stein_x + i
    s\stein_y = s\stein_y + j
  Next
Next

;Spieler auf 1 setzen da Spieler1 anfängt
Global Spieler = 1
;Frame0 = Leeres Feld, Frame1 = Kreis und Frame2 = Quadrat
Global stein_frames = 1

Repeat
  ClsColor 127,127,127
  Cls

  ;Alle Felder Abfragen
  For s.steine = Each steine
    ;Felder auf dem Bildschirm Malen
    DrawImage stein,s\stein_x*52,s\stein_y*52,s\stein_frames
    ;Kollision mit dem einzelnen Feld Prüfen
    If RectsOverlap(MouseX(),MouseY(),1,1,s\stein_x*52,s\stein_y*52,50,50) Then
      ;Wenn s\stein_frames = 0 dann ist ja das Feld noch leer
      ;und man kann dann auf dem entsprechendes Feld klicken
      If s\stein_frames = 0 Then
        If MouseDown(1) Then
          If MouseHit(1) Then
            ;Wenn Spieler = 1 dann führe das hier aus
            ;anschließend die werte für Spieler2 setzen
            ;stein_frames = 2 und Spieler = 2
            If Spieler = 1 Then
              s\stein_frames = 1
              stein_frames = 2
              Spieler = 2
            EndIf
            Else
            ;Wenn Spieler = 2 dann führe das hier aus
            ;anschließend die werte für Spieler1 setzen
            ;stein_frames = 1 und Spieler = 1
            If Spieler = 2 Then
              s\stein_frames = 2
              stein_frames = 1
              Spieler = 1
            EndIf
          EndIf
        EndIf
      EndIf
    EndIf
  Next

  ;Anzeigen welcher Stein Dran ist
  DrawImage stein,250,50,stein_frames

  Flip
Until KeyHit(1)

End


und ich habe hier im Forum nix gefunden wie man sowas Prüft Crying or Very sad
ich danke euch schonmal für die Hilfe Wink

Gruss Andreas
 

JanK

BeitragFr, Jun 09, 2006 1:20
Antworten mit Zitat
Benutzer-Profile anzeigen
Vielleicht könntest du eine Variable benutzen, die immer um eins erhöht wird wenn
ein Kreis gemalt wird. Wenn das nächste Type auch ein kreis ist, dann wird die Variable wieder erhöht. Wenn die Variable = 3 dann sind drei nebeneinander.
Natürlich muss man die Var auch wieder auf 0 setzen wenn kein Kreis kommt.

O man...ich hoff des is halbwegs verständlich(01:20) Wink
Ich habe keine Zeit, mich zu beeilen.
The Pollux Conflict || The Pollux Renegades || Lipstick-live.de

D2006

Administrator

BeitragFr, Jun 09, 2006 1:24
Antworten mit Zitat
Benutzer-Profile anzeigen
Also das ist imho ja mal ein erstklassiger Fall, wo man ein Dim Feld den Types vorziehen sollte.

Einfach das Spielfeld als ein Dimfeld:
BlitzBasic: [AUSKLAPPEN]
Dim feld%(2,2)


und dort schreibst du immer das "Frame" rein bzw. allgemein die Spieler Nummer. Ergo: 0 ist leer, 1 ist Spieler 1, 2 ist Spieler 2.

Das Überprüfen ist durch den Direktzugriff nun auch nur noch Schreibarbeit:
- erst mit 2 verschachtelten For Schleifen die drei Zeilen durchgehen
- dann analog die drei spalten von oben nach unten
- zum Schluss die zwei Diagonalen, die es gibt

Wobei der eigentliche Vorgang der Prüfung dann zum Beispiel folgendermaßen gehen könnte:
Du bildest jeweils immer das Produkt der Inhalte aller drei Felder!
-> kommt null raus, war mindestens ein Feld leer -> kein Gewinn
-> kommt eins raus -> Spieler eins gewinnt (1*1*1 = 1, wohingegen 1*2*1 =2 oder 2*2*1 = 4)
-> kommt acht raus -> Spieler zwei gewinnt (2*2*2 = 8)

Das ganze hat natürlich noch Optimierungspotential.

MfG
D2006
Intel Core i5 2500 | 16 GB DDR3 RAM dualchannel | ATI Radeon HD6870 (1024 MB RAM) | Windows 7 Home Premium
Intel Core 2 Duo 2.4 GHz | 2 GB DDR3 RAM dualchannel | Nvidia GeForce 9400M (256 MB shared RAM) | Mac OS X Snow Leopard
Intel Pentium Dual-Core 2.4 GHz | 3 GB DDR2 RAM dualchannel | ATI Radeon HD3850 (1024 MB RAM) | Windows 7 Home Premium
Chaos Interactive :: GoBang :: BB-Poker :: ChaosBreaker :: Hexagon :: ChaosRacer 2
 

bruce85

BeitragFr, Jun 09, 2006 1:29
Antworten mit Zitat
Benutzer-Profile anzeigen
ich danke dir, aber man kann des net einfach mit Variablen machen, wenn man z.B. so macht:

[0] [] [X]
[] [X] [0]
[] [0] [X]

da sind auch 3 Kreise aber net nebeneinander, so hat ja der spieler dann gewonnen wenn nur 3 kreise drauf sind, man muss es irgendwie Prüfen ohne Extra Variablen zu benutzen die die Kreise ählen, weil des nichts wird, ich danke dir Trotzdem für deine Hilfe.

danke schonmal auf weitere hilfen Wink

Gruss Andreas
 

bruce85

BeitragFr, Jun 09, 2006 1:33
Antworten mit Zitat
Benutzer-Profile anzeigen
ich danke dir D2006,
ich benutze Types weil ich mich damit am besten auskenne, aber wenn Dim Felder besser sind dann werde ich die natürlich benutzen, ich danke dir für die Hilfe, ich werds dann mal ausprobieren Very Happy

Gruss Andreas
 

bruce85

BeitragMi, Jun 14, 2006 22:27
Antworten mit Zitat
Benutzer-Profile anzeigen
hallo nochmal,
ich möchte das lieber mit types machen, wie kann man denn Prüfen ob sich 3 gleiche nebeneinander befinden?

Gruss Andreas

PowerProgrammer

BeitragMi, Jun 14, 2006 22:37
Antworten mit Zitat
Benutzer-Profile anzeigen
An deiner Stelle würde ich es doch mit Dim-Feldern machen, da sie in diesem mehr Leistungsschonend sind und dazu noch einfacher.

Aber trotzdem:
Ich denke, ich würde 3 einfache Routinen entwickeln: Horizontal, Diagonal, Vertikal. Und diese zu programmieren ist doch nicht schwer...

Wer so kompliziertes wie Types (ja, ich hab mich am Anfang damit (auch) schwer getan) in einem so simplen Code benutzt, sollte daran nicht scheitern...
www.xairro.com Alles für Webmaster und Programmierer! Es gibt mehr als bloß einen Counter!
 

bruce85

BeitragMi, Jun 14, 2006 23:01
Antworten mit Zitat
Benutzer-Profile anzeigen
ich danke dir, ich habe das jetzt mal mit Dim felder gemacht, aber wie kann ich die einzelnen Felder ansprechen?

habs mal so probiert:

Code: [AUSKLAPPEN]
Graphics 350,250,16,2
SetBuffer BackBuffer()

AppTitle "Tic Tac Toe"

Global backround = LoadImage("backround.png")
MaskImage backround,255,0,255

;Feld Laden
Global stein = LoadAnimImage("stein.png",50,50,0,3)
MaskImage stein,255,0,255

Dim feld(3,3)

;Die Daten für die Felder
;0=Lerres Feld, 1=Kreuz und 2=Kreis
Data 0,0,0
Data 0,0,0
Data 0,0,0

;Felder lesen
For y=1 To 3
  For x=1 To 3
    Read feld(x,y)
  Next
Next

Repeat
  ClsColor 127,127,127
  Cls

  DrawImage backround,50,50

  ;Feld malen
  For y=1 To 3
    For x=1 To 3
      DrawImage stein,x*51,y*51,feld(x,y)
    Next
  Next

  If feld(x,y) = 0 Then
    If RectsOverlap(MouseX(),MouseY(),1,1,x*51,y*51,50,50) Then
     
    EndIf
  EndIf

  Flip
Until KeyHit(1)

End


danke dir schonmal Wink

Gruss Andreas

Thorsten

BeitragMi, Jun 14, 2006 23:31
Antworten mit Zitat
Benutzer-Profile anzeigen
Zitat:

Data 0,0,0
Data 0,0,0
Data 0,0,0

;Felder lesen
For y=1 To 3
For x=1 To 3
Read feld(x,y)
Next
Next


das ist wohl eher unnötig da beim tictactoe am anfang ja sowieso kein spielstein auf dem feld ist.

die felder kannst du einfach mit
Code: [AUSKLAPPEN]
feld(x,y)

abfragen

werte kannst du auch einfach so speichern :

Code: [AUSKLAPPEN]
feld(x,y) = 2


cya,
BlindGuy

PowerProgrammer

BeitragDo, Jun 15, 2006 10:07
Antworten mit Zitat
Benutzer-Profile anzeigen
Genau.

Du kannst aber auch "Dim feld(2,2)" schreiben, da 0 auch ein Feld ist...

Hier ist mal ein sehr unoptimierter Code. Den solltest du ganz stark verkürzen...
In den 6 Variablen werden die Felder zurückgegeben, die zum Gewinn geführt haben...
Code: [AUSKLAPPEN]

; Hier werden die Felder angegeben, die zum Gewinn geführt haben...
Global GewinnerFeld_1_X, GewinnerFeld_1_Y
Global GewinnerFeld_2_X, GewinnerFeld_2_Y
Global GewinnerFeld_3_X, GewinnerFeld_3_Y


; Diese Funktion liefert eine Null, oder eine 1 oder eine 2 zurück...
Function Check%()
   For I = 1 To 3
      ;Horizontal
      If feld(1,I) = 1 And feld(2,I) = 1 And feld(3,I) = 1 Then
         GewinnerFeld_1_X = 1
         GewinnerFeld_1_Y = I
         GewinnerFeld_2_X = 2
         GewinnerFeld_2_Y = I
         GewinnerFeld_3_X = 3
         GewinnerFeld_3_Y = I
         Return 1
      ElseIf feld(1,I) = 2 And feld(2,I) = 2 And feld(3,I) = 2 Then
         GewinnerFeld_1_X = 1
         GewinnerFeld_1_Y = I
         GewinnerFeld_2_X = 2
         GewinnerFeld_2_Y = I
         GewinnerFeld_3_X = 3
         GewinnerFeld_3_Y = I
         Return 2
      EndIf
      ;Vertikal
      If feld(I,1) = 1 And feld(I,2) = 1 And feld(I,3) = 1 Then
         GewinnerFeld_1_X = I
         GewinnerFeld_1_Y = 1
         GewinnerFeld_2_X = I
         GewinnerFeld_2_Y = 2
         GewinnerFeld_3_X = I
         GewinnerFeld_3_Y = 3
         Return 1
      ElseIf feld(I,1) = 2 And feld(I,2) = 2 And feld(I,3) = 2 Then
         GewinnerFeld_1_X = I
         GewinnerFeld_1_Y = 1
         GewinnerFeld_2_X = I
         GewinnerFeld_2_Y = 2
         GewinnerFeld_3_X = I
         GewinnerFeld_3_Y = 3
         Return 2
      EndIf
   Next
   ;Diagonal
   If feld(1,1) = 1 And feld(2,2) = 1 And feld(3,3) = 1 Then
      GewinnerFeld_1_X = 1
      GewinnerFeld_1_Y = 1
      GewinnerFeld_2_X = 2
      GewinnerFeld_2_Y = 2
      GewinnerFeld_3_X = 3
      GewinnerFeld_3_Y = 3
      Return 1
   ElseIf feld(1,1) = 2 And feld(2,2) = 2 And feld(3,3) = 2 Then
      GewinnerFeld_1_X = 1
      GewinnerFeld_1_Y = 1
      GewinnerFeld_2_X = 2
      GewinnerFeld_2_Y = 2
      GewinnerFeld_3_X = 3
      GewinnerFeld_3_Y = 3
      Return 2
   EndIf
   If feld(1,3) = 1 And feld(2,2) = 1 And feld(3,1) = 1 Then
      GewinnerFeld_1_X = 1
      GewinnerFeld_1_Y = 3
      GewinnerFeld_2_X = 2
      GewinnerFeld_2_Y = 2
      GewinnerFeld_3_X = 3
      GewinnerFeld_3_Y = 1
      Return 1
   ElseIf feld(1,3) = 2 And feld(2,2) = 2 And feld(3,1) = 2 Then
      GewinnerFeld_1_X = 1
      GewinnerFeld_1_Y = 3
      GewinnerFeld_2_X = 2
      GewinnerFeld_2_Y = 2
      GewinnerFeld_3_X = 3
      GewinnerFeld_3_Y = 1
      Return 2
   EndIf
   ;Nichts :-(
   Return 0
End Function

www.xairro.com Alles für Webmaster und Programmierer! Es gibt mehr als bloß einen Counter!
 

bruce85

BeitragDo, Jun 15, 2006 22:56
Antworten mit Zitat
Benutzer-Profile anzeigen
cool danke das du dir die mühe gegeben hast das zu posten Very Happy

aber wie kann ich die einzelnen Felder ansprechen?
wen icz.B. auf FeldX=2 und FeldY=1 klicke das dann auf dieser Position umgewechselt wird in Data Nr. 1 oder so?
geht das mit RectsOverlap?

danke dir schonmal Wink

Gruss Andreas

PowerProgrammer

BeitragFr, Jun 16, 2006 6:42
Antworten mit Zitat
Benutzer-Profile anzeigen
Ich bin mir nicht ganz sicher, was du meins t. Aber ich denke, du meinst die Abfrage der Felder.

Code: [AUSKLAPPEN]
;Abfrage
For I = 1 To 3
   For J = 1 To 3
      ; Hoffe, die Kollisionsabfrage stimmt
      If RectsOverlap(MouseX(),MouseY(),1,1,J*51,I*51,50,50) And MouseHit(1) Then
         feld(J,I) = Spieler ; der dran ist
      EndIf
   Next
Next


Jedes Feld eines Dim-Feldes (z.B. feld(2,3)) kannst du wie Variablen ansprechen - nur eben, das die "Variablen" dann ein kleines Klammer-Anhängsel haben...
www.xairro.com Alles für Webmaster und Programmierer! Es gibt mehr als bloß einen Counter!

Neue Antwort erstellen


Übersicht BlitzBasic Beginners-Corner

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group