home *** CD-ROM | disk | FTP | other *** search
/ DP Tool Club 11 / CD_ASCQ_11_0294.iso / maj / 666 / xcbitmap.asm < prev    next >
Assembly Source File  |  1993-09-12  |  11KB  |  423 lines

  1. ;-----------------------------------------------------------------------
  2. ; MODULE XCBITMAP
  3. ; This module was written by Matthew MacKenzie
  4. ; matm@eng.umd.edu
  5. ;
  6. ; Compiled bitmap  functions all MODE X 256 Color resolutions
  7. ;
  8. ; Compile with Tasm.
  9. ; C callable.
  10. ;
  11. ; ****** XLIB - Mode X graphics library                ****************
  12. ; ******                                               ****************
  13. ; ****** Written By Themie Gouthas                     ****************
  14. ; ****** Aeronautical Research Laboratory              ****************
  15. ; ****** Defence Science and Technology Organisation   ****************
  16. ; ****** Australia                                     ****************
  17. ;
  18. ; egg@dstos3.dsto.gov.au
  19. ; teg@bart.dsto.gov.au
  20. ;-----------------------------------------------------------------------
  21.  
  22. include xlib.inc
  23. include xcbitmap.inc
  24.  
  25. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  26. ; _x_compile_bitmap
  27. ;
  28. ; Compile a linear bitmap to generate machine code to plot it
  29. ; at any required screen coordinates FAST. Faster than blits
  30. ; using planar bitmaps as in module XPBIITMAP
  31. ;
  32. ; C near-callable as:
  33. ; int x_compile_bitmap  (WORD logical_screen_width,
  34. ;                        char far * bitmap, char far * output);
  35. ;
  36. ; The logical width is in bytes rather than pixels.
  37. ;
  38. ; All four main registers are totaled.
  39. ;
  40. ;  The source linear bitmaps have the following structure:
  41. ;
  42. ;  BYTE 0                 The bitmap width in pixels  range 1..255
  43. ;  BYTE 1                 The bitmap height in rows   range 1..255
  44. ;  BYTE 2..n              The width*height bytes of the bitmap in
  45. ;                         cloumn row order
  46. ;
  47. ; The returned value is the size of the compiled bitmap, in bytes.
  48.  
  49.  
  50. ; accessory macros to save typing (what else?)
  51. Emitb macro arg
  52.     mov byte ptr es:[di],&arg&
  53.     inc di
  54.     endm
  55.  
  56. Emitw macro arg
  57.     mov word ptr es:[di],&arg&
  58.     add di,2
  59.     endm
  60.  
  61. ; opcodes emitted by _x_compile_sprite
  62. ROL_AL          equ 0c0d0h              ; rol al
  63. SHORT_STORE_8   equ 044c6h              ; mov [si]+disp8,  imm8
  64. STORE_8         equ 084c6h              ; mov [si]+disp16, imm8
  65. SHORT_STORE_16  equ 044c7h              ; mov [si]+disp8,  imm16
  66. STORE_16        equ 084c7h              ; mov [si]+disp16, imm16
  67. ADC_SI_IMMED    equ 0d683h              ; adc si,imm8
  68. OUT_AL          equ 0eeh                ; out dx,al
  69. RETURN          equ 0cbh                ; ret
  70.  
  71.  
  72. .data
  73.  
  74. align 2
  75. ColumnMask      db      011h,022h,044h,088h
  76.  
  77.  
  78. .code
  79.  
  80.     align   2
  81. _x_compile_bitmap proc
  82. ARG   logical_width:word,bitmap:dword,output:dword
  83. LOCAL bwidth,scanx,scany,outputx,outputy,column,set_column,input_size:word=LocalStk
  84.     push bp
  85.     mov  bp, sp         ; caller's stack frame
  86.     sub  sp,LocalStk    ; local space
  87.     push si
  88.     push di
  89.     push ds
  90.  
  91.     mov word ptr [scanx],0
  92.     mov word ptr [scany],0
  93.     mov word ptr [outputx],0
  94.     mov word ptr [outputy],0
  95.     mov word ptr [column],0
  96.     mov word ptr [set_column],0
  97.  
  98.     lds si,[bitmap]     ; 32-bit pointer to source bitmap
  99.  
  100.     les di,[output]     ; 32-bit pointer to destination stream
  101.  
  102.     lodsb               ; load width byte
  103.     xor ah, ah          ; convert to word
  104.     mov [bwidth], ax    ; save for future reference
  105.     mov bl, al          ; copy width byte to bl
  106.     lodsb               ; load height byte -- already a word since ah=0
  107.     mul bl              ; mult height word by width byte
  108.     mov [input_size], ax;  to get pixel total 
  109.  
  110. @@MainLoop:
  111.     mov bx, [scanx]     ; position in original bitmap
  112.     add bx, [scany]
  113.  
  114.     mov al, [si+bx]     ; get pixel
  115.     or  al, al          ; skip empty pixels
  116.     jnz @@NoAdvance
  117.     jmp @@Advance
  118. @@NoAdvance:
  119.  
  120.     mov dx, [set_column]
  121.     cmp dx, [column]
  122.     je @@SameColumn
  123. @@ColumnLoop:
  124.     Emitw ROL_AL        ; emit code to move to new column
  125.     Emitw ADC_SI_IMMED
  126.     Emitb 0
  127.  
  128.     inc dx
  129.     cmp dx, [column]
  130.     jl @@ColumnLoop
  131.  
  132.     Emitb OUT_AL        ; emit code to set VGA mask for new column
  133.     mov [set_column], dx
  134. @@SameColumn:
  135.     mov dx, [outputy]   ; calculate output position
  136.     add dx, [outputx]
  137.     sub dx, 128
  138.  
  139.     add word ptr [scanx], 4
  140.     mov cx, [scanx]     ; within four pixels of right edge?
  141.     cmp cx, [bwidth]
  142.     jge @@OnePixel
  143.  
  144.     inc word ptr [outputx]
  145.     mov ah, [si+bx+4]   ; get second pixel
  146.     or ah, ah
  147.     jnz @@TwoPixels
  148. @@OnePixel:
  149.     cmp dx, 127         ; can we use shorter form?
  150.     jg @@OnePixLarge
  151.     cmp dx, -128
  152.     jl @@OnePixLarge
  153.     Emitw SHORT_STORE_8
  154.     Emitb dl            ; 8-bit position in output
  155.     jmp @@EmitOnePixel
  156. @@OnePixLarge:
  157.     Emitw STORE_8
  158.     Emitw dx            ; position in output
  159. @@EmitOnePixel:
  160.     Emitb al
  161.     jmp short @@Advance
  162. @@TwoPixels:
  163.     cmp dx, 127
  164.     jg @@TwoPixLarge
  165.     cmp dx, -128
  166.     jl @@TwoPixLarge
  167.     Emitw SHORT_STORE_16
  168.     Emitb dl            ; 8-bit position in output
  169.     jmp @@EmitTwoPixels
  170. @@TwoPixLarge:
  171.     Emitw STORE_16
  172.     Emitw dx            ; position in output
  173. @@EmitTwoPixels:
  174.     Emitw ax
  175.  
  176. @@Advance:
  177.     inc word ptr [outputx]
  178.     mov ax, [scanx]
  179.     add ax, 4
  180.     cmp ax, [bwidth]
  181.     jl @@AdvanceDone
  182.     mov dx, [outputy]
  183.     add dx, [logical_width]
  184.     mov cx, [scany]
  185.     add cx, [bwidth]
  186.     cmp cx, [input_size]
  187.     jl @@NoNewColumn
  188.     inc word ptr [column]
  189.     mov cx, [column]
  190.     cmp cx, 4
  191.     je @@Exit           ; Column 4: there is no column 4.
  192.     xor cx, cx          ; scany and outputy are 0 again for
  193.     mov dx, cx          ; the new column
  194. @@NoNewColumn:
  195.     mov [outputy], dx
  196.     mov [scany], cx
  197.     mov word ptr [outputx], 0
  198.     mov ax,[column]
  199. @@AdvanceDone:
  200.     mov [scanx], ax
  201.     jmp @@MainLoop
  202.  
  203. @@Exit:
  204.     Emitb RETURN
  205.     mov ax,di
  206.     sub ax,word ptr [output] ; size of generated code
  207.  
  208.     pop ds
  209.     pop di
  210.     pop si
  211.     mov sp, bp
  212.     pop bp
  213.  
  214.     ret
  215. _x_compile_bitmap endp
  216.  
  217.  
  218. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  219. ; _x_sizeof_cbitmap
  220. ;
  221. ; This function follows the same algorithm as the one above,
  222. ; but does not generate a new object.  Its sole purpose is to
  223. ; determine how much space the compiled bitmap will require.
  224. ;
  225. ; C near-callable as:
  226. ; int x_sizeof_cbitmap  (WORD logical_screen_width,
  227. ;                                char far * bitmap);
  228. ;
  229. ; The logical width is in bytes rather than pixels.
  230. ;
  231. ; All four main registers are totaled.
  232. ;
  233. ;  The source linear bitmaps have the following structure:
  234. ;
  235. ;  BYTE 0                 The bitmap width in pixels  range 1..255
  236. ;  BYTE 1                 The bitmap height in rows   range 1..255
  237. ;  BYTE 2..n              The width*height bytes of the bitmap in
  238. ;                         cloumn row order
  239. ;
  240. ; The returned value is the size of the compiled bitmap, in bytes.
  241.  
  242.  
  243.     align   2
  244. _x_sizeof_cbitmap proc
  245. ARG   logical_width:word,bitmap:dword
  246. LOCAL bwidth,scanx,scany,outputx,outputy,column,set_column,input_size:word=LocalStk
  247.     push bp
  248.     mov  bp, sp         ; caller's stack frame
  249.     sub  sp,LocalStk    ; local space
  250.     push si
  251.     push di
  252.     push ds
  253.  
  254.     mov word ptr [scanx], 0
  255.     mov word ptr [scany], 0
  256.     mov word ptr [outputx], 0
  257.     mov word ptr [outputy], 0
  258.     mov word ptr [column], 0
  259.     mov word ptr [set_column], 0
  260.  
  261.     lds si,[bitmap]     ; 32-bit pointer to source bitmap
  262.  
  263.     mov di, 1           ; initial size is just the size of the far RET
  264.  
  265.     lodsb               ; load width byte
  266.     xor ah, ah          ; convert to word
  267.     mov [bwidth], ax    ; save for future reference
  268.     mov bl, al          ; copy width byte to bl
  269.     lodsb               ; load height byte -- already a word since ah=0
  270.     mul bl              ; mult height word by width byte
  271.     mov [input_size], ax;  to get pixel total
  272.  
  273. @@MainLoop:
  274.     mov bx, [scanx]     ; position in original bitmap
  275.     add bx, [scany]
  276.  
  277.     mov al, [si+bx]     ; get pixel
  278.     or  al, al          ; skip empty pixels
  279.     jnz @@NoAdvance
  280.     jmp @@Advance
  281. @@NoAdvance:
  282.  
  283.     mov dx, [set_column]
  284.     cmp dx, [column]
  285.     je @@SameColumn
  286. @@ColumnLoop:
  287.     add di, 5           ; size of code to move to new column
  288.     inc dx
  289.     cmp dx,[column]
  290.     jl @@ColumnLoop
  291.  
  292.     inc di              ; size of code to set VGA mask
  293.     mov [set_column], dx
  294. @@SameColumn:
  295.     mov dx, [outputy]   ; calculate output position
  296.     add dx, [outputx]
  297.     sub dx, 128
  298.  
  299.     add word ptr [scanx], 4
  300.     mov cx, [scanx]     ; within four pixels of right edge?
  301.     cmp cx, [bwidth]
  302.     jge @@OnePixel
  303.  
  304.     inc word ptr [outputx]
  305.     mov ah,[si+bx+4]    ; get second pixel
  306.     or ah, ah
  307.     jnz @@TwoPixels
  308. @@OnePixel:
  309.     cmp dx, 127         ; can we use shorter form?
  310.     jg @@OnePixLarge
  311.     cmp dx, -128
  312.     jl @@OnePixLarge
  313.     add di, 4           ; size of 8-bit position in output plus one pixel
  314.     jmp @@EmitOnePixel
  315. @@OnePixLarge:
  316.     add di, 5           ; size of position in output plus one pixels
  317. @@EmitOnePixel:
  318.     jmp short @@Advance
  319. @@TwoPixels:
  320.     cmp dx, 127
  321.     jg @@TwoPixLarge
  322.     cmp dx, -128
  323.     jl @@TwoPixLarge
  324.     add di, 5           ; size of 8-bit position in output plus two pixels
  325.     jmp @@EmitTwoPixels
  326. @@TwoPixLarge:
  327.     add di, 6           ; size of 16-bit position in output plus two pixels
  328. @@EmitTwoPixels:
  329.  
  330. @@Advance:
  331.     inc word ptr [outputx]
  332.     mov ax, [scanx]
  333.     add ax,4
  334.     cmp ax, [bwidth]
  335.     jl @@AdvanceDone
  336.     mov dx, [outputy]
  337.     add dx, [logical_width]
  338.     mov cx, [scany]
  339.     add cx, [bwidth]
  340.     cmp cx, [input_size]
  341.     jl @@NoNewColumn
  342.     inc word ptr [column]
  343.     mov cx, [column]
  344.     cmp cx, 4
  345.     je @@Exit           ; Column 4: there is no column 4.
  346.     xor cx,cx           ; scany and outputy are 0 again for
  347.     mov dx,cx           ; the new column
  348. @@NoNewColumn:
  349.     mov [outputy], dx
  350.     mov [scany], cx
  351.     mov word ptr [outputx], 0
  352.     mov ax,[column]
  353. @@AdvanceDone:
  354.     mov [scanx], ax
  355.     jmp @@MainLoop
  356.  
  357. @@Exit:
  358.     mov ax, di          ; size of generated code
  359.  
  360.     pop ds
  361.     pop di
  362.     pop si
  363.     mov sp,bp
  364.     pop bp
  365.  
  366.     ret
  367. _x_sizeof_cbitmap endp
  368.  
  369.  
  370. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  371. ; _x_put_cbitmap
  372. ;
  373. ; Displays a compiled bitmap generated by x_compile_bitmap at given
  374. ; coordinates, on a given screen page.
  375. ;
  376. ; C near-callable as:
  377. ; void x_put_cbitmap (int XPos, int YPos,
  378. ;                     unsigned int PageOffset, char far * Sprite);
  379. ; ax, bx, cx, and dx are squashed like insignificant insects.
  380.  
  381.     align   2
  382. _x_put_cbitmap proc
  383. ARG XPos:word,YPos:word,PageOffset:word,Sprite:dword
  384.  
  385.     push bp
  386.     mov bp, sp
  387.     push si
  388.     push ds
  389.  
  390.     mov ax, [_ScrnLogicalByteWidth] ; global Xlib variable
  391.     mul word ptr [YPos] ; height in bytes
  392.     mov si, [XPos]
  393.     mov bx, si
  394.     sar si, 2           ; width in bytes
  395.     add si, ax
  396.     add si, [PageOffset]; (YPos * screen width) +
  397.     add si, 128         ;   (Xpos / 4) + page base + 128 ==> starting pos
  398.  
  399.     and bx, 3
  400.     mov ah, ColumnMask[bx]
  401.  
  402.     mov dx, SC_INDEX
  403.     mov al, MAP_MASK
  404.     out dx, ax
  405.     inc dx              ; ready to send out other masks as bytes
  406.     mov al, ah
  407.  
  408.     mov bx, SCREEN_SEG
  409.     mov ds, bx          ; We do this so the compiled shape won't need
  410.                         ;  segment overrides.
  411.  
  412.     call dword ptr [Sprite] ; the business end of the routine
  413.  
  414.     pop ds
  415.     pop si
  416.     pop bp
  417.  
  418.     ret
  419. _x_put_cbitmap endp
  420.  
  421. end
  422.  
  423.