1 ;-----------------------------------------------------------
\r
3 ; MXCC.ASM - Fast clip line function
\r
4 ; Copyright (c) 1994 by Alessandro Scotti
\r
6 ;-----------------------------------------------------------
\r
13 MX_TEXT SEGMENT USE16 PARA PUBLIC 'CODE'
\r
14 ASSUME cs:MX_TEXT, ds:NOTHING, es:NOTHING
\r
16 EXTRN mx_BytesPerLine : WORD
\r
17 EXTRN mx_VideoSegment : WORD
\r
19 EXTRN mx_ClipX1 : WORD
\r
20 EXTRN mx_ClipY1 : WORD
\r
21 EXTRN mx_ClipX2 : WORD
\r
22 EXTRN mx_ClipY2 : WORD
\r
24 tblGroups LABEL WORD
\r
41 tbl00 DW cc00, cc01, cc02, ccFF, cc04, cc05, cc06, ccFF, cc08, cc09, cc0A
\r
42 tbl10 DW cc10, ccFF, cc12, ccFF, cc14, ccFF, cc16, ccFF, cc18, ccFF, cc1A
\r
43 tbl20 DW cc20, cc21, ccFF, ccFF, cc24, cc25, ccFF, ccFF, cc28, cc29
\r
44 tbl40 DW cc40, cc41, cc42, ccFF, ccFF, ccFF, ccFF, ccFF, cc48, cc49, cc4A
\r
45 tbl50 DW cc50, ccFF, cc52, ccFF, ccFF, ccFF, ccFF, ccFF, cc58, ccFF, cc5A
\r
46 tbl60 DW cc60, cc61, ccFF, ccFF, ccFF, ccFF, ccFF, ccFF, cc68, cc69
\r
47 tbl80 DW cc80, cc81, cc82, ccFF, cc84, cc85, cc86
\r
48 tbl90 DW cc90, ccFF, cc92, ccFF, cc94, ccFF, cc96
\r
49 tblA0 DW ccA0, ccA1, ccFF, ccFF, ccA4, ccA5
\r
56 ; Group 00 -------------------------------------------------
\r
90 ; Group 10 -------------------------------------------------
\r
105 cmp bx, [mx_ClipY1]
\r
110 cmp bx, [mx_ClipY1]
\r
113 cmp cx, [mx_ClipX2]
\r
118 cmp bx, [mx_ClipY2]
\r
123 cmp bx, [mx_ClipY2]
\r
126 cmp cx, [mx_ClipX2]
\r
130 ; Group 20 -------------------------------------------------
\r
145 cmp bx, [mx_ClipY1]
\r
150 cmp bx, [mx_ClipY1]
\r
153 cmp cx, [mx_ClipX1]
\r
158 cmp bx, [mx_ClipY2]
\r
163 cmp bx, [mx_ClipY2]
\r
166 cmp cx, [mx_ClipX1]
\r
170 ; Group 40 -------------------------------------------------
\r
182 cmp di, [mx_ClipX1]
\r
185 cmp si, [mx_ClipY1]
\r
190 cmp di, [mx_ClipX2]
\r
198 cmp di, [mx_ClipX1]
\r
201 cmp si, [mx_ClipY2]
\r
206 cmp di, [mx_ClipX2]
\r
209 cmp si, [mx_ClipY2]
\r
214 ; Group 50 -------------------------------------------------
\r
224 cmp bx, [mx_ClipY1]
\r
229 cmp si, [mx_ClipY1]
\r
232 cmp di, [mx_ClipX1]
\r
237 cmp cx, [mx_ClipX1]
\r
240 cmp di, [mx_ClipX1]
\r
245 cmp bx, [mx_ClipY2]
\r
248 cmp bx, [mx_ClipY1]
\r
250 cmp si, [mx_ClipY2]
\r
254 ; Group 60 -------------------------------------------------
\r
264 cmp bx, [mx_ClipY1]
\r
269 cmp si, [mx_ClipY2]
\r
272 cmp di, [mx_ClipX2]
\r
277 cmp cx, [mx_ClipX2]
\r
280 cmp bx, [mx_ClipY1]
\r
285 cmp si, [mx_ClipY1]
\r
288 cmp bx, [mx_ClipY2]
\r
290 cmp si, [mx_ClipY2]
\r
294 cmp bx, [mx_ClipY1]
\r
298 ; Group 80 -------------------------------------------------
\r
310 cmp di, [mx_ClipX1]
\r
315 cmp di, [mx_ClipX2]
\r
323 cmp di, [mx_ClipX1]
\r
326 cmp si, [mx_ClipY1]
\r
331 cmp di, [mx_ClipX2]
\r
334 cmp si, [mx_ClipY1]
\r
338 ; Group 90 -------------------------------------------------
\r
348 cmp bx, [mx_ClipY2]
\r
353 cmp si, [mx_ClipY2]
\r
356 cmp di, [mx_ClipX1]
\r
361 cmp cx, [mx_ClipX1]
\r
364 cmp bx, [mx_ClipY2]
\r
369 cmp bx, [mx_ClipY1]
\r
372 cmp si, [mx_ClipY2]
\r
374 cmp bx, [mx_ClipY2]
\r
378 cmp si, [mx_ClipY1]
\r
382 ; Group A0 -------------------------------------------------
\r
392 cmp bx, [mx_ClipY2]
\r
397 cmp si, [mx_ClipY2]
\r
400 cmp di, [mx_ClipX2]
\r
405 cmp cx, [mx_ClipX2]
\r
408 cmp bx, [mx_ClipY2]
\r
413 cmp si, [mx_ClipY2]
\r
416 cmp bx, [mx_ClipY1]
\r
418 cmp si, [mx_ClipY1]
\r
422 cmp bx, [mx_ClipY2]
\r
426 ; Y1 = (Y2-Y1)*(mx_ClipX1-X1)/(X2-X1)+Y1 = (SI-BX)*(mx_ClipX1-DI)/(CX-DI)+BX
\r
431 mov dx, [mx_ClipX1]
\r
438 mov di, [mx_ClipX1]
\r
442 ; Y1 = (Y2-Y1)*(mx_ClipX2-X1)/(X2-X1)+Y1 = (SI-BX)*(mx_ClipX2-DI)/(CX-DI)+BX
\r
447 mov dx, [mx_ClipX2]
\r
454 mov di, [mx_ClipX2]
\r
458 ; X1 = (X2-X1)*(mx_ClipY2-Y1)/(Y2-Y1)+X1 = (CX-DI)*(mx_ClipY2-BX)/(SI-BX)+DI
\r
463 mov dx, [mx_ClipY2]
\r
470 mov bx, [mx_ClipY2]
\r
474 ; X1 = (X2-X1)*(mx_ClipY1-Y1)/(Y2-Y1)+X1 = (CX-DI)*(mx_ClipY1-BX)/(SI-BX)+DI
\r
479 mov dx, [mx_ClipY1]
\r
486 mov bx, [mx_ClipY1]
\r
490 ; Y2 = (Y1-Y2)*(mx_ClipX1-X2)/(X1-X2)+Y2 = (BX-SI)*(mx_ClipX1-CX)/(DI-CX)+SI
\r
495 mov dx, [mx_ClipX1]
\r
502 mov cx, [mx_ClipX1]
\r
506 ; Y2 = (Y1-Y2)*(mx_ClipX2-X2)/(X1-X2)+Y2 = (BX-SI)*(mx_ClipX2-CX)/(DI-CX)+SI
\r
511 mov dx, [mx_ClipX2]
\r
518 mov cx, [mx_ClipX2]
\r
522 ; X2 = (X1-X2)*(mx_ClipY2-Y2)/(Y1-Y2)+X2 = (DI-CX)*(mx_ClipY2-SI)/(BX-SI)+CX
\r
527 mov dx, [mx_ClipY2]
\r
534 mov si, [mx_ClipY2]
\r
538 ; X2 = (X1-X2)*(mx_ClipY1-Y2)/(Y1-Y2)+X2 = (DI-CX)*(mx_ClipY1-SI)/(BX-SI)+CX
\r
543 mov dx, [mx_ClipY1]
\r
550 mov si, [mx_ClipY1]
\r
554 ;-----------------------------------------------------------
\r
556 ; Checks the coordinates of a line against the active
\r
558 ; Uses the Sobkow-Pospisil-Yang (SPY) algorithm: this was
\r
559 ; supposed to be twice as fast as Cohen-Sutherland, but my
\r
560 ; tests show only a very small increase in speed and a noticeable
\r
561 ; increase of the program size! Maybe this is caused by the
\r
562 ; slow speed of VGA cards, so probably a better test should
\r
563 ; be performed with lines drawn in RAM.
\r
569 ; CF = set if line is full clipped
\r
570 ; AX, BX = clipped X1, Y1
\r
571 ; CX, DX = clipped X2, Y2
\r
575 xsubClipLine PROC NEAR
\r
577 xor si, si ; SPY code
\r
579 cmp dx, [mx_ClipY2]
\r
584 cmp dx, [mx_ClipY1]
\r
589 cmp cx, [mx_ClipX2]
\r
594 cmp cx, [mx_ClipX1]
\r
599 cmp bx, [mx_ClipY2]
\r
604 cmp bx, [mx_ClipY1]
\r
609 cmp ax, [mx_ClipX2]
\r
614 cmp ax, [mx_ClipX1]
\r
620 and di, 000Fh ; Index of procedure
\r
622 .shr si, 2 ; Index of group (times 4)
\r
623 cmp di, cs:tblGroups[si] ; Is index within range?
\r
624 jg @@Exit ; No, line is full clipped
\r
625 mov si, cs:tblGroups[si+2] ; Get offset of group table
\r
626 shl di, 1 ; We must index word elements
\r
627 add si, di ; Make full offset
\r
628 mov di, ax ; Move X1 to DI and free AX
\r
629 mov si, cs:[si] ; Get subroutine address
\r
630 xchg dx, si ; Move Y2 to SI and free DX
\r
631 call dx ; Call the proper subroutine
\r
632 mov ax, di ; Restore AX to X1
\r
633 mov dx, si ; Restore DX to Y2
\r