Umíte pascalsky - 27.lekce ...

Umíte pascalsky?
27.lekce
Vytisknout  

Pohyb po obrazovce

Pohyb určitého objektu na obrazovce provedeme pomocí postupného přesunu odpovídající části obrazovky na požadované místo. Přesun se provede tak, že obsah části obrazovky se uloží do paměti a pak se z paměti přesune na určené místo.

Uložení obsahu části obrazovky tvaru obdélníka na adresu Buffer provádí procedura
GetImage(x1,y1,x2,y2,Buffer)

Proměnná Buffer je dynamický proměnná, které musíme nejprve přidělit volnou paměť potřebnou k uložení části obrazovky.

Počet bytú potřebných k uložení určené části obrazovky do paměti zjišťuje funkce
ImageSize(x1,y1,x2,y2)

Přidělení volné paměti velikosti pocet_bytu dynamické proměnné Buffer zajistí procedura
GetMem(Buffer,pocet_bytu)

Každou dynamickou proměnnou je dobrým zvykem zrušit, pokud ji už nepotřebujeme. To provádí procedura
FreeMem(Buffer,pocet_bytu)

Uložení části obrazovky lze tedy provést následovně:

var x1,y1,x2,y2 : Word;
        Buffer : Pointer;
        pocet_bytu : Word;
...................
pocet_bytu := ImageSize(x1,y1,x2,y2);
GetMem(Buffer,pocet_bytu);
GetImage(x1,y1,x2,y2,Buffer);
...................
FreeMem(Buffer,pocet_bytu);


Přesun z paměti na určené místo obrazovky provádí procedura
PutImage(x,y,Buffer,zpusob)

x,y jsou souřadnice levého horního rohu obdélníka, do kterého se přesun provede
zpusob nabývá hodnot:

0 = NormalPut mov - přímý přesun
1 = XORPut xor
2 = ORPut or
3 = ANDPut and
4 = NOTPut not


Příklad:
Sestavte program Balon, který zobrazí pohybující se míč 20 kroků dolů se změnou o 10,10 a potom 20 kroků nahoru stejným způsobem.



Myšlenka (hrubý algoritmus):

Inicializace - inicializace grafického režimu
Mic - nakreslí míč a uloží do paměti
Pohyb - opakovaně přesunuje míč o změnu_x=10 a změnu_y=10

Upřesníme souřadnice jednotlivých elementů na obrazovce:



Program Balon může vypadat takto:

program Balon;
  uses Crt, Graph;
  var driver,mode:integer;
           x1,y1,x2,y2:Word;
           Buffer:Pointer;
           pocet_bytu:Word;
{připojení jednotky Crt,Graph}
{proměnné potřebné pro inicializaci}
{souřadnice levého hor. a pravého dol.rohu}
{pro uložení části obrazovky do paměti}
{velikost části obrazovky}
 
procedure Inicializace;
  begin
    DetectGraph(driver,mode);
    InitGraph(driver,mode,'c:\tp\bgi ');
    if GraphResult <> 0 then
      begin
        writeln('Chyba grafiky:',GraphErrorMsg(driver));
        exit;
      end

{detekce graf.karty a modu}
{inicializace}
{jestliže došlo k chybě}

{výpis chybového hlášení}
{ukončení programu}

  end;

procedure Mic;
  begin
    SetBkColor(white);
    SetViewPort(0,0,640,480,true);
    SetColor(12);
    Rectangle(5,5,635,475);
    SetColor(9);
    Circle(40,240,20);
    SetFillStyle(1,9);
    FloodFill(40,240,9);
    pocet_bytu:= ImageSize(10,210,70,270);
    GetMem(Buffer,pocet_bytu);
    GetImage(10,210,70,270,Buffer^);
{pozadí obrazovky bílé}
{okno pro obrazovku}
{červená barva pera}
{orámování - obdélník}
{modrá barva pera}
{kružnice}
{nastavení šrafování}
{modrá výplň kružnice}
{zjištění velikosti proměnné}
{přidělení paměti dyn.proměnné}
{uložení míče + okraje do paměti}
  end;

procedure Leti;
  var x,y,kolik:Word;
  begin
    x:=0;y:=200;
    delay(2000);
    for kolik:=1 to 20 do
      begin
        x:=x+10;y:=y+10;
        PutImage(x,y,Buffer^,0);
        delay(100);
      end;
    for kolik:=1 to 20 do
      begin
        x:=x+10;y:=y-10;
        PutImage(x,y,Buffer^,0);
        delay(100);
      end;
{po pricteni kroku vychozi pozice}
{čekání}
{20x se bude opakovat}

{souř,pro posun dolů pod úhlem 45o}
{zobrazení míče na nové posici}
{čekání-zpomalení pohybu}

{20x se bude opakovat}

{souř,pro posun nahoru pod úhlem 45o}
{zobrazení míče na nové posici}
{čekání-zpomalení pohybu}

  end;

Begin
   Inicializace;
   Mic;
   Leti;
   readln;
   FreeMem(Buffer,pocet_bytu);
   CloseGraph;
{inicializace graf.režimu}
{nakreslení míče a uložení výřezu do paměti}
{pohyb míče}

{uvolnění paměti}
{ukončení graf.režimu}
End.


Pohyb (míče) nemusíme přesně definovat v programu.
A) pohyb můžeme generovat náhodně
B) pohyb může řídit uživatel stiskem příslušných kláves

A) Při modelování náhodného pohybu musimě nejprve inicializovat generátor náhodných čísel procedurou
Randomize

Potom již můžeme použít funkce
Random(horni)
která generuje náhodné číslo z intervalu <0,horni). (hodnoty horni nenabývá, nulu ano)

Chceme-li náhodně vygenerovat směr:
1 - nahoru
2 - doprava
3 - dolu
4 - doleva
vygenerujeme proměnnou smer např. takto:
smer := Trunc(Rand(4)+1);
a potom pomocí příkazu:
case of smer
  1: {nahoru}
  ....
end;
změníme odpovídajícím způsobem hodnotu x a hodnotu y.

B) U pohybu řízeného uživatelem nejprve určíme klávesy, které budou řídit pohyb. Výhodné je použít kurzorových šipek s těmito kódy.


Která klávesa byla stisknuta zjistí funkce typu char: ReadKey
a její kód zjistíme pomocí funkce: Ord(klavesa)

Příkaz
klavesa = ReadKey;
zastaví program a čeká na stisk klávesy. Po stisknutí klávesy se znak nezobrazí na monituru a znak z klávesnice se uloží do proměnné klavesa typu char.
Je-li stisknuta řídící klávesa (F1 .. F12, Ins, Del, kurzorové šipky,..), funkce ReadKey přečte #0, při dalším volání ReadKey přečte znak odpovídající této klávese.

Pomocí následujícího cyklu tedy lze řídit pohyb kurzorovými klávesami:

repeat
   klavesa:=readkey;
   if klavesa=#0 then
     klavesa:=readkey;
   case ord(klavesa) of
     075: {doleva};
     072: {nahoru};
     077: {doprava};
     050: {dolů};
   end;
   ......
until klavesa = {ukončovací klávesa}


Domácí úkol:

    Sestavte program Nahoda, který nakreslí zvolený objekt (nebo míč) a nechá ho náhodně pohybovat po obrazovce a program Ridim , který tento objekt nechá pohybovat pomocí kláves stisknutých uživatelem.
Pro pokročilé: Zkuste vytvořit jednoduchou hru s pohybem.

On-line účast na řešení úkolu

Řešit úkol Prohlídka hodnocení úkolu Dotazy,připomínky

Pomocí volby Řešit můžete (po přihlášení) odeslat vaše řešení domácího úkolu (každý úkol smíte řešit jen jednou). Volbou Hodnocení si přečtete hodnocení a komentář od vyučujícího. Dotaz nebo připomínku můžete opakovaně zasílat pomocí tlačítka Dotazy, Komunikace (na levém okraji) zobrazuje příklad možné komunikace s vyučujícím.