Bűvös lámpák
Az itt látható játékprogramban az a
cél, hogy a megjelenő, kezdetben még nem látható (alvó) lámpák mindegyikét
felkapcsoljuk. A kapcsolgatást egérkattintással végezhetjük. Ha egy lámpára
kattintunk, akkor állapota megváltozik, de nem csak az övé, hanem minden
lapszomszédjának állapota is.
Kezdetben megadhatjuk, hogy a lámpák hány sorban és
hány oszlopban helyezkedjenek el. A sorok és oszlopok maximális száma 16.
A másik opció érdekesebb. Megadhatjuk,
hogy a lámpák milyen felületen helyezkedjenek el. Lehet egy síkbeli téglalapon,
vagy térben egy henger, vagy egy tórusz (úszógumi) felületén. Az utóbbiak a
megjelenítésben nem láthatók, a működésben viszont igen. Úgy kell elképzelni a
henger esetén, mintha az utolsó oszlop az első oszlop szomszédja lenne. Vagyis,
ha az első oszlopon kattintunk, akkor annak az utolsó oszlopban is lesz hatása.
A tórusznál pedig nemcsak az első oszlop és az utolsó oszlop szomszédos, hanem
az első sor és az utolsó sor is.
Ha minden lámpát sikerült felkapcsolni,
akkor a program írja ki: Game Over és ne engedje tovább a kapcsolgatást. A
programból lehessen bármikor kilépni és bármikor új játékot kezdeni, valamint
számolja, és írja ki a lépések számát a képernyőre.
A
program egy futási képe:
Ha sikerült felkapcsolni minden lámpát:
A program listája:
unit ULampak;
interface
uses
Windows, Messages, SysUtils, Variants, Classes,
Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, Grids;
type
TfmLampak = class(TForm)
btKilepes: TButton;
btStart: TButton;
lbLampak: TLabel;
rgFelulet: TRadioGroup;
lbSSz: TLabel;
lbOSz: TLabel;
edSSz: TEdit;
edOSz: TEdit;
Procedure Racs(BFx,BFy,Bx,By,Nx,Ny: Integer);
Procedure Kepre;
Function Vege: Boolean;
procedure btKilepesClick(Sender: TObject);
procedure edSSzChange(Sender: TObject);
procedure edOSzChange(Sender: TObject);
procedure btStartClick(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure FormClick(Sender: TObject);
procedure FormMouseMove(Sender: TObject; Shift: TShiftState; X,
Y: Integer);
procedure FormPaint(Sender: TObject);
procedure rgFeluletClick(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
Const Max=16;
D=32;
Dx=16;
Dy=16;
T=14;
var
fmLampak: TfmLampak;
Xk, Yk, Fx, Fy, Hx, Hy, Mx, My: Integer;
L: Array[0..Max+1,0..Max+1] Of Byte;
Felulet: Byte;
F: Array[1..3] Of String;
SSz, OSz: Byte;
N: Word;
VegeVan: Boolean;
implementation
{$R *.dfm}
procedure TfmLampak.btKilepesClick(Sender: TObject);
begin
Close;
end;
procedure TfmLampak.FormPaint(Sender: TObject);
begin
With Canvas Do
Begin
Pen.Color:= clBtnFace;
Rectangle(Xk-80,35,Xk+80,80);
With Font Do
Begin
Size:= 20;
Name:= 'Times New Roman';
Color:= clBlue;
End;
TextOut(Xk-40,40,F[Felulet]);
Pen.Color:= clBlack;
End;
end;
procedure TfmLampak.FormCreate(Sender: TObject);
begin
Xk:= ClientWidth Div 2;
Yk:= ClientHeight Div 2;
F[1]:= 'Téglalap';
F[2]:= 'Henger';
F[3]:= 'Tórusz';
Felulet:= 1;
N:= 0;
VegeVan:= False;
end;
procedure TfmLampak.rgFeluletClick(Sender: TObject);
begin
Felulet:= rgFelulet.ItemIndex+1;
FormPaint(Sender);
btStartClick(Sender);
end;
procedure TfmLampak.FormMouseMove(Sender: TObject; Shift: TShiftState; X,
Y: Integer);
begin
Mx:= X;
My:= Y;
If (Mx<Xk-(Fx-1)*D-1-Dx-T) Or (Mx>Xk+(Fx-1)*D+10+Dx+T) Or
(My<Yk-(Fy-1)*D-1-Dy-T) Or (My>Yk+(Fy-1)*D+10+Dy+T) Then
Cursor:= crDefault Else Cursor:= crCross;
end;
Procedure TfmLampak.Racs(BFx,BFy,Bx,By,Nx,Ny: Integer);
Var I, Sx,Sy: Integer;
Begin
If Nx*Ny=0 Then Exit;
Sx:= Bfx+Nx*(Bx+1);
Sy:= Bfy+Ny*(By+1);
With Canvas Do
Begin
Rectangle(BFx,Bfy,Sx,Sy);
I:= BFx+Bx+1; While I<Sx Do
Begin MoveTo(I,BFy); LineTo(I,Sy); Inc(I,Bx+1) End;
I:= BFy+By+1; While I<Sy Do
Begin MoveTo(BFx,I); LineTo(Sx,I); Inc(I,By+1) End;
End;
End;
procedure TfmLampak.edSSzChange(Sender: TObject);
begin
With edSSz Do
Begin
If Length(Text)>0 Then
If Not (Text[Length(Text)] In ['0'..'9']) Then Text:= '';
If Length(Text)>2 Then Text:= '';
End;
end;
procedure TfmLampak.edOSzChange(Sender: TObject);
begin
With edOSz Do
Begin
If Length(Text)>0 Then
If Not (Text[Length(Text)] In ['0'..'9']) Then Text:= '';
If Length(Text)>2 Then Text:= '';
End;
end;
procedure TfmLampak.btStartClick(Sender: TObject);
Var I, J: Word;
begin
SSz:= StrToInt(edSSz.Text);
If SSz>Max Then Begin SSz:= Max; edSSz.Text:= IntToStr(SSz) End;
OSz:= StrToInt(edOSz.Text);
If OSz>Max Then Begin OSz:= Max; edOSz.Text:= IntToStr(OSz) End;
Fx:= Max Div 2;
Fy:= Max Div 2;
With Canvas Do
Begin
Pen.Color:= clBtnFace;
Brush.Color:= clBtnFace;
Rectangle(Xk-(Fx+1)*D,Yk-(Fy+1)*D,Xk+(Fx+1)*D,Yk+(Fy+1)*D);
Pen.Color:= clBlack;
End;
Fx:= OSz Div 2;
Fy:= SSz Div 2;
Racs(Xk-Fx*D,Yk-Fy*D,D,D,OSz,SSz);
For I:= 0 To Max+1 Do For J:= 0 To Max+1 Do L[I,J]:= 0;
FormPaint(Sender);
N:= 0;
VegeVan:= False;
end;
Procedure TfmLampak.Kepre;
Var I, J: Word;
Begin
With Canvas Do
For I:= 1 To OSz Do For J:= 1 To SSz Do
Begin
Case L[I,J] Of
0: Begin
Pen.Color:= clBtnFace;
Brush.Color:= clBtnFace;
End;
1: Begin
Pen.Color:= clBlue;
Brush.Color:= clBlue;
End;
End;
Ellipse(Xk-(Fx-I)*D+I-Dx-T,Yk-(Fy-J)*D+J-Dy-T,
Xk-(Fx-I)*D+I-Dx+T,Yk-(Fy-J)*D+J-Dy+T);
Pen.Color:= clBtnFace;
Brush.Color:= clBtnFace;
Rectangle(Xk-30,2*Yk-80,Xk+30,2*Yk);
Pen.Color:= clBlue;
TextOut(Xk-20,2*Yk-80,IntToStr(N));
Pen.Color:= clBlack;
End;
End;
Function TfmLampak.Vege: Boolean;
Var I, J, S: Word;
Begin
S:= 0; Vege:= False; VegeVan:= False;
For I:= 1 To OSz Do For J:= 1 To SSz Do Inc(S,L[I,J]);
If S=OSz*SSz Then With Canvas Do
Begin
With Font Do
Begin
Size:= 40;
Name:= 'Times New Roman';
Color:= clRed;
End;
Brush.Color:= clWhite;
TextOut(Xk-130,Yk,' Game Over ');
Vege:= True; VegeVan:= True; N:= 0;
End;
End;
procedure TfmLampak.FormClick(Sender: TObject);
begin
If VegeVan Then Exit;
Hx:= (Mx-Xk+(Fx+1)*D-OSz Div 2) Div D;
Hy:= (My-Yk+(Fy+1)*D-SSz Div 2) Div D;
If (Hx<1) Or (Hx>OSz) Or (Hy<1) Or (Hy>SSz) Then Exit;
Inc(N);
L[Hx,Hy]:= 1-L[Hx,Hy];
L[Hx-1,Hy]:= 1-L[Hx-1,Hy];
L[Hx+1,Hy]:= 1-L[Hx+1,Hy];
L[Hx,Hy-1]:= 1-L[Hx,Hy-1];
L[Hx,Hy+1]:= 1-L[Hx,Hy+1];
If Felulet>1 Then
Begin
If Hx=1 Then L[OSz,Hy]:= 1-L[OSz,Hy];
If Hx=OSz Then L[1,Hy]:= 1-L[1,Hy];
End;
If Felulet>2 Then
Begin
If Hy=1 Then L[Hx,SSz]:= 1-L[Hx,SSz];
If Hy=SSz Then L[Hx,1]:= 1-L[Hx,1];
End;
Kepre;
Vege;
end;
end.