.386 .MODEL small INCLUDE defs.inc ;============================================================================ ; ; R_DrawColumn ; ;============================================================================ .data loopcount dd 0 pixelcount dd 0 EXTRN _centery:DWORD EXTRN _destview:DWORD .code ALIGN 16 PROC R_DrawColumnLow_ PUBLIC R_DrawColumnLow_ pushr mov ebp,[_dc_yl] cmp ebp,[_dc_yh] jg done lea edi,[ebp*8+ebp] add edi,ebp shl edi,3 mov ebx,[_dc_x] mov ecx,ebx shr ebx,1 add edi,ebx add edi,[_destview] ; edi = destscreen + y*80 + x/2 and ecx,1 shl ecx,1 mov eax,3 shl eax,cl mov edx,SC_INDEX+1 out dx,al ; set mapmask register jmp lowentry ENDP ALIGN 16 PROC R_DrawColumn_ PUBLIC R_DrawColumn_ pushr mov ebp,[_dc_yl] cmp ebp,[_dc_yh] jg done lea edi,[ebp*8+ebp] add edi,ebp shl edi,3 mov ebx,[_dc_x] mov ecx,ebx shr ebx,2 add edi,ebx add edi,[_destview] ; edi = destscreen + y*80 + x/4 and ecx,3 mov eax,1 shl eax,cl mov edx,SC_INDEX+1 out dx,al ; set mapmask register lowentry: mov eax,[_dc_yh] inc eax sub eax,ebp ; pixel count mov [pixelcount],eax ; save for final pixel js done ; nothing to scale shr eax,1 ; double pixel count mov [loopcount],eax mov ecx,[_dc_iscale] mov eax,[_centery] sub eax,ebp imul ecx mov ebp,[_dc_texturemid] sub ebp,eax shl ebp,9 ; 7 significant bits, 25 frac mov esi,[_dc_source] mov ebx,[_dc_iscale] shl ebx,9 mov eax,OFFSET patch1+2 ; convice tasm to modify code... mov [eax],ebx mov eax,OFFSET patch2+2 ; convice tasm to modify code... mov [eax],ebx ; eax aligned colormap ; ebx aligned colormap ; ecx,edx scratch ; esi virtual source ; edi moving destination pointer ; ebp frac mov ecx,ebp ; begin calculating first pixel add ebp,ebx ; advance frac pointer shr ecx,25 ; finish calculation for first pixel mov edx,ebp ; begin calculating second pixel add ebp,ebx ; advance frac pointer shr edx,25 ; finish calculation for second pixel mov eax,[_dc_colormap] mov ebx,eax mov al,[esi+ecx] ; get first pixel mov bl,[esi+edx] ; get second pixel mov al,[eax] ; color translate first pixel mov bl,[ebx] ; color translate second pixel test [pixelcount],0fffffffeh jnz doubleloop ; at least two pixels to map jmp checklast ALIGN 16 doubleloop: mov ecx,ebp ; begin calculating third pixel patch1: add ebp,12345678h ; advance frac pointer mov [edi],al ; write first pixel shr ecx,25 ; finish calculation for third pixel mov edx,ebp ; begin calculating fourth pixel patch2: add ebp,12345678h ; advance frac pointer mov [edi+PLANEWIDTH],bl ; write second pixel shr edx,25 ; finish calculation for fourth pixel mov al,[esi+ecx] ; get third pixel add edi,PLANEWIDTH*2 ; advance to third pixel destination mov bl,[esi+edx] ; get fourth pixel dec [loopcount] ; done with loop? mov al,[eax] ; color translate third pixel mov bl,[ebx] ; color translate fourth pixel jnz doubleloop ; check for final pixel checklast: test [pixelcount],1 jz done mov [edi],al ; write final pixel done: popr ret ENDP ;============================================================================ ; ; R_DrawSpan ; ; Horizontal texture mapping ; ;============================================================================ .data startdest dd 0 startplane dd 0 plane dd 0 startfrac dd 0 fracstep dd 0 qfracstep dd 0 firstx dd 0 firstbyte dd 0 lastbyte dd 0 .code ALIGN 16 PROC R_DrawSpan_ PUBLIC R_DrawSpan_ PUSHR ; ; calculate screen dest and plane position ; mov eax,[_ds_x1] mov [firstx],eax mov ebx,eax and ebx,3 mov [startplane],ebx mov [plane],ebx shr eax,2 mov ebp,[_ds_y] lea edi,[ebp*8+ebp] add edi,ebp shl edi,3 add edi,eax add edi,[_destview] ; edi = destscreen + y*80 + x/4 mov [startdest],edi ; ; build composite position ; mov ebx,[_ds_xfrac] shl ebx,10 and ebx,0ffff0000h mov eax,[_ds_yfrac] shr eax,6 and eax,0ffffh or ebx,eax mov [startfrac],ebx ; ; build composite step ; mov ebx,[_ds_xstep] shl ebx,10 and ebx,0ffff0000h mov eax,[_ds_ystep] shr eax,6 and eax,0ffffh or ebx,eax mov [fracstep],ebx ; ; patch composite step * 4 into the immediate fields ; shl ebx,2 mov [qfracstep],ebx mov eax,OFFSET hpatch1+2 ; convice tasm to modify code... mov [eax],ebx mov eax,OFFSET hpatch2+2 ; convice tasm to modify code... mov [eax],ebx ; ; draw a plane ; mov ecx,[plane] planeloop: mov eax,1 shl eax,cl mov edx,SC_INDEX+1 out dx,al ; ; find loop count ; mov eax,[_ds_x2] cmp eax,[firstx] jb alldone sub eax,[plane] ; - plane js hdone shr eax,2 ; last planar byte to write mov [lastbyte],eax dec eax js singlepixel shr eax,1 ; last full word to write on line mov ebx,[firstx] shr ebx,2 ; first plane byte to write cmp ebx,[lastbyte] je singlepixel mov [firstbyte],ebx inc ebx shr ebx,1 ; first full word to write on line inc eax sub eax,ebx js hdone mov [loopcount],eax ; eax aligned colormap ; ebx aligned colormap ; ecx,edx scratch ; esi virtual source ; edi moving destination pointer ; ebp frac mov eax,[_ds_colormap] mov ebx,eax mov esi,[_ds_source] mov edi,[startdest] mov ebp,[startfrac] test [firstbyte],1 jz evenstart ; ; map one extra pixel at start ; shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) add ebp,[qfracstep] ; advance frac pointer and ecx,4095 ; finish calculation for first pixel mov al,[esi+ecx] ; get first pixel mov dl,[eax] ; color translate first pixel mov [edi],dl inc edi jz hdone evenstart: ; ; set up for word mapping ; shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) add ebp,[qfracstep] ; advance frac pointer and ecx,4095 ; finish calculation for first pixel shld edx,ebp,22 ; begin calculating second pixel (y units) shld edx,ebp,6 ; begin calculating second pixel (x units) add ebp,[qfracstep] ; advance frac pointer and edx,4095 ; finish calculation for second pixel mov al,[esi+ecx] ; get first pixel mov bl,[esi+edx] ; get second pixel mov dl,[eax] ; color translate first pixel test [loopcount],0ffffffffh jnz hdoubleloop ; at least one pixels to map jmp hchecklast singlepixel: mov eax,[_ds_colormap] mov esi,[_ds_source] mov edi,[startdest] mov ebp,[startfrac] shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) and ecx,4095 ; finish calculation for first pixel mov al,[esi+ecx] ; get first pixel mov dl,[eax] ; color translate first pixel mov [edi],dl jmp hdone ALIGN 16 hdoubleloop: shld ecx,ebp,22 ; begin calculating third pixel (y units) mov dh,[ebx] ; color translate second pixel shld ecx,ebp,6 ; begin calculating third pixel (x units) hpatch1: add ebp,12345678h ; advance frac pointer and ecx,4095 ; finish calculation for third pixel mov [edi],dx ; write two pixels shld edx,ebp,22 ; begin calculating fourth pixel (y units) add edi,2 ; advance to third pixel destination shld edx,ebp,6 ; begin calculating fourth pixel (x units) hpatch2: add ebp,12345678h ; advance frac pointer and edx,4095 ; finish calculation for fourth pixel mov al,[esi+ecx] ; get third pixel mov bl,[esi+edx] ; get fourth pixel dec [loopcount] ; done with loop? mov dl,[eax] ; color translate third pixel jnz hdoubleloop ; ; check for final pixel at end ; hchecklast: test [lastbyte],1 jnz hdone mov [edi],dl ; write final pixel hdone: mov ecx,[plane] inc ecx and ecx,3 jnz noinc inc [startdest] ; over to next byte noinc: cmp ecx,[startplane] je alldone mov [plane],ecx mov ebx,[startfrac] add ebx,[fracstep] mov [startfrac],ebx ; advance frac to next pixel inc [firstx] jmp planeloop alldone: popr ret ENDP ;============================================================================ ; ; R_DrawSpanLow ; ; Horizontal texture mapping ; ;============================================================================ ALIGN 16 PROC R_DrawSpanLow_ PUBLIC R_DrawSpanLow_ PUSHR ; ; calculate screen dest and plane position ; mov eax,[_ds_x1] mov [firstx],eax mov ebx,eax and ebx,1 mov [startplane],ebx mov [plane],ebx shr eax,1 mov ebp,[_ds_y] lea edi,[ebp*8+ebp] add edi,ebp shl edi,3 add edi,eax add edi,[_destview] ; edi = destscreen + y*80 + x/2 mov [startdest],edi ; ; build composite position ; mov ebx,[_ds_xfrac] shl ebx,10 and ebx,0ffff0000h mov eax,[_ds_yfrac] shr eax,6 and eax,0ffffh or ebx,eax mov [startfrac],ebx ; ; build composite step ; mov ebx,[_ds_xstep] shl ebx,10 and ebx,0ffff0000h mov eax,[_ds_ystep] shr eax,6 and eax,0ffffh or ebx,eax mov [fracstep],ebx ; ; patch composite step * 4 into the immediate fields ; shl ebx,1 mov [qfracstep],ebx mov eax,OFFSET hlpatch1+2 ; convice tasm to modify code... mov [eax],ebx mov eax,OFFSET hlpatch2+2 ; convice tasm to modify code... mov [eax],ebx ; ; draw a plane ; mov ecx,[plane] lplaneloop: mov eax,3 shl eax,cl shl eax,cl mov edx,SC_INDEX+1 out dx,al ; ; find loop count ; mov eax,[_ds_x2] cmp eax,[firstx] jb lalldone sub eax,[plane] ; - plane js hldone shr eax,1 ; last planar byte to write mov [lastbyte],eax dec eax js lsinglepixel shr eax,1 ; last full word to write on line mov ebx,[firstx] shr ebx,1 ; first plane byte to write cmp ebx,[lastbyte] je lsinglepixel mov [firstbyte],ebx inc ebx shr ebx,1 ; first full word to write on line inc eax sub eax,ebx js hldone mov [loopcount],eax ; eax aligned colormap ; ebx aligned colormap ; ecx,edx scratch ; esi virtual source ; edi moving destination pointer ; ebp frac mov eax,[_ds_colormap] mov ebx,eax mov esi,[_ds_source] mov edi,[startdest] mov ebp,[startfrac] test [firstbyte],1 jz levenstart ; ; map one extra pixel at start ; shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) add ebp,[qfracstep] ; advance frac pointer and ecx,4095 ; finish calculation for first pixel mov al,[esi+ecx] ; get first pixel mov dl,[eax] ; color translate first pixel mov [edi],dl inc edi jz hldone levenstart: ; ; set up for word mapping ; shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) add ebp,[qfracstep] ; advance frac pointer and ecx,4095 ; finish calculation for first pixel shld edx,ebp,22 ; begin calculating second pixel (y units) shld edx,ebp,6 ; begin calculating second pixel (x units) add ebp,[qfracstep] ; advance frac pointer and edx,4095 ; finish calculation for second pixel mov al,[esi+ecx] ; get first pixel mov bl,[esi+edx] ; get second pixel mov dl,[eax] ; color translate first pixel test [loopcount],0ffffffffh jnz hldoubleloop ; at least one pixels to map jmp hlchecklast lsinglepixel: mov eax,[_ds_colormap] mov esi,[_ds_source] mov edi,[startdest] mov ebp,[startfrac] shld ecx,ebp,22 ; begin calculating first pixel (y units) shld ecx,ebp,6 ; begin calculating first pixel (x units) and ecx,4095 ; finish calculation for first pixel mov al,[esi+ecx] ; get first pixel mov dl,[eax] ; color translate first pixel mov [edi],dl jmp hldone ALIGN 16 hldoubleloop: shld ecx,ebp,22 ; begin calculating third pixel (y units) mov dh,[ebx] ; color translate second pixel shld ecx,ebp,6 ; begin calculating third pixel (x units) hlpatch1: add ebp,12345678h ; advance frac pointer and ecx,4095 ; finish calculation for third pixel mov [edi],dx ; write two pixels shld edx,ebp,22 ; begin calculating fourth pixel (y units) add edi,2 ; advance to third pixel destination shld edx,ebp,6 ; begin calculating fourth pixel (x units) hlpatch2: add ebp,12345678h ; advance frac pointer and edx,4095 ; finish calculation for fourth pixel mov al,[esi+ecx] ; get third pixel mov bl,[esi+edx] ; get fourth pixel dec [loopcount] ; done with loop? mov dl,[eax] ; color translate third pixel jnz hldoubleloop ; ; check for final pixel at end ; hlchecklast: test [lastbyte],1 jnz hldone mov [edi],dl ; write final pixel hldone: mov ecx,[plane] inc ecx and ecx,1 jnz lnoinc inc [startdest] ; over to next byte lnoinc: cmp ecx,[startplane] je lalldone mov [plane],ecx mov ebx,[startfrac] add ebx,[fracstep] mov [startfrac],ebx ; advance frac to next pixel inc [firstx] jmp lplaneloop lalldone: popr ret ENDP END