|
![]() |
|
Registriert seit: 30. Dez 2002 Ort: Brandshagen 1.819 Beiträge Delphi 2007 Professional |
#1
Hi,
ich hab mal die Klassen für die Spieler, Spielerliste, Spiele und Spielliste fertig gestellt. Leider hab ich das System für den Eintrag eines Spielers in ein neues Spiel noch nicht ganz durchschaut. Für die Gewinner ist das ja recht einfach. Bei den Verlierern hab ich da so meine Probleme. Ich pack hier mal die Procedure rein.
Delphi-Quellcode:
Hier noch einige Bemerkungen zum Ablauf. Wird in einem Spiel ein Spielstand (oder eine andere Eigenschaft) geändert so ruft das Spiel die Procedure ChangePlay seiner PlayList auf und übergibt sich selbst sowie den Namen der Eigenschaft an die Procedure.
procedure TPlayList.ChangePlay(APlayClass: TPlayClass; AProperty : String);
var AWinner, ALooser : TPlayerClass; procedure PlayerinGame(APlayer : TPlayerClass; AOldPlay : TPlayClass; winning : Boolean); var NewPlay : TPlayClass; begin if winning then begin // Spieler ist Gewinner des alten Spieles case ORD(AOldPlay.FGame) of ORD('R') : begin // Gewinner der ersten Runde if Odd(AOldPlay.Number) then begin NewPlay := GetPlay('G', 1, (AOldPlay.Number+1) div 2); if Assigned(NewPlay) then NewPlay.FPlayer1 := APlayer; end else begin NewPlay := GetPlay('G', 1, (AOldPlay.Number) div 2); if Assigned(NewPlay) then NewPlay.FPlayer2 := APlayer; end; end; ORD('G') : begin if Odd(AOldPlay.Number) then begin NewPlay := GetPlay('G', AOldPlay.FRound+1, (AOldPlay.FNumber+1) div 2); if Assigned(NewPlay) then begin NewPlay.FPlayer1 := APlayer; end else begin // das war das letzte Gewinnerspiel, ab ins Filale NewPlay := GetPlay('F', 0, 0); if Assigned(NewPlay) then NewPlay.Player1 := APlayer; end; end else begin NewPlay := GetPlay('G', AOldPlay.FRound+1, (AOldPlay.FNumber) div 2); if Assigned(NewPlay) then begin NewPlay.FPlayer2 := APlayer; end else begin // das war das letzte Gewinnerspiel, ab ins Filale NewPlay := GetPlay('F', 0, 0); if Assigned(NewPlay) then NewPlay.Player1 := APlayer; end; end; end; ORD('V') : begin NewPlay := GetPlay('V', AOldPlay.Round + 1, 1); if Assigned(NewPlay) then begin NewPlay.FPlayer1 := APlayer; end else begin // das war das letzte Gewinnerspiel, ab ins Filale NewPlay := GetPlay('F', 0, 0); if Assigned(NewPlay) then NewPlay.Player2 := APlayer; end; end; end; end else begin // Spieler ist Verlierer des alten Spieles case ORD(AOldPlay.FGame) of ORD('R') : begin // Gewinner der ersten Runde if Odd(AOldPlay.Number) then begin NewPlay := GetPlay('V', 1, (AOldPlay.Number+1) div 2); if Assigned(NewPlay) then NewPlay.FPlayer1 := APlayer; end else begin NewPlay := GetPlay('V', 1, (AOldPlay.Number) div 2); if Assigned(NewPlay) then NewPlay.FPlayer2 := APlayer; end; end; ORD('G') : begin // jo, da hab ich noch kein System entdeckt ??????????? end; ORD('V') : begin // das wars dann, kein weiteres Spiel :-( // oder doch? :-) hab ich das System aber auch noch nicht durchschaut end; end; end; end; begin // ein Spieler ist ein Freilos? if ((AProperty = 'Player1') or (AProperty = 'Player2')) and (Assigned(APlayClass.Player1) and Assigned(APlayClass.Player2)) and ((APlayClass.Player1.FPlayerType = pt_Looser) or (APlayClass.Player2.FPlayerType = pt_Looser)) then begin if APlayClass.Player1.FPlayerType = pt_Looser then begin // Player2 hat gewonnen AWinner := APlayClass.FPlayer2; ALooser := APlayClass.FPlayer1; end else begin // Player1 hat gewonnen AWinner := APlayClass.Player1; ALooser := APlayClass.Player2; end; // neues Spiel für Gewinner ermitteln PlayerinGame(AWinner, APlayClass, True); // neues Spiel für Verlierer ermitteln PlayerinGame(ALooser, APlayClass, False); // Counter der gespielten Spiele der Spieler erhöhen AWinner.PlayCount := AWinner.PlayCount + 1; ALooser.PlayCount := ALooser.PlayCount + 1; // aktuelle Platzierung der Spieler setzen AWinner.Position := FPlayerList.Count - AWinner.PlayCount; ALooser.Position := FPlayerList.Count - ALooser.PlayCount - 1; // Spielstatus auf beendet APlayClass.Status := ps_finish; Exit; end; // der Spielstand hat sich geändert if AProperty = 'PlayResult' then begin if (APlayClass.FPlayResult.Player1 <> 0) or (APlayClass.FPlayResult.Player2 <> 0) then begin // es gibt einen Spielstand <> 0 if APlayClass.FPlayResult.Player1 > APlayClass.PlayResult.Player2 then begin // Player1 hat gewonnen AWinner := APlayClass.Player1; ALooser := APlayClass.Player2; end else begin // Player2 hat gewonnen AWinner := APlayClass.Player2; ALooser := APlayClass.Player1; end; // neues Spiel für Gewinner ermitteln PlayerinGame(AWinner, APlayClass, True); // neues Spiel für Verlierer ermitteln PlayerinGame(ALooser, APlayClass, False); // Counter der gespielten Spiele der Spieler erhöhen AWinner.PlayCount := AWinner.PlayCount + 1; ALooser.PlayCount := ALooser.PlayCount + 1; // aktuelle Platzierung der Spieler setzen AWinner.Position := FPlayerList.Count - AWinner.PlayCount; ALooser.Position := FPlayerList.Count - ALooser.PlayCount - 1; // Spielstatus auf beendet APlayClass.Status := ps_finish; end; end; end; Die Procedure der PlayList macht jetzt folgendes. Erstens wird geschaut, ob der geänderte Parameter des Spiels der Spielstand oder der Typ des Spielers ist (Freilos bei Spieler). Ist ein gültiger Spielstand eingetragen, so wird der Gewinner und Verlierer des Spiels ermittelt. Dann werden diese an die Procedure PlayerinGame übergeben. Diese erhält folgender Werte: APlayer = Spieler der in ein neues Spiel eingetragen werden soll AOldPlay = Spiel das gerade zu Ende gespielt wurde winning = gibt an, ob der Spieler der Gewinner oder Verlierer des Spieles ist. Nun prüft die Procedure erst mal, welches Spiel das gerade gespielte Spiel ist, um das neue Spiel zu ermitteln, in das der aktuelle Spieler jetzt eingetragen werden soll. Der erste Block der Abfrage für den Gewinner sollte eigentlich soweit ok sein. Keinen Plan hab ich noch für den zweiten Block, Eintrag des Verlierers. Das vorallem wenn er ein V- oder G-Spiel verloren hat. Da die Procedure eine eigene Methode der PlayList ist, wird hier auf eigene Hilfsfunktionen zugegriffen. Das ist z.B. die Funktion GetPlay. GetPlay sucht in der Liste nach einem Spiel mit der angegebenen Bezeichnung und gibt die Instanz dieses Spieles als Ergebnis zurück. Wurde kein Spiel mit dieser Bezeichnung gefunden, so liefert die Funktion nil. Das ergibt natürlich, dass in der Liste alle Spiele schon eingetragen sind. Erledigt wird das bei der Übergabe der Spielerliste an die PlayList. Dabei wird auf Basis der Anzahl der in der PlayerList eingetragenen Spieler der gesamte Spielplan automatisch erstellt und alle Spiele eingetragen. Das ist auch schon fertig und hat so keine großen Probleme bereitet. Hier mal diese Funktion zur Kontrolle:
Delphi-Quellcode:
Du brauchst die Methoden hier nicht rauskopieren. Ich hab die Unit mit den Klassen schon fertig und hänge sie hier bei einem der nächsten Beiträge mit ran, dann kannst du sie dir direkt downloaden.
procedure TPlayList.UpdatePlayCount;
var APlayerCount : Integer; Counter, CRound : Integer; procedure AddPlays(AGame : Char; ARound, ANumberCount : Integer); var BCounter : Integer; begin for BCounter := 1 to ANumberCount div 2 - 1 do begin if not Assigned(GetPlay(AGame, ARound, BCounter)) then begin // Spiel ist noch nicht angelegt Add(TPlayClass.Create(AGame, ARound, BCounter)); end; end; end; begin if not Assigned(FPlayerList) or (FPlayerList.Count = 0) then begin Clear; end else begin Clear; APlayerCount := FPlayerList.Count; // bei ungerade Anzahl von Spielern einen dazu if odd(APlayerCount) then inc(APlayerCount); // R-Spiele anlegen AddPlays('R', 1, APlayerCount div 2); // G-Spiele anlegen Counter := APlayerCount div 4; CRound := 1; while (Frac(Counter/2) = 0) do begin AddPlays('G', CRound, Counter); inc(CRound); Counter := Counter div 2; end; // V-Spiele anlegen Counter := APlayerCount div 4; CRound := 1; while (Frac(Counter/2) = 0) do begin AddPlays('V', CRound, Counter); inc(CRound); if not odd(CRound) then Counter := Counter div 2; end; // Finale anlegen Add(TPlayClass.Create('F', 0, 0)); end; end; Ja, somit müssen wir nur noch die kleinen Probleme mit der Spielzuordnung für die Verlierer lösen und das Datenmodell ist fertig. Dann können wir uns um den visuellen Teil kümmern. Dann bis die Tage, Gruß oki
42
|
![]() |
Ansicht |
![]() |
![]() |
![]() |
ForumregelnEs ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.
BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus. Trackbacks are an
Pingbacks are an
Refbacks are aus
|
|
Nützliche Links |
Heutige Beiträge |
Sitemap |
Suchen |
Code-Library |
Wer ist online |
Alle Foren als gelesen markieren |
Gehe zu... |
LinkBack |
![]() |
![]() |