program assembler_addition;
var a,b,c:integer;
begin
 readln(A,B); {Hodnoty nacte uzivatel}
 asm
  mov AX,A {Mov destination, source --> ax:=a;}
  mov BX,B
  add AX,BX {AX:=AX+BX}
  mov C,AX  {C:=AX}
 end;
 writeln(A, '+', B, '=', C);
 readln;
end.

******************************************************************************

program graph_init;
uses Crt;
begin
 asm
  mov al,00h {textovy rezim 40x25 = ten nejhorsi mozny, ale funguje
             v nem writeln; a je poznat, ze doslo ke zmene
              jine hodnoty napr. 02h - graficky rezim 640x480x16,
              02h - textovy rezim 80x25x16
              12h - graficky 640x480x16 apod. viz Sysman}
  mov ah,00h  {sluzba 00h - inicializace grafiky}
  int 10h     {preruseni 10h - obsluha obrazovky}
 end;
 writeln('Graficky rezim byl inicializovan');
 repeat until KeyPressed;
 asm{uklid na neco normalniho}
  mov al,02h
  mov ah,00h
  int 10h
 end;
end.

***************************************************************************

program mouse_init;
uses Crt;
begin
 asm
  mov al,12h {640x480x16 viz Sysman}
  mov ah,00h  {sluzba 00h - inicializace grafiky}
  int 10h     {preruseni 10h - obsluha obrazovky}

  mov ax,00h  {inicializace mysi - nastaveni spravnych rozmeru obrazovky,
              nacteni spravneho typu kurzoru...}
  int 33h

  mov ax,01h {inicializace kurzoru mysi, neni spravne, ze nekontrolujeme,
             zda mys existuje a zda ma ovladac}
  int 33h
 end;

 repeat until KeyPressed;
 asm{uklid na neco normalniho}
  mov al,02h
  mov ah,00h
  int 10h
 end;
end.

***************************************************************************
program graphics;
{Kresli na obrazovku nahodne barevne body, vyuziva pritom preruseni}
uses Crt;
var x,y:word;
    color:byte;

procedure Init;
{Nastavi graficky rezim a generator nahodnych cisel}
begin
 Randomize;
 asm
  mov al,12h
  mov ah,00h
  int 10h {Inicializace grafiky 640x480x16}
 end;
end;

procedure PutPixel;assembler;
asm
  mov ah,0ch
  mov al,color
  mov cx,x
  mov dx,y
  mov bx,1
  int 10H
end;

begin
 Init;
 repeat
  X:=random(640);
  Y:=random(480);
  color:=random(16);
  PutPixel;
 until KeyPressed;
 {Tady bychom meli ukoncit graficky rezim a nespolehat se na to,
  ze to pocitac udela za nas...}
end.
****************************************************************************
program graphics2;
{Stejne jako minuly program, ale porovnejte rychlost.
Zaver: Pascalovska unita Graph je nepouzitelna.}
uses Crt, Graph;
var
 Gd, Gm: Integer;
 Color: Word;
begin
 Gd := Detect;
 InitGraph(Gd, Gm, ' ');
 if GraphResult <> grOk then {Na rozdil od minuleho programu kontrolujeme,
                             zda se nam podarilo graficky rezim nastavit}
   Halt(1);
 Color := GetMaxColor;
 Randomize;
 repeat
   PutPixel(Random(640), Random(480), Random(Color));
   Delay(10);
 until KeyPressed;
 CloseGraph;
end.

****************************************************************

program nahodne_cary;
{Kresli na obrazovku nahodne cary.
Vyuziva pritom Breshamuv algoritmus}
{Nevyuzivam primy zapis do videopameti, pouze volam preruseni}
uses Crt;

procedure InitGraph;assembler;
asm
  mov al,12h
  mov ah,00h
  int 10h {Muj oblibeny rezim 640x480x16 - da se na to koukat
          a jeste se s nim dobre pracuje}
end;

procedure DrawLine(x1,y1,x2,y2:integer;color:byte);
{Vlastni algoritmus na kresleni car,
jelikoz je deleni realnych cisel velmi pomale,
vse prevadime na praci se zlomky. (Breshamuv algoritmus)

Je to jednoduche:
Predstavme si na chvili, kreslime caru z [0,0] do [50,10].
Jsme v prvnim kvadrantu a rychleji "rosteme" ve smeru x.
Smernice je 10/50. Zvysime-li souradnici x o jedna,
zvysi se jmenovatel zlomku o 10.
No a pokud je zlomek vetsi nebo roven jedne (to pozname tak, ze citatel>=jmenovatel),
tak zvysime i hodnotu y-ove souradnice.

Situaci ve zbylych kvadrantech vyresime pomoci symetrie.
Pokud chceme dobrou rychlost, musime vse prepsat do assembleru
a vytvorit osm ruznych verzi nasi funkce (pro kazdy smer trosku jinou).
Napr (dec x) je mnohem rychlejsi nez inc x,-1 takze rozdeleni vede
k viditelnemu zrychleni.
}

function abs(x,y:integer):boolean;
begin
 if x<0 then x:=-x;
 if y<0 then y:=-y;
 abs:=x> y;
end;

var diffx,diffy,t:integer;
begin
 diffx:=x2-x1;
 diffy:=y2-y1;
 if abs(diffx,diffy) then
  begin {budeme zvysovat x-ovou souradnici}
   if diffx<0 then
                  begin
                       t:=x1; x1:=x2; x2:=t;diffx:=-diffx;
                       t:=y1; y1:=y2; y2:=t;diffy:=-diffy;
                  end;
   if diffy>0 then t:=1 else begin t:=-1; diffy:=-diffy; end;
   y2:=diffx;
    repeat
     inc(x1);
     dec(y2,diffy);
     if y2<=0 then begin inc(y1,t); inc(y2,diffx); end;
        {Tohle je maly podraz, jelikoz pocitac rychleji zjisti,
        zda cislo je ci neni zaporne, misto toho, abychom k jmenovateli
        neco pricitali a pak ho porovnavali s hodnotou jmenovatele,
        delame to opacne - na zacatku do citatele ulozime hodnotu jmenovatele
        a pak odcitame :) a kontrolujeme, zda nahodou neni citatel zaporny.}

     asm {Vlastni kresleni bodu}
       mov ah,0ch
       mov al,color
       mov cx,x1
       mov dx,y1
       mov bx,1
       int 10H
     end;
    until x1=x2;
  end
 else
  begin {zvysujeme y-ovou souradnici}
    if diffy<0 then
                  begin
                       t:=x1; x1:=x2; x2:=t;diffx:=-diffx;
                       t:=y1; y1:=y2; y2:=t;diffy:=-diffy;
                  end;
   if diffx>0 then t:=1 else begin t:=-1; diffx:=-diffx; end;
   x2:=diffy;
    repeat
     inc(y1);
     dec(x2,diffx);
     if x2<=0 then begin inc(x1,t); inc(x2,diffy); end;
     asm {Vlastni kresleni bodu}
       mov ah,0ch
       mov al,color
       mov cx,x1
       mov dx,y1
       mov bx,1
       int 10H
     end;
    until y1=y2;
  end
end;

begin
 Randomize;
 InitGraph;
 repeat
  DrawLine(Random(640),Random(480),Random(640),Random(480),Random(16));
 until KeyPressed;
end.



***************************************************************************

program cary;
{V tomhle pripade Pascalovska grafika v rychlosti vede,
ale to jen kvuli tomu, ze jsme nasi proceduru nenapsali
v cistem assembleru (+nepouzili primy zapis do videopameti)
+nevyuzili graficky akcelerator.}
uses Graph,Crt;
var gd,gm:integer;
begin
 Randomize;
 gd:=Detect;
 InitGraph(gd,gm,' ');

 repeat
 SetColor(Random(16));
 Line(Random(640),Random(480),Random(640),Random(480));
 until KeyPressed;

 CloseGraph;
end.
