Generowanie mapy do gry strategicznej

psychoszayber

Może się komuś przydać. Zaczniemy od wprowadzenia. Generator - rzecz która przy pomocy jakiś materiałów coś wytwarza. Winamp posiada np. funkcje generowania html`owej playlisty (Ctrl+Alt+G). Może sie to przydać do wydrukowania listy mp3. Ale już bardziej przydatne jest jako odtwarzacz map do gier. Jak byłeś początkującym programistą (albo nim jesteś) to (Może. Nie mówie na pewno) zastanawiałeś się jakim cudem można zapisać mapkę do gry strategicznej (Nie 3D). Pewnie myślałeś że to BMP lub jakiś obrazek. G.... prawda (Przepraszam). Wtedy ta mapka zajmowała by jakieś 32 MB tak jak jest w TA (Total Annihilation). Owszem można było ją zapisać jako Bmp ale (średnio) zajmowała jakieś 23,5 Mb. A jak się ją zapisało normalnie to jej rozmiar skurczył się do 351 Kb !!! Teraz pokażę jak to było możliwe.

Na początek mapka składała się z iluśtam kwadratów. Jeden kwadarat to 32x32 px (Px=Pixel). bibloteka programu miała np. 200 bitmapek 32x32 ich nazwy to 1.bmp,2.bmp .. 200.bmp. Nie 255 bo te 55 to specjalne obiekty. Pewnie zauważyłeś że litera składa sie od 0..255 liczby, i dobrze dzięki temu mapka będzie miała mniejsze rozmiary. Cell to po angielsku komórka. Więc mapka składała by się np. tak:

W=szerokość (Width).
H=wysokość (Height).
C=Komórka (Cell).

WHCCCCCCCCCCCCCCCC

czyli:

E/R)?\FśJ]'";|,=#2

Coś jak moje CMP ale jeszcze więcej będzie potrzebne.

Dla algorytmików , Zaawansowanych i piszących gry to będzie pryszcz (chyba).

Deklarujemy zmienne globalne:

var
  map: array [0 .. 255, 0 .. 255] of byte;
  cell: bitmap;

Potrzebne nam będzie:
DrawGrind o nazwie "DG" i ustaw DefaultColWidth oraz DefaultRowHeight na 32. FixedCols i FixedRows na 0.
OpenDialog nazwa 'OD' i SaveDialog nazwa 'SD';
3 Buttony. 1-szy capition na 'Save'. 2-gi capition na 'Load'. 3-ci capition na 'Draw';

W form On create:

cell := Tbitmap.Create;
cell.Width := 32;
cell.Height := 32;

1 button on click:

sd.execute;
SaveMap(sd.fileName);

2 button on click:

od.execute;
LoadMap(od.filename);

3 button on click:

DrawMap;

Procedury:

Procedure Tform1.SaveMap(S: string);
var
  F: file;
  I, II: integer;
  ss: array [1 .. 2] of byte;
begin
  assignfile(F, S);
  Rewrite(F, 1);
  ss[1] := DG.colcount;
  ss[2] := DG.Rowcount;
  blockwrite(F, ss, 2);
  for I := 0 to DG.Rowcount - 1 do
  begin
    blockwrite(F, map[I], DG.colcount);
  end;
  closefile(F);
end;
 
Procedure Tform1.LoadMap(S: string);
var
  F: file;
  I, II: integer;
  ss: array [1 .. 2] of byte;
begin
  assignfile(F, S);
  Reset(F, 1);
  blockread(F, ss, 2);
  DG.colcount := ord(ss[1]);
  DG.Rowcount := ord(ss[2]);
  for I := 0 to DG.Rowcount - 1 do
  begin
    blockread(F, map[I], DG.colcount);
  end;
  closefile(F);
end;
 
Procedure Tform1.DrawMap;
var
  I, II: integer;
begin
  for I := 0 to DG.Rowcount - 1 do
    for II := 0 to DG.colcount - 1 do
    begin
      cell.LoadFromFile(extractfiledir(application.ExeName) + '' +
        inttostr(map[II, I]) + '.bmp');
      DG.Canvas.StretchDraw(DG.CellRect(II, I), cell);
    end;
end;

Jeszcze przychodzą do tego jakieś zabezpieczenia, żeby nie zniknęły obrazeczki z DrawGring po naziśnięciu myszką ale już nie chce mi się tego pisać. Jeszcze zrób z tego edytor i zapełnij 255 obrazeczków i już możesz zrobić grę strategiczną :P.

8 komentarzy

sorry za odkop ale mam newbie pytanie: co to jest " E/R)?\FśJ]'";|,=#2 " ?

Przydało by się formatowanie kodu; Proszę o poprawienie go, bo strasznie źle się go czyta;

strasznie dużo mówiący tytuł tegp \"arta\" :D

Capitionalna sprawa z tym mapowaniem ale nie kumam za bardzo

Dobre ale w końcu opisałem tylko edytor i sposób.

hahah.... "DrawGring" "DrawGrind" "Capition" hehehe teraz mi sie tak skojarzylo ze zrobie zaawansowany edytor map a samej gry nie zrobie :D

edytor map do Tonego Hawka 3? "DrawGrind

Ładnie, ale może spróbuj to zredagować, bo ja tam nic nie widzę!