Delphi Hangman / Galgenraten / Galgenmännchen

Selvos

Lt. Junior Grade
Registriert
Jan. 2009
Beiträge
303
Hallo liebe Community,
Ich habe die Aufgabe ein Galgenmännchenspiel zu programmieren, vielleicht könnt ihr mir helfen ?
Die Funktion das er die Fehlversuche zählt funktioniert nicht richtig , deswegen kann er auch das Galgenmännchen nicht zeichen, glaube ich. Genauso weiß ich nicht warum das Programm zuviele Striche zeichnet wenn man auf Starten drückt. Außerdem ersetzt er die Striche nicht mit den Buchstaben wenn man einen richtigen eingegeben hat. Könntet ihr mir bei der Fehlersuche helfen ? Vielen Dank !

Code:
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Turtle;

type
  TForm1 = class(TForm)
    Turtle1: TTurtle;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Edit1: TEdit;
    Edit2: TEdit;
    Button1: TButton;
    Button2: TButton;
    Label4: TLabel;
    Button3: TButton;
    Label5: TLabel;
    Label6: TLabel;
    Label7: TLabel;
    Button4: TButton;
    Button5: TButton;
    Label8: TLabel;
    Label9: TLabel;
    Label10: TLabel;
    procedure Button1Click(Sender: TObject);
    procedure Button3Click(Sender: TObject);
    procedure Button4Click(Sender: TObject);
    procedure Button5Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
  private
    { Private-Deklarationen }
  public
    { Public-Deklarationen }
  end;

var
  Form1: TForm1;
  a,c : integer;
  b,z,striche : string;


implementation

uses Unit2, Unit3, Unit4;

{$R *.dfm}
procedure Zufall( var label5:Tlabel);
 begin

        Randomize;
        a:=random(3);
        if a = 0 then b:='Lolip';
        if a = 1 then b:='Testbetrieb';
        if a = 2 then b:='Uhr' ;

        z:=uppercase(b);
        c:=Length(z);
        Label5.Caption:=IntToStr(c);
end;

procedure BStriche(var label10:Tlabel);
var p : integer;
begin
striche:='';
for p:=1 to c do
begin
    striche:=striche+'- ';
end;
Label10.Caption:=striche;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
i,fehler : integer ;
temp,intern : string;
e: char;
drin : boolean;
begin
Edit1.text:=Uppercase(Edit1.text);
if Edit1.Text <> '' then e:=Edit1.Text[1];
Label9.Caption:=Label9.Caption+e+' ';
temp:= Label10.Caption;
drin:= false;

for i := 1 to c do
        if z[i]= e then
                if intern[i] = e then drin :=false
                else begin
                intern[i] := e;
                temp[i*2] := e;
                drin:= true;
                end;

Edit1.Text:='';
edit1.SetFocus;




if not drin then begin
        inc(fehler);
        label7.Caption:=IntTostr(fehler);

        if fehler=1 then form1.Turtle1.cs;form1.Turtle1.ht;
form1.Turtle1.pu;form1.Turtle1.fd(10);form1.Turtle1.lt(90);form1.Turtle1.fd(120);
form1.Turtle1.pd;form1.Turtle1.fd(220);form1.Turtle1.pu;      //Grundplatte
        if fehler=2   then
form1.Turtle1.rt(180);form1.Turtle1.fd(110);form1.Turtle1.lt(90);form1.Turtle1.pd;
form1.Turtle1.fd(300);  // Ständer hoch
        if fehler=3    then
form1.Turtle1.rt(90);form1.Turtle1.fd(140);   //ständer schräg
        if fehler=4    then
form1.Turtle1.rt(90);form1.Turtle1.fd(50);       // seil runter
        if fehler=5     then
form1.Turtle1.lt(90);
 for i:=1 to 64 do
  begin
        form1.Turtle1.rt(360/64);
        form1.Turtle1.fd(2.5);
  end;
form1.Turtle1.pu;
  for i:=1 to 32 do
  begin
        form1.Turtle1.rt(360/64);
        form1.Turtle1.fd(2.5);
  end;                                 // Kopf
        if fehler=6  then
form1.Turtle1.lt(90);form1.Turtle1.pd;form1.Turtle1.fd(70);    //Rumpf
        if fehler=7   then
form1.Turtle1.lt(30); form1.Turtle1.fd(60);  // linkes bein
        if fehler=8    then
form1.Turtle1.pu;form1.Turtle1.lt(180);form1.Turtle1.fd(60);form1.Turtle1.lt(120);
form1.Turtle1.pd;form1.Turtle1.fd(60); //rechtes bein
        if fehler=9   then
form1.Turtle1.pu;form1.Turtle1.lt(180);form1.Turtle1.fd(60);form1.Turtle1.lt(30);
form1.Turtle1.fd(45);form1.Turtle1.rt(45);form1.Turtle1.pd;
form1.Turtle1.fd(65); // linker Arm
        if fehler=10  then
form1.Turtle1.lt(180);form1.Turtle1.fd(65);form1.Turtle1.rt(90);
form1.Turtle1.fd(65); //rechter arm
        if fehler=10 then
        begin
        form4.showmodal;
        end;


end;
end;
procedure TForm1.Button3Click(Sender: TObject);
begin
form2.showmodal;
end;


procedure TForm1.Button4Click(Sender: TObject);
begin
close;
end;

procedure TForm1.Button5Click(Sender: TObject);
begin
Edit1.Text:='';Label9.caption:='';
Label10.Caption:='';
Zufall(label5);
Bstriche(label10);
button1.Visible:=True;
button2.Visible:=True;
edit1.Visible:=True;
edit2.Visible:=True;
Edit1.MaxLength := 1;
Edit1.setfocus;


end;

procedure TForm1.Button2Click(Sender: TObject);
var u,w : string ;
begin
u:=Edit2.Text;

w:=Uppercase(u);
if w=z then form3.showmodal;
end;
end.
 

Anhänge

  • Galgenmännchen.rar
    180,1 KB · Aufrufe: 446
Zuletzt bearbeitet: (Variable initialisieren)
Zum Thema "zuviele Striche" würde ich schnell vermuten, dadurch, dass du die Variable "Striche" zwar als String deklarierst, ihr aber keinen Anfangswert (in dem Fall 0 Zeichen, also "") zuweist, wird die Variable selbst einfach so irgendwo im Speicher reingelegt. Ergebnis: Die Variable nimmt automatisch den Wert der Speicherzelle an und hat somit bereits eine Zeichenkette, auf die dann pro Buchstabe noch ein "_" dazukommt. Mein Prof hat mal gemeint, eine Variable zu initialisieren, ohne ihr einen Wert zuzuordnen ist zwar programmtechnisch machbar, aber

a) unsauber und
b) unsicher.

Vieleicht hilfts ja.

Eventuell kannst du ja auch einfach das Lösungswort in einen 2. String kopieren und dann darin alle Buchstaben durch "_" ersetzen. Somit hast du garantiert die korrekte Länge, anstatt dir einen neuen String zu erschaffen.
 
Danke, das hat geholfen . Jetzt brauch ich nur noch eine Hilfe für die anderen Probleme :D
 
was ist TTurtle für eine klasse?
die wird in keiner unit aus der .rar datei deklariert?!
 
Turtle ist eine didaktische Komponente für Delphi mit der man zeichnen kann, da liegt aber kaum der Fehler.
 
Hab mich eben nochmal durch den Quelltext gefuchst. Bei der Fehlerzählung hast du auch keinen Anfangswert deklariert. Versuch einfach mal, wenn du die Fehleranzahl-Variable initialisierst, diese erstmal auf 0 zu setzen, damit die Zählung auch korrekt losgeht. Wie schon gesagt, es ist immer hilfreich, eine Variable mit einem festen Anfangswert zu versehen, damit keine unkontrollierbaren Werte darin stehen.

Zu der Thematik "Ersetze korrekte Buchstaben in Striche":

Wenn du die Variante verwendet haben solltest, mit der du zuerst den Original-String kopierst, dann sollte durch einen einfachen Vergleich der Strings miteinander auch die richtige Position ersetzt werden.
 
Ich hab dir das Programm mal durchgeschaut und das meiste gefixt. Der Kopf zeichnet sich aber immer noch nicht und ich mag nicht deine Turtle-Grafik durchschauen.

Dafür hab ich dir eine zusätzliche Unit mit der Klasse THangman hinzugefügt, die sich um die nicht grafische Spiellogik kümmert.

Code:
unit hangman;

interface

type
  THangman = class
  private
    fSuchwort: string;
    fBuchstaben: string;
    function getFehlversuche: Integer;
    function GetHinweisWort: string;
  public
    constructor Create;
    destructor Destroy;
    function VersucheBuchstabe(C:Char):Boolean;
    function VersucheWort(Wort:string):Boolean;
    procedure Play(Suchwort:string);
  published
    property Fehlversuche: Integer read getFehlversuche;
    property HinweisWort: string read GetHinweisWort;
    property Buchstaben:string read fBuchstaben;
  end;

implementation

{ THangman }

constructor THangman.Create;
begin
  inherited Create;
  fSuchwort := '';
  fBuchstaben := '';
end;

destructor THangman.Destroy;
begin
  fSuchwort := '';
  fBuchstaben := '';
  inherited Destroy;
end;

function THangman.getFehlversuche: Integer;
var
  I: Integer;
begin
  Result := 0;
  for I := 0 to Length(fBuchstaben) - 1 do
  begin
    if Pos(fBuchstaben[I],fSuchwort) = 0 then
    begin
      inc(Result);
    end;
  end;
end;

function THangman.GetHinweisWort: string;
var
  I: Integer;
begin
  SetLength(Result,Length(fSuchwort));
  for I := 1 to Length(Result) do
  begin
    if Pos(fSuchwort[I],fBuchstaben) = 0 then
    begin
      Result[I] := '-';
    end
    else
    begin
      Result[I] := fSuchwort[I];
    end;
  end;
end;

procedure THangman.Play(Suchwort: string);
begin
  fSuchwort := Suchwort;
  fBuchstaben := '';
end;

function THangman.VersucheBuchstabe(C: Char): Boolean;
var
  I: Integer;
begin
  if Pos(C,fBuchstaben) = 0 then
  begin
    fBuchstaben := fBuchstaben + C;
    Result := Pos(C,fSuchwort) > 0;
  end;
end;

function THangman.VersucheWort(Wort: string): Boolean;
begin
  Result := Wort = fSuchwort;
end;

end.

Und deine Unit1 korrigiert:
Code:
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Turtle, hangman;

type
  TForm1 = class(TForm)
    Turtle1: TTurtle;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Edit1: TEdit;
    Edit2: TEdit;
    Button1: TButton;
    Button2: TButton;
    Label4: TLabel;
    Button3: TButton;
    Label5: TLabel;
    Label6: TLabel;
    Label7: TLabel;
    Button4: TButton;
    Button5: TButton;
    Label8: TLabel;
    Label9: TLabel;
    Label10: TLabel;
    procedure Button1Click(Sender: TObject);
    procedure Button3Click(Sender: TObject);
    procedure Button4Click(Sender: TObject);
    procedure Button5Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
  private
    { Private-Deklarationen }
    Hangman:THangman;
  public
    { Public-Deklarationen }
  end;

var
  Form1: TForm1;

implementation

uses Unit2, Unit3, Unit4;

{$R *.dfm}
function ZufallsWort:string;
var
  a:integer;
  b: string;
begin
  Randomize;
  a:=random(3);
  if a = 0 then b:='Lolip';
  if a = 1 then b:='Testbetrieb';
  if a = 2 then b:='Uhr' ;
  Result:=uppercase(b);
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  i,fehler : integer ;
  temp,intern : string;
  Buchstabe: char;
  Erfolg : boolean;
begin
  Buchstabe := UpCase(Edit1.Text[1]);
  Edit1.Text:='';
  edit1.SetFocus;
  Erfolg := Hangman.VersucheBuchstabe(Buchstabe);
  Label9.Caption := Hangman.Buchstaben;
  Label10.Caption := Hangman.Hinweiswort;
  if not Erfolg then
  begin
    fehler := Hangman.Fehlversuche;
    label7.Caption:=IntTostr(fehler);
    if fehler=1 then
    begin
      form1.Turtle1.cs;
      form1.Turtle1.ht;
      form1.Turtle1.pu;
      form1.Turtle1.fd(10);
      form1.Turtle1.lt(90);
      form1.Turtle1.fd(120);
      form1.Turtle1.pd;
      form1.Turtle1.fd(220);
      form1.Turtle1.pu;      //Grundplatte
    end;
    if fehler=2 then
    begin
      form1.Turtle1.rt(180);
      form1.Turtle1.fd(110);
      form1.Turtle1.lt(90);
      form1.Turtle1.pd;
      form1.Turtle1.fd(300);  // Ständer hoch
    end;
    if fehler=3 then
    begin
      form1.Turtle1.rt(90);
      form1.Turtle1.fd(140);   //ständer schräg
     end;
    if fehler=4 then
    begin
      form1.Turtle1.rt(90);
      form1.Turtle1.fd(50);       // seil runter
    end;
    if fehler=5 then
    begin
      form1.Turtle1.lt(90);
      for i:=1 to 64 do
      begin
        form1.Turtle1.rt(360/64);
        form1.Turtle1.fd(2.5);
        form1.Turtle1.pu;
      end;
      for i:=1 to 32 do
      begin
        form1.Turtle1.rt(360/64);
        form1.Turtle1.fd(2.5);
      end;                                  // Kopf
    end;
    if fehler=6 then
    begin
      form1.Turtle1.lt(90);
      form1.Turtle1.pd;
      form1.Turtle1.fd(70);    //Rumpf
    end;
    if fehler=7   then
    begin
      form1.Turtle1.lt(30);
      form1.Turtle1.fd(60);  // linkes bein
    end;
    if fehler=8 then
    begin
      form1.Turtle1.pu;
      form1.Turtle1.lt(180);
      form1.Turtle1.fd(60);
      form1.Turtle1.lt(120);
      form1.Turtle1.pd;
      form1.Turtle1.fd(60); //rechtes bein
    end;
    if fehler=9 then
    begin
      form1.Turtle1.pu;
      form1.Turtle1.lt(180);
      form1.Turtle1.fd(60);
      form1.Turtle1.lt(30);
      form1.Turtle1.fd(45);
      form1.Turtle1.rt(45);
      form1.Turtle1.pd;
      form1.Turtle1.fd(65); // linker Arm
    end;
    if fehler=10 then
    begin
      form1.Turtle1.lt(180);
      form1.Turtle1.fd(65);
      form1.Turtle1.rt(90);
      form1.Turtle1.fd(65); //rechter arm
    end;
    if fehler=10 then
    begin
      form4.showmodal;
    end;
  end;
end;
procedure TForm1.Button3Click(Sender: TObject);
begin
  form2.showmodal;
end;


procedure TForm1.Button4Click(Sender: TObject);
begin
  close;
end;

procedure TForm1.Button5Click(Sender: TObject);
var
  Wort : string;
begin
  Edit1.Text:='';
  Wort := ZufallsWort;
  button1.Visible:=True;
  button2.Visible:=True;
  edit1.Visible:=True;
  edit2.Visible:=True;
  Edit1.MaxLength := 1;
  Edit1.setfocus;
  FreeAndNil(Hangman);
  Hangman := THangman.Create;
  Hangman.Play(UpperCase(Wort));
  Label9.Caption := Hangman.Buchstaben;
  Label10.Caption := Hangman.Hinweiswort;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
  if Hangman.VersucheWort(UpperCase(Edit2.Text)) then
  begin
    form3.showmodal;
  end;
end;

end.

Für das nächste mal:
- Begin und End sind deine besten Freunde.
- Variablen solltest du innerhalb der Methode oder als Attribute der (Fenster-)Klasse festlegen, aber bitte nicht global in der Unit.
- Quelltextformatierung ist was tolles.

Deine Zeichenroutine hat nicht funktioniert, weil du kein Begin-End um die Anweisungsblöcke gesetzt hast.
Das Hochzählen der Fehler hat nicht funktioniert, weil "fehler" eine lokale variable war, die bei jedem Durchlauf der Methode wieder auf 0 zu zählen angefangen hat.
 
Ich danke dir vielmals. Ich schaffe es aber immernoch nicht das Programm zum laufen zu bringen, ich ersetzte meine Unit1 mit deiner und erstelle eine neue Unit mit dem Namen 'hangman' , doch leider scheint er das nicht wirklich an zu erkennen. Ich danke dir auch für die Tipps , ich bin noch Anfänger wie man merkt.^^
 
Du musst die Unit "hangman" dem Projekt hinzufügen. Wenn das nicht hilft, Poste mir mal bitte Screenshot und Fehlermeldung.

Welche Delphi-Version verwendest du?
 
Doch das hat geholfen, ich habe wahrscheinlich vorhin einen Fehler beim kopieren gemacht weil ich in Eile war , jetzt funktioniert ALLES wunderbar, ich danke dir wirklich tausendmal für deine Hilfe !
 

Ähnliche Themen

B
Antworten
6
Aufrufe
1.053
Bizepsbenny
B
Zurück
Oben