[Back to GRAPHICS SWAG index]  [Back to Main SWAG index]  [Original]

{This 2 procedures work with standard VGA (640x480x16). I did this about
 4 years ago to get higher speed of handling images. There are two
 restictions: 1. only NormalPut is done. (no such parameter for PutImageX8)
              2. the x-position must be X mod 8 = 0.
 For static images I use them often, because they are more than 4 times
 faster then the BGI originals. The function ImageSize can be used to get the
 required size of image.

 Dec. 13, 1995, Udo Juerss, 57078 Siegen, Germany, CompuServe [101364,526]}

procedure GetImageX8(X1,Y1,X2,Y2:Integer; var OP); assembler;
var
  XLen,YLen : Word;

asm
    push ds                              {Verwendete Segmentregister sichern}
    push es
    les  di,[OP]                                  {ES:DI = Zeiger auf Bitmap}
    mov  ax,X2
    mov  bx,X1
    and  ax,0FFF8h
    add  ax,8
    and  bx,0FFF8h
    sub  ax,bx                                 {AX = horizontale Punktanzahl}
    push ax
    stosw      {Als Information f|r GetImage diesen Wert in Bitmap speichern}
    mov  ax,Y2
    sub  ax,Y1                                   {AX = vertikale Punktanzahl}
    mov  YLen,ax                            {F|r spdteren Zdhlwert speichern}
    stosw      {Als Information f|r GetImage diesen Wert in Bitmap speichern}
    pop  ax
    shr  ax,3
    mov  XLen,ax
    mov  bx,X1
    shr  bx,3
    mov  si,Y1
    shl  si,4
    mov  cx,si
    shl  si,2
    add  si,cx
    add  si,bx                                   {SI = BPR * Y1 + (X1 shl 8)}
    mov  ds,SegA000                                   {DS = Video Basissegment}
    mov  dx,03CEh                     {DX = Graphics Controller Command Port}
    mov  al,4                                    {Read-Map Register anwdhlen}
    out  dx,al
    inc  dx                              {DX = Graphics Controller Data Port}
    mov  bx,YLen                                         {BX = Anzahl Zeilen}
    mov  cx,XLen                                         {CX = Anzahl  Bytes}

@1: mov  al,3                                       {Maske f|r Plane 3 laden}

@2: out  dx,al                            {Plane f|r Lesezugriff selektieren}
    push si                                   {Quelloffset auf Stack sichern}
    push cx                                {Repetierzdhler auf Stack sichern}
    rep  movsb                                        {Kopiervorgang starten}
    pop  cx                                      {Repetierzdhler zur|ckholen}
    pop  si                                         {Quelloffset zur|ckholen}
    dec  al                                {AL = AL - 1 ndchste untere Plane}
    jnl  @2                           {Wenn AL nicht < 0, dann weiter bei @2}
    add  si,80                         {Quelloffset auf ndchste Zeile setzen}
    dec  bx                                              {Vertikalzdhler - 1}
    jnl  @1                              {Wenn nicht < 0, dann ndchste Zeile}

    pop  es                          {Verwendete Segmentregister zur|ckholen}
    pop  ds
end;
{---------------------------------------------------------------------------}

procedure PutImageX8(XOfs,YOfs:Integer; var IP); assembler;
var
  XLen,YLen : Word;

asm
    push  ds                             {Verwendete Segmentregister sichern}
    push  es

    mov  es,SegA000                          {Basis Videosegment A000h laden}

    push ds                                                      {DS sichern}
    lds  si,[IP]                                  {DS:SI = Zeiger auf Bitmap}
    lodsw                                {1. Wort = Anzahl Punkte horizontal}
    shr  ax,3                    {AX = Anzahl Bytes von horizontalen Punkten}
    mov  XLen,ax             {Laufvariable f|r Anzahl horizontale Scanzyklen}
    lodsw                         {2. Wort = Anzahl Zeilen (Punkte vertikal)}
    mov  YLen,ax              {Laufvariable f|r Anzahl vertikaler Scanzyklen}
    mov  di,ds                                           {DS in DI speichern}
    pop  ds                         {DS zur|ckholen um Maskenarrays zu laden}
    mov  ax,YOfs
    shl  ax,4
    mov  bx,ax
    shl  ax,2
    add  ax,bx
    mov  bx,XOfs                  {CX = Offset linker Punkt vom Zeilenanfang}
    shr  bx,3
    add  ax,bx                                  {Speicheradresse von 1.Punkt}
    mov  ds,di                                       {DI wieder zur|ck in DS}
    mov  di,ax      {Zielregister auf Speicheradresse von 1.Punkt einstellen}

    mov  dx,03C4h                               {DX = Sequenzer Command Port}
    mov  al,2                                {Das Map-Mask Register anwdhlen}
    out  dx,al
    inc  dx                                        {DX = Sequnezer Data Port}

    mov  bx,YLen                                         {BX = Anzahl Zeilen}
    mov  cx,XLen                                         {CX = Anzahl  Bytes}

@1: mov  al,8                       {Maske f|r 3. Plane im Map-Mask Register}

@2: out  dx,al
    push di                                           {Quelloffset auf Stack}
    push cx                                       {Laufregister CX auf Stack}
    rep  movsb                                        {Kopiervorgang starten}
    pop  cx                                        {Laufregister zur|ckholen}
    pop  di                                         {Quelloffset zur|ckholen}
    shr  al,1                              {Maske f|r ndchste Plane erzeugen}
    jnz  @2            {Wenn AL > 0, dann die gleiche Zeile nochmal kopieren}
    add  di,80                            {Offset f|r ndchste Zeile addieren}
    dec  bx                                   {Vertikalzdhler dekrementieren}
    jnl  @1                           {Wenn BX nicht < 0, dann weiter bei @1}

    dec  dx                                     {DX = Sequenzer Command Port}
    mov  ax,0F02h         {Map-Mask Register Normalzustand alle Planes aktiv}
    out  dx,ax

    pop  es                                     {Segmentregister zur|ckholen}
    pop  ds

end;
{---------------------------------------------------------------------------}

[Back to GRAPHICS SWAG index]  [Back to Main SWAG index]  [Original]