home *** CD-ROM | disk | FTP | other *** search
/ Monster Media 1994 #1 / monster.zip / monster / PROG_PAS / XLIB_TP5.ZIP / UNITS / X_POLYGO.PAS < prev    next >
Pascal/Delphi Source File  |  1993-12-28  |  31KB  |  934 lines

  1. unit X_Polygon;
  2. (*-----------------------------------------------------------------------  *)
  3. (* MODULE XPOLYGON                                                         *)
  4. (*                                                                         *)
  5. (* Filled Triangle function for all MODE X 256 Color resolutions           *)
  6. (*                                                                         *)
  7. (*                                                                         *)
  8. (* ****** XLIB - Mode X graphics library                ****************   *)
  9. (* ******                                               ****************   *)
  10. (* ****** Written By Themie Gouthas                     ****************   *)
  11. (* ****** Converted by Christian Harms                  ****************   *)
  12. (*                                                                         *)
  13. (* This module is based on code developed by Steve Dollind for his         *)
  14. (* XSPACE game.                                                            *)
  15. (* Copyright (C) 1992 Steven Dollins  --  sdollins@uiuc.edu                *)
  16. (*                                                                         *)
  17. (*                                                                         *)
  18. (* egg@dstos3.dsto.gov.au or teg@bart.dsto.gov.au                          *)
  19. (* harms@mickey.informatik.uni-stuttgart.de                                *)
  20. (*-----------------------------------------------------------------------  *)
  21.  
  22. interface
  23.  
  24. type Point = record x,y:Word; end;
  25.  
  26. (*-----------------------------------------------------------------------  *)
  27. (* procedure x_triangle(X0,Y0,X1,Y1,X2,Y2:Word;Color:Byte);                *)
  28. (*                                                                         *)
  29. (*                                                                         *)
  30. (* Written by S. Dollins                                                   *)
  31.  
  32. procedure x_triangle(X0,Y0,X1,Y1,X2,Y2,Color:Word);
  33.  
  34. (* You can draw a triangle with different colors in every line. The colors *)
  35. (* are in a ColorTable:Array[Y0..GetMaxY] of Byte.                         *)
  36. procedure x_triangleCol(X0,Y0,X1,Y1,X2,Y2:Word;var ColorTable);
  37.  
  38. procedure x_poly(Var P:Array of Point;num,Color:Word);
  39. procedure x_polyCol(Var P:Array of Point;num:Word;Var Color);
  40.  
  41. implementation
  42.  
  43. uses X_Const;
  44.  
  45.  
  46. (*-----------------------------------------------------------------------  *)
  47. (* HLineClipR                                                              *)
  48. (*                                                                         *)
  49. (*       Draws a horizontal line from (X1, Y) to (X2, Y).                  *)
  50. (*       Uses Watcom Parameter passing convention in registers             *)
  51. (*                                                                         *)
  52. (*   X1 in AX                                                              *)
  53. (*   X2 in DX                                                              *)
  54. (*   Y in CX                                                               *)
  55. (*   Color in BX                                                           *)
  56. (*   PageOffset in DI                                                      *)
  57. (*                                                                         *)
  58. (* By Themie Gouthas - Adapted from x_fill_rect.                           *)
  59. (*-----------------------------------------------------------------------  *)
  60. procedure  HLineClipR; assembler;
  61.  
  62. (* Plane masks for clipping left and right edges of rectangle.             *)
  63. const    LeftClipPlaneMask  : Array[0..3] of Byte = ($0f,$0e,$0c,$08);
  64.     RightClipPlaneMask : Array[0..3] of Byte = ($0f,$01,$03,$07);
  65.  
  66. asm
  67.     push    di
  68.     cmp     dx,ax                (* if (X2 < X1) then assume no line   *)
  69.     jl      @@Invisible          (*   is visible                       *)
  70.  
  71.     cmp     cx,[TopClip]         (* if (Y < TopClip) then no line      *)
  72.     jl      @@Invisible
  73.  
  74.     cmp     cx,[BottomClip]      (*if (Y > BottomClip) then no line    *)
  75.     jg      @@Invisible
  76.  
  77.     mov     di,[RightClip]       (*convert RightClip to pixel coords   *)
  78.     sal     di,1
  79.     sal     di,1
  80.     cmp     ax,di                (* if (X1 > RightClip) then no line   *)
  81.     jg      @@Invisible
  82.  
  83.     cmp     dx,di                (* if (X2 > RightClip) then           *)
  84.     jle     @@ClipLeft           (*  X2:=RightClip                     *)
  85.     mov     dx,di
  86.  
  87. @@ClipLeft:
  88.     mov     di,[LeftClip]       (*convert LeftClip to pixel coords    *)
  89.     sal     di,1
  90.     sal     di,1
  91.         cmp     dx,di                (* if (X2 < LeftClip) then no line    *)
  92.         jl      @@Invisible
  93.  
  94.     cmp     ax,di                (*if (X1 > LeftClip) then were ready to plot *)
  95.     jge     @@DoLine
  96.  
  97.     mov     ax,di                (*  X1:=LeftClip                      *)
  98.         jmp     @@DoLine
  99.  
  100. @@Invisible:
  101.     pop     di
  102.     ret
  103.  
  104. @@DoLine:
  105.         pop     di                      (* di = PageOffset                 *)
  106.     xchg    cx,ax                   (* AX = Y,  CX = X1                *)
  107.         mov     si,dx                   (* SI = DX = X2                    *)
  108.     mul     [ScrnLogicalByteWidth]
  109.         mov     dx,si                   (* Reset DX to X1 since mul erases DX *)
  110.     add     ax,di
  111.     mov     di,cx
  112.     sar     di,1                    (* Convert to bytes                *)
  113.     sar     di,1
  114.     add     di,ax                   (* DI->First byte                  *)
  115.  
  116.         and     si,03h                  (* look up right edge plane mask   *)
  117.     mov     ah,[offset RightClipPlaneMask+si]
  118.     mov     si,cx                   (* look up left edge plane mask    *)
  119.     and     si,03h
  120.     mov     al,[offset LeftClipPlaneMask+si]
  121.  
  122.     cmp     dx,cx                   (* No harm in being paranoid..     *)
  123.     jle     @@Invisible2
  124.  
  125.     xchg    cx,dx                   (*CX=X2, DX=X1                     *)
  126.     dec     cx
  127.     and     dx,not 03h
  128.     sub     cx,dx
  129.         js      @@Invisible2
  130.     shr     cx,1
  131.     shr     cx,1
  132.     jnz     @@MasksSet
  133.     and     al,ah
  134. @@MasksSet:
  135.     mov     dl,bl                 (* set BX=Plane Masks, AH=Color      *)
  136.     mov     bx,ax
  137.     mov     ah,dl
  138.     mov     dx,SC_INDEX+1         (*set the Sequence Controller Index to *)
  139.     mov     al,bl
  140.     out     dx,al
  141.         mov     al,ah
  142.     stosb                         (* Plot left byte                    *)
  143.     dec     cx
  144.     js      @@Invisible2
  145.     jz      @@RightEnd
  146.  
  147.  
  148.     mov     al,0fh                (* plot middle bytes                 *)
  149.     out     dx,al
  150.         mov     al,ah
  151.         shr     cx,1
  152.     rep     stosw
  153.         adc     cx,cx
  154.         rep     stosb
  155.  
  156.  
  157.  
  158. @@RightEnd:
  159.     mov     al,bh              (* Plot right  byte                     *)
  160.     out     dx,al
  161.         mov     al,ah
  162.     stosb
  163. @@Invisible2:
  164. end;
  165.  
  166.  
  167. procedure x_triangle(X0,Y0,X1,Y1,X2,Y2,Color:Word);  assembler;
  168. var DX01,DY01,DX02,DY02,DX12,DY12,DP01,DP02,DP12,XA01,XA02,XA12:Word;
  169. asm
  170.     push    ds
  171.         push    es
  172.         push    si
  173.         push    di  (* Save es for polygon routine                        *)
  174.  
  175.     mov     ax,X0
  176.     mov     bx,Y0
  177.     mov     cx,X1
  178.     mov     dx,Y1
  179.  
  180.     cmp     bx,dx   (* Y0,Y1 *)
  181.     jl     @tri_Y0lY1
  182.     je     @tri_Y0eY1
  183.     xchg    ax,cx   (* X0,X1 *)
  184.     xchg    bx,dx   (* Y0,Y1 *)
  185. @tri_Y0lY1:
  186.     cmp     dx,Y2   (* Y1,Y2 *)
  187.     jg     @tri_a
  188.     jmp    @tri_sorted
  189. @tri_a: xchg    cx,X2   (* X1,X2 *)
  190.     xchg    dx,Y2   (* Y1,Y2 *)
  191.     cmp     bx,dx   (* Y0,Y1 *)
  192.     jge    @tri_b
  193.     jmp    @tri_sorted
  194. @tri_b: je     @tri_bot
  195.     xchg    ax,cx   (* X0,X1 *)
  196.     xchg    bx,dx   (* Y0,Y1 *)
  197.     jmp    @tri_sorted
  198. @tri_Y0eY1:
  199.     cmp     bx,Y2   (* Y0,Y2 *)
  200.     jl     @tri_bot
  201.     jg     @tri_c
  202.     jmp    @tri_done
  203. @tri_c: xchg    ax,X2   (* X0,X2 *)
  204.     xchg    bx,Y2   (* Y0,Y2 *)
  205.     jmp    @tri_sorted
  206.  
  207. @tri_bot:
  208.     cmp     ax,cx   (* X0,X1 *)
  209.     jl     @tri_bot_sorted
  210.     jg     @tri_bot_a
  211.     jmp    @tri_done
  212. @tri_bot_a:
  213.     xchg    ax,cx   (* X0,X1 *)
  214. @tri_bot_sorted:
  215.     cmp     bx,[BottomClip]
  216.     jle    @tri_bot_y0ok
  217.     jmp    @tri_done
  218. @tri_bot_y0ok:
  219.     mov     si,Y2
  220.     cmp     si,[TopClip]
  221.     jge    @tri_bot_y2ok
  222.     jmp    @tri_done
  223. @tri_bot_y2ok:
  224.     mov     X0,ax
  225.     mov     Y0,bx
  226.     mov     X1,cx
  227.     mov     Y1,dx
  228.  
  229.     mov     bx,Y2   (*    bx <- Y2                *)
  230.     sub     bx,Y0   (*    bx <- Y2 - Y0           *)
  231.     mov     DY02,bx (*  DY02 <- Y2 - Y0           *)
  232.     mov     ax,X2   (*    ax <- X2                *)
  233.     sub     ax,X0   (*    ax <- X2 - X0           *)
  234.     mov     DX02,ax (*  DX02 <- X2 - X0           *)
  235.     mov     cx,ax   (*    cx <- DX02              *)
  236.     cwd             (* dx:ax <- DX02              *)
  237.     idiv    bx      (*    ax <- DX02 / DY02       *)
  238.     cmp     cx,0
  239.     jge    @tri_bot02
  240.     dec     ax      (*    ax <- DX02 / DY02 - 1   *)
  241. @tri_bot02:
  242.     mov     XA02,ax (*  XA02 <- DX02 / DY02       *)
  243.     imul    bx      (*    ax <- XA02 * DY02       *)
  244.     sub     cx,ax   (*    cx <- DX02 - XA02 * DY02*)
  245.     mov     DP02,cx (*  DP02 <- DX02 - XA02 * DY02*)
  246.  
  247.     mov     bx,Y2   (*    bx <- Y2                *)
  248.     sub     bx,Y1   (*    bx <- Y2 - Y1           *)
  249.     mov     DY12,bx (*  DY02 <- Y2 - Y1           *)
  250.     mov     ax,X2   (*    ax <- X2                *)
  251.     sub     ax,X1   (*    ax <- X2 - X1           *)
  252.     mov     DX12,ax (*  DX12 <- X2 - X1           *)
  253.     mov     cx,ax   (*    cx <- DX12              *)
  254.     cwd             (* dx:ax <- DX12              *)
  255.     idiv    bx      (*    ax <- DX12 / DY12       *)
  256.     cmp     cx,0
  257.     jge    @tri_bot12
  258.     dec     ax      (*    ax <- DX12 / DY12 - 1   *)
  259. @tri_bot12:
  260.     mov     XA12,ax (*  XA12 <- DX12 / DY12       *)
  261.     imul    bx      (*    ax <- XA12 * DY12       *)
  262.     sub     cx,ax   (*    cx <- DX12 - XA12 * DY12*)
  263.     mov     DP12,cx (*  DP12 <- DX12 - XA12 * DY12*)
  264.  
  265.     mov     ax,0    (* PL <- 0                    *)
  266.     mov     bx,0    (* PS <- 0                    *)
  267.     mov     cx,Y0   (*  Y <- Y0                   *)
  268.     mov     si,X0
  269.     mov     di,X1
  270.     dec     di
  271. @tri_bot_loop:
  272.     inc     cx      (* Y                          *)
  273.  
  274.     add     ax,DP02 (* PL,DP02                    *)
  275.     jle    @tri_bot_shortl
  276.     sub     ax,DY02 (* PL,DY02                    *)
  277.     inc     si      (* XL                         *)
  278. @tri_bot_shortl:
  279.     add     si,XA02 (* XL,XA02                    *)
  280.  
  281.     add     bx,DP12 (* PS,DP12                    *)
  282.     jle    @tri_bot_shortr
  283.     sub     bx,DY12 (* PS,DY12                    *)
  284.     inc     di      (* XS                         *)
  285. @tri_bot_shortr:
  286.     add     di,XA12 (* XS,XA12                    *)
  287.  
  288.     push    di      (* XS                         *)
  289.     push    si      (* XL                         *)
  290.     cmp     cx,Y2   (* Y,Y2                       *)
  291.     jl     @tri_bot_loop
  292.  
  293.     jmp    @tri_draw_lines
  294.  
  295.  
  296. @tri_sorted:
  297.     cmp     bx,[BottomClip]
  298.     jle    @tri_y0ok
  299.     jmp    @tri_done
  300. @tri_y0ok:
  301.     mov     si,Y2
  302.     cmp     si,[TopClip]
  303.     jge    @tri_y2ok
  304.     jmp    @tri_done
  305. @tri_y2ok:
  306.     mov     X0,ax
  307.     mov     Y0,bx
  308.     mov     X1,cx
  309.     mov     Y1,dx
  310.  
  311.     mov     bx,dx   (*    bx <- Y1                *)
  312.     sub     bx,Y0   (*    bx <- Y1 - Y0           *)
  313.     mov     DY01,bx (*  DY01 <- Y1 - Y0           *)
  314.     mov     ax,X1   (*    ax <- X1                *)
  315.     sub     ax,X0   (*    ax <- X1 - X0           *)
  316.     mov     DX01,ax (*  DX01 <- X1 - X0           *)
  317.     mov     cx,ax   (*    cx <- DX01              *)
  318.     cwd             (* dx:ax <- DX01              *)
  319.     idiv    bx      (*    ax <- DX01 / DY01       *)
  320.     cmp     cx,0    (*  DX01 ? 0                  *)
  321.     jge    @tri_psl01
  322.     dec     ax      (*    ax <- DX01 / DY01 - 1   *)
  323. @tri_psl01:
  324.     mov     XA01,ax (*  XA01 <- DX01 / DY01       *)
  325.     imul    bx      (*    ax <- XA01 * DY01       *)
  326.     sub     cx,ax   (*    cx <- DX01 - XA01 * DY01*)
  327.     mov     DP01,cx (*  DP01 <- DX01 - XA01 * DY01*)
  328.  
  329.     mov     bx,Y2   (*    bx <- Y2                *)
  330.     sub     bx,Y0   (*    bx <- Y2 - Y0           *)
  331.     mov     DY02,bx (*  DY02 <- Y2 - Y0           *)
  332.     mov     ax,X2   (*    ax <- X2                *)
  333.     sub     ax,X0   (*    ax <- X2 - X0           *)
  334.     mov     DX02,ax (*  DX02 <- X2 - X0           *)
  335.     mov     cx,ax   (*    cx <- DX02              *)
  336.     cwd             (* dx:ax <- DX02              *)
  337.     idiv    bx      (*    ax <- DX02 / DY02       *)
  338.     cmp     cx,0
  339.     jge    @tri_psl02
  340.     dec     ax      (*    ax <- DX02 / DY02 - 1   *)
  341. @tri_psl02:
  342.     mov     XA02,ax (*  XA02 <- DX02 / DY02       *)
  343.     imul    bx      (*    ax <- XA02 * DY02       *)
  344.     sub     cx,ax   (*    cx <- DX02 - XA02 * DY02*)
  345.     mov     DP02,cx (*  DP02 <- DX02 - XA02 * DY02*)
  346.  
  347.     mov     bx,Y2   (*    bx <- Y2                *)
  348.     sub     bx,Y1   (*    bx <- Y2 - Y1           *)
  349.     jle    @tri_const_computed
  350.     mov     DY12,bx (*  DY12 <- Y2 - Y1           *)
  351.     mov     ax,X2   (*    ax <- X2                *)
  352.     sub     ax,X1   (*    ax <- X2 - X1           *)
  353.     mov     DX12,ax (*  DX12 <- X2 - X1           *)
  354.     mov     cx,ax   (*    cx <- DX12              *)
  355.     cwd             (* dx:ax <- DX12              *)
  356.     idiv    bx      (*    ax <- DX12 / DY12       *)
  357.     cmp     cx,0
  358.     jge    @tri_psl12
  359.     dec     ax      (*    ax <- DX12 / DY12 - 1   *)
  360. @tri_psl12:
  361.     mov     XA12,ax (*  XA12 <- DX12 / DY12       *)
  362.     imul    bx      (*    ax <- XA12 * DY12       *)
  363.     sub     cx,ax   (*    cx <- DX12 - XA12 * DY12*)
  364.     mov     DP12,cx (*  DP12 <- DX12 - XA12 * DY12*)
  365.  
  366. @tri_const_computed:
  367.     mov     ax,DX01
  368.     imul    word ptr DY02
  369.     mov     bx,ax
  370.     mov     cx,dx   (* DX01 * DY02 in cx:bx       *)
  371.  
  372.     mov     ax,DX02
  373.     imul    word ptr DY01 (* DX02 * DY01 in dx:ax *)
  374.     cmp     cx,dx
  375.     jg     @tri_pt1rt
  376.     jl     @tri_pt1lt
  377.     cmp     bx,ax
  378.     ja     @tri_pt1rt
  379.     jb     @tri_pt1lt
  380.     jmp    @tri_done
  381.  
  382. (*------------------------------------                *)
  383. (* Short sides are on the left                        *)
  384. (*                                                    *)
  385. @tri_pt1lt:
  386.     mov     ax,0    (* PL <- 0                    *)
  387.     mov     bx,0    (* PS <- 0                    *)
  388.     mov     cx,Y0   (*  Y <- Y0                   *)
  389.     mov     si,X0
  390.     mov     di,si
  391.     dec     si
  392. @tri_lt_loop:
  393.     inc     cx      (* Y                          *)
  394.  
  395.     add     ax,DP02 (* PL,DP02                    *)
  396.     jle    @tri_lt_shortl
  397.     sub     ax,DY02 (* PL,DY02                    *)
  398.     inc     si      (* XL                         *)
  399. @tri_lt_shortl:
  400.     add     si,XA02 (* XL,XA02                    *)
  401.  
  402.     add     bx,DP01 (* PS,DP01                    *)
  403.     jle    @tri_lt_shortr
  404.     sub     bx,DY01 (* PS,DY01                    *)
  405.     inc     di      (* XS                         *)
  406. @tri_lt_shortr:
  407.     add     di,XA01 (* XS,XA01                    *)
  408.  
  409.     push    si      (* XL                         *)
  410.     push    di      (* XS                         *)
  411.     cmp     cx,Y1   (* Y,Y1                       *)
  412.     jl     @tri_lt_loop
  413.  
  414.     jmp    @tri_lb_start
  415. @tri_lb_loop:
  416.     inc     cx      (* Y                          *)
  417.  
  418.     add     ax,DP02 (* PL,DP02                    *)
  419.     jle    @tri_lb_shortl
  420.     sub     ax,DY02 (* PL,DY02                    *)
  421.     inc     si      (* XL                         *)
  422. @tri_lb_shortl:
  423.     add     si,XA02 (* XL,XA02                    *)
  424.  
  425.     add     bx,DP12 (* PS,DP12                    *)
  426.     jle    @tri_lb_shortr
  427.     sub     bx,DY12 (* PS,DY12                    *)
  428.     inc     di      (* XS                         *)
  429. @tri_lb_shortr:
  430.     add     di,XA12 (* XS,XA12                    *)
  431.  
  432.     push    si      (* XL                         *)
  433.     push    di      (* XS                         *)
  434. @tri_lb_start:
  435.     cmp     cx,Y2   (* Y,Y2                       *)
  436.     jl     @tri_lb_loop
  437.     jmp    @tri_draw_lines
  438.  
  439. (*------------------------------------                *)
  440. (* short sides are on the right                       *)
  441. (*                                                    *)
  442. @tri_pt1rt:
  443.     mov     ax,0    (* PL <- 0                    *)
  444.     mov     bx,0    (* PS <- 0                    *)
  445.     mov     cx,Y0   (*  Y <- Y0                   *)
  446.     mov     si,X0
  447.     mov     di,si
  448.     dec     di
  449. @tri_rt_loop:
  450.     inc     cx      (* Y                          *)
  451.  
  452.     add     ax,DP02 (* PL,DP02                    *)
  453.     jle    @tri_rt_shortl
  454.     sub     ax,DY02 (* PL,DY02                    *)
  455.     inc     si      (* XL                         *)
  456. @tri_rt_shortl:
  457.     add     si,XA02 (* XL,XA02                    *)
  458.  
  459.     add     bx,DP01 (* PS,DP01                    *)
  460.     jle    @tri_rt_shortr
  461.     sub     bx,DY01 (* PS,DY01                    *)
  462.     inc     di      (* XS                         *)
  463. @tri_rt_shortr:
  464.     add     di,XA01 (* XS,XA01                    *)
  465.  
  466.     push    di      (* XS                         *)
  467.     push    si      (* XL                         *)
  468.     cmp     cx,Y1   (* Y,Y1                       *)
  469.     jl     @tri_rt_loop
  470.  
  471.     jmp    @tri_rb_start
  472. @tri_rb_loop:
  473.     inc     cx      (* Y                          *)
  474.  
  475.     add     ax,DP02 (* PL,DP02                    *)
  476.     jle    @tri_rb_shortl
  477.     sub     ax,DY02 (* PL,DY02                    *)
  478.     inc     si      (* XL                         *)
  479. @tri_rb_shortl:
  480.     add     si,XA02 (* XL,XA02                    *)
  481.  
  482.     add     bx,DP12 (* PS,DP12                    *)
  483.     jle    @tri_rb_shorts
  484.     sub     bx,DY12 (* PS,DY12                    *)
  485.     inc     di      (* XS                         *)
  486. @tri_rb_shorts:
  487.     add     di,XA12 (* XS,XA12                    *)
  488.  
  489.     push    di      (* XS                         *)
  490.     push    si      (* XL                         *)
  491. @tri_rb_start:
  492.     cmp     cx,Y2   (* Y,Y2                       *)
  493.     jl     @tri_rb_loop
  494.  
  495. (*------------------------------------                *)
  496. (* Draw the horizontal lines                          *)
  497. (*                                                    *)
  498.  
  499.  
  500. @tri_draw_lines:
  501.  
  502.     mov     cx,SCREEN_SEG       (*point ES to video segment            *)
  503.     mov     es,cx
  504.     mov     dx,SC_INDEX         (*set the Sequence Controller Index to *)
  505.     mov     al,MAP_MASK         (* point to the Map Mask register      *)
  506.     out     dx,al
  507.  
  508.  
  509. @line_loop:
  510.     pop     ax
  511.     pop     dx
  512.     cmp     ax,dx
  513.     jg     @tri_draw_next
  514.     mov     bx,Color
  515.     mov     cx,Y2
  516.     add     dx,2
  517.     mov     di,ScreenOfs
  518.     call    HLineClipR
  519. @tri_draw_next:
  520.     dec     word ptr Y2
  521.     dec     word ptr DY02
  522.     jnz    @line_loop
  523.  
  524. @tri_done:
  525.     pop     di
  526.         pop     si
  527.         pop     es
  528.         pop     ds
  529. end;
  530.  
  531.  
  532.  
  533. procedure x_triangleCol(X0,Y0,X1,Y1,X2,Y2:Word;var ColorTable);  assembler;
  534. var DX01,DY01,DX02,DY02,DX12,DY12,DP01,DP02,DP12,XA01,XA02,XA12:Word;
  535. asm
  536.     push    ds
  537.         push    es
  538.         push    si
  539.         push    di  (* Save es for polygon routine                        *)
  540.  
  541.     mov     ax,X0
  542.     mov     bx,Y0
  543.     mov     cx,X1
  544.     mov     dx,Y1
  545.  
  546.     cmp     bx,dx   (* Y0,Y1 *)
  547.     jl     @tri_Y0lY1
  548.     je     @tri_Y0eY1
  549.     xchg    ax,cx   (* X0,X1 *)
  550.     xchg    bx,dx   (* Y0,Y1 *)
  551. @tri_Y0lY1:
  552.     cmp     dx,Y2   (* Y1,Y2 *)
  553.     jg     @tri_a
  554.     jmp    @tri_sorted
  555. @tri_a: xchg    cx,X2   (* X1,X2 *)
  556.     xchg    dx,Y2   (* Y1,Y2 *)
  557.     cmp     bx,dx   (* Y0,Y1 *)
  558.     jge    @tri_b
  559.     jmp    @tri_sorted
  560. @tri_b: je     @tri_bot
  561.     xchg    ax,cx   (* X0,X1 *)
  562.     xchg    bx,dx   (* Y0,Y1 *)
  563.     jmp    @tri_sorted
  564. @tri_Y0eY1:
  565.     cmp     bx,Y2   (* Y0,Y2 *)
  566.     jl     @tri_bot
  567.     jg     @tri_c
  568.     jmp    @tri_done
  569. @tri_c: xchg    ax,X2   (* X0,X2 *)
  570.     xchg    bx,Y2   (* Y0,Y2 *)
  571.     jmp    @tri_sorted
  572.  
  573. @tri_bot:
  574.     cmp     ax,cx   (* X0,X1 *)
  575.     jl     @tri_bot_sorted
  576.     jg     @tri_bot_a
  577.     jmp    @tri_done
  578. @tri_bot_a:
  579.     xchg    ax,cx   (* X0,X1 *)
  580. @tri_bot_sorted:
  581.     cmp     bx,[BottomClip]
  582.     jle    @tri_bot_y0ok
  583.     jmp    @tri_done
  584. @tri_bot_y0ok:
  585.     mov     si,Y2
  586.     cmp     si,[TopClip]
  587.     jge    @tri_bot_y2ok
  588.     jmp    @tri_done
  589. @tri_bot_y2ok:
  590.     mov     X0,ax
  591.     mov     Y0,bx
  592.     mov     X1,cx
  593.     mov     Y1,dx
  594.  
  595.     mov     bx,Y2   (*    bx <- Y2                *)
  596.     sub     bx,Y0   (*    bx <- Y2 - Y0           *)
  597.     mov     DY02,bx (*  DY02 <- Y2 - Y0           *)
  598.     mov     ax,X2   (*    ax <- X2                *)
  599.     sub     ax,X0   (*    ax <- X2 - X0           *)
  600.     mov     DX02,ax (*  DX02 <- X2 - X0           *)
  601.     mov     cx,ax   (*    cx <- DX02              *)
  602.     cwd             (* dx:ax <- DX02              *)
  603.     idiv    bx      (*    ax <- DX02 / DY02       *)
  604.     cmp     cx,0
  605.     jge    @tri_bot02
  606.     dec     ax      (*    ax <- DX02 / DY02 - 1   *)
  607. @tri_bot02:
  608.     mov     XA02,ax (*  XA02 <- DX02 / DY02       *)
  609.     imul    bx      (*    ax <- XA02 * DY02       *)
  610.     sub     cx,ax   (*    cx <- DX02 - XA02 * DY02*)
  611.     mov     DP02,cx (*  DP02 <- DX02 - XA02 * DY02*)
  612.  
  613.     mov     bx,Y2   (*    bx <- Y2                *)
  614.     sub     bx,Y1   (*    bx <- Y2 - Y1           *)
  615.     mov     DY12,bx (*  DY02 <- Y2 - Y1           *)
  616.     mov     ax,X2   (*    ax <- X2                *)
  617.     sub     ax,X1   (*    ax <- X2 - X1           *)
  618.     mov     DX12,ax (*  DX12 <- X2 - X1           *)
  619.     mov     cx,ax   (*    cx <- DX12              *)
  620.     cwd             (* dx:ax <- DX12              *)
  621.     idiv    bx      (*    ax <- DX12 / DY12       *)
  622.     cmp     cx,0
  623.     jge    @tri_bot12
  624.     dec     ax      (*    ax <- DX12 / DY12 - 1   *)
  625. @tri_bot12:
  626.     mov     XA12,ax (*  XA12 <- DX12 / DY12       *)
  627.     imul    bx      (*    ax <- XA12 * DY12       *)
  628.     sub     cx,ax   (*    cx <- DX12 - XA12 * DY12*)
  629.     mov     DP12,cx (*  DP12 <- DX12 - XA12 * DY12*)
  630.  
  631.     mov     ax,0    (* PL <- 0                    *)
  632.     mov     bx,0    (* PS <- 0                    *)
  633.     mov     cx,Y0   (*  Y <- Y0                   *)
  634.     mov     si,X0
  635.     mov     di,X1
  636.     dec     di
  637. @tri_bot_loop:
  638.     inc     cx      (* Y                          *)
  639.  
  640.     add     ax,DP02 (* PL,DP02                    *)
  641.     jle    @tri_bot_shortl
  642.     sub     ax,DY02 (* PL,DY02                    *)
  643.     inc     si      (* XL                         *)
  644. @tri_bot_shortl:
  645.     add     si,XA02 (* XL,XA02                    *)
  646.  
  647.     add     bx,DP12 (* PS,DP12                    *)
  648.     jle    @tri_bot_shortr
  649.     sub     bx,DY12 (* PS,DY12                    *)
  650.     inc     di      (* XS                         *)
  651. @tri_bot_shortr:
  652.     add     di,XA12 (* XS,XA12                    *)
  653.  
  654.     push    di      (* XS                         *)
  655.     push    si      (* XL                         *)
  656.     cmp     cx,Y2   (* Y,Y2                       *)
  657.     jl     @tri_bot_loop
  658.  
  659.     jmp    @tri_draw_lines
  660.  
  661.  
  662. @tri_sorted:
  663.     cmp     bx,[BottomClip]
  664.     jle    @tri_y0ok
  665.     jmp    @tri_done
  666. @tri_y0ok:
  667.     mov     si,Y2
  668.     cmp     si,[TopClip]
  669.     jge    @tri_y2ok
  670.     jmp    @tri_done
  671. @tri_y2ok:
  672.     mov     X0,ax
  673.     mov     Y0,bx
  674.     mov     X1,cx
  675.     mov     Y1,dx
  676.  
  677.     mov     bx,dx   (*    bx <- Y1                *)
  678.     sub     bx,Y0   (*    bx <- Y1 - Y0           *)
  679.     mov     DY01,bx (*  DY01 <- Y1 - Y0           *)
  680.     mov     ax,X1   (*    ax <- X1                *)
  681.     sub     ax,X0   (*    ax <- X1 - X0           *)
  682.     mov     DX01,ax (*  DX01 <- X1 - X0           *)
  683.     mov     cx,ax   (*    cx <- DX01              *)
  684.     cwd             (* dx:ax <- DX01              *)
  685.     idiv    bx      (*    ax <- DX01 / DY01       *)
  686.     cmp     cx,0    (*  DX01 ? 0                  *)
  687.     jge    @tri_psl01
  688.     dec     ax      (*    ax <- DX01 / DY01 - 1   *)
  689. @tri_psl01:
  690.     mov     XA01,ax (*  XA01 <- DX01 / DY01       *)
  691.     imul    bx      (*    ax <- XA01 * DY01       *)
  692.     sub     cx,ax   (*    cx <- DX01 - XA01 * DY01*)
  693.     mov     DP01,cx (*  DP01 <- DX01 - XA01 * DY01*)
  694.  
  695.     mov     bx,Y2   (*    bx <- Y2                *)
  696.     sub     bx,Y0   (*    bx <- Y2 - Y0           *)
  697.     mov     DY02,bx (*  DY02 <- Y2 - Y0           *)
  698.     mov     ax,X2   (*    ax <- X2                *)
  699.     sub     ax,X0   (*    ax <- X2 - X0           *)
  700.     mov     DX02,ax (*  DX02 <- X2 - X0           *)
  701.     mov     cx,ax   (*    cx <- DX02              *)
  702.     cwd             (* dx:ax <- DX02              *)
  703.     idiv    bx      (*    ax <- DX02 / DY02       *)
  704.     cmp     cx,0
  705.     jge    @tri_psl02
  706.     dec     ax      (*    ax <- DX02 / DY02 - 1   *)
  707. @tri_psl02:
  708.     mov     XA02,ax (*  XA02 <- DX02 / DY02       *)
  709.     imul    bx      (*    ax <- XA02 * DY02       *)
  710.     sub     cx,ax   (*    cx <- DX02 - XA02 * DY02*)
  711.     mov     DP02,cx (*  DP02 <- DX02 - XA02 * DY02*)
  712.  
  713.     mov     bx,Y2   (*    bx <- Y2                *)
  714.     sub     bx,Y1   (*    bx <- Y2 - Y1           *)
  715.     jle    @tri_const_computed
  716.     mov     DY12,bx (*  DY12 <- Y2 - Y1           *)
  717.     mov     ax,X2   (*    ax <- X2                *)
  718.     sub     ax,X1   (*    ax <- X2 - X1           *)
  719.     mov     DX12,ax (*  DX12 <- X2 - X1           *)
  720.     mov     cx,ax   (*    cx <- DX12              *)
  721.     cwd             (* dx:ax <- DX12              *)
  722.     idiv    bx      (*    ax <- DX12 / DY12       *)
  723.     cmp     cx,0
  724.     jge    @tri_psl12
  725.     dec     ax      (*    ax <- DX12 / DY12 - 1   *)
  726. @tri_psl12:
  727.     mov     XA12,ax (*  XA12 <- DX12 / DY12       *)
  728.     imul    bx      (*    ax <- XA12 * DY12       *)
  729.     sub     cx,ax   (*    cx <- DX12 - XA12 * DY12*)
  730.     mov     DP12,cx (*  DP12 <- DX12 - XA12 * DY12*)
  731.  
  732. @tri_const_computed:
  733.     mov     ax,DX01
  734.     imul    word ptr DY02
  735.     mov     bx,ax
  736.     mov     cx,dx   (* DX01 * DY02 in cx:bx       *)
  737.  
  738.     mov     ax,DX02
  739.     imul    word ptr DY01 (* DX02 * DY01 in dx:ax *)
  740.     cmp     cx,dx
  741.     jg     @tri_pt1rt
  742.     jl     @tri_pt1lt
  743.     cmp     bx,ax
  744.     ja     @tri_pt1rt
  745.     jb     @tri_pt1lt
  746.     jmp    @tri_done
  747.  
  748. (*------------------------------------                *)
  749. (* Short sides are on the left                        *)
  750. (*                                                    *)
  751. @tri_pt1lt:
  752.     mov     ax,0    (* PL <- 0                    *)
  753.     mov     bx,0    (* PS <- 0                    *)
  754.     mov     cx,Y0   (*  Y <- Y0                   *)
  755.     mov     si,X0
  756.     mov     di,si
  757.     dec     si
  758. @tri_lt_loop:
  759.     inc     cx      (* Y                          *)
  760.  
  761.     add     ax,DP02 (* PL,DP02                    *)
  762.     jle    @tri_lt_shortl
  763.     sub     ax,DY02 (* PL,DY02                    *)
  764.     inc     si      (* XL                         *)
  765. @tri_lt_shortl:
  766.     add     si,XA02 (* XL,XA02                    *)
  767.  
  768.     add     bx,DP01 (* PS,DP01                    *)
  769.     jle    @tri_lt_shortr
  770.     sub     bx,DY01 (* PS,DY01                    *)
  771.     inc     di      (* XS                         *)
  772. @tri_lt_shortr:
  773.     add     di,XA01 (* XS,XA01                    *)
  774.  
  775.     push    si      (* XL                         *)
  776.     push    di      (* XS                         *)
  777.     cmp     cx,Y1   (* Y,Y1                       *)
  778.     jl     @tri_lt_loop
  779.  
  780.     jmp    @tri_lb_start
  781. @tri_lb_loop:
  782.     inc     cx      (* Y                          *)
  783.  
  784.     add     ax,DP02 (* PL,DP02                    *)
  785.     jle    @tri_lb_shortl
  786.     sub     ax,DY02 (* PL,DY02                    *)
  787.     inc     si      (* XL                         *)
  788. @tri_lb_shortl:
  789.     add     si,XA02 (* XL,XA02                    *)
  790.  
  791.     add     bx,DP12 (* PS,DP12                    *)
  792.     jle    @tri_lb_shortr
  793.     sub     bx,DY12 (* PS,DY12                    *)
  794.     inc     di      (* XS                         *)
  795. @tri_lb_shortr:
  796.     add     di,XA12 (* XS,XA12                    *)
  797.  
  798.     push    si      (* XL                         *)
  799.     push    di      (* XS                         *)
  800. @tri_lb_start:
  801.     cmp     cx,Y2   (* Y,Y2                       *)
  802.     jl     @tri_lb_loop
  803.     jmp    @tri_draw_lines
  804.  
  805. (*------------------------------------                *)
  806. (* short sides are on the right                       *)
  807. (*                                                    *)
  808. @tri_pt1rt:
  809.     mov     ax,0    (* PL <- 0                    *)
  810.     mov     bx,0    (* PS <- 0                    *)
  811.     mov     cx,Y0   (*  Y <- Y0                   *)
  812.     mov     si,X0
  813.     mov     di,si
  814.     dec     di
  815. @tri_rt_loop:
  816.     inc     cx      (* Y                          *)
  817.  
  818.     add     ax,DP02 (* PL,DP02                    *)
  819.     jle    @tri_rt_shortl
  820.     sub     ax,DY02 (* PL,DY02                    *)
  821.     inc     si      (* XL                         *)
  822. @tri_rt_shortl:
  823.     add     si,XA02 (* XL,XA02                    *)
  824.  
  825.     add     bx,DP01 (* PS,DP01                    *)
  826.     jle    @tri_rt_shortr
  827.     sub     bx,DY01 (* PS,DY01                    *)
  828.     inc     di      (* XS                         *)
  829. @tri_rt_shortr:
  830.     add     di,XA01 (* XS,XA01                    *)
  831.  
  832.     push    di      (* XS                         *)
  833.     push    si      (* XL                         *)
  834.     cmp     cx,Y1   (* Y,Y1                       *)
  835.     jl     @tri_rt_loop
  836.  
  837.     jmp    @tri_rb_start
  838. @tri_rb_loop:
  839.     inc     cx      (* Y                          *)
  840.  
  841.     add     ax,DP02 (* PL,DP02                    *)
  842.     jle    @tri_rb_shortl
  843.     sub     ax,DY02 (* PL,DY02                    *)
  844.     inc     si      (* XL                         *)
  845. @tri_rb_shortl:
  846.     add     si,XA02 (* XL,XA02                    *)
  847.  
  848.     add     bx,DP12 (* PS,DP12                    *)
  849.     jle    @tri_rb_shorts
  850.     sub     bx,DY12 (* PS,DY12                    *)
  851.     inc     di      (* XS                         *)
  852. @tri_rb_shorts:
  853.     add     di,XA12 (* XS,XA12                    *)
  854.  
  855.     push    di      (* XS                         *)
  856.     push    si      (* XL                         *)
  857. @tri_rb_start:
  858.     cmp     cx,Y2   (* Y,Y2                       *)
  859.     jl     @tri_rb_loop
  860.  
  861. (*------------------------------------                *)
  862. (* Draw the horizontal lines                          *)
  863. (*                                                    *)
  864.  
  865.  
  866. @tri_draw_lines:
  867.  
  868.     mov     cx,SCREEN_SEG       (*point ES to video segment            *)
  869.     mov     es,cx
  870.     mov     dx,SC_INDEX         (*set the Sequence Controller Index to *)
  871.     mov     al,MAP_MASK         (* point to the Map Mask register      *)
  872.     out     dx,al
  873.  
  874.  
  875. @line_loop:
  876.     pop     ax
  877.     pop     dx
  878.     cmp     ax,dx
  879.     jg     @tri_draw_next
  880.     mov     cx,Y2
  881.     add     dx,2
  882.  
  883.         push    ds
  884.         lds     di,dword ptr [ColorTable]
  885.         add     di,cx
  886.     mov     bx,ds:[di]
  887.         pop     ds
  888.  
  889.     mov     di,ScreenOfs
  890.     call    HLineClipR
  891. @tri_draw_next:
  892.     dec     word ptr Y2
  893.     dec     word ptr DY02
  894.     jnz    @line_loop
  895.  
  896. @tri_done:
  897.     pop     di
  898.         pop     si
  899.         pop     es
  900.         pop     ds
  901. end;
  902.  
  903. (*-----------------------------------------------------------------------  *)
  904. (*                                                                         *)
  905. (* Written by T. Gouthas                                                   *)
  906. (*                                                                         *)
  907. (* Note: This is just a quick hack of a generalized polygon routine.       *)
  908. (*   The way it works is by splitting up polygons into triangles and       *)
  909. (*   drawing each individual triangle.                                     *)
  910. (*                                                                         *)
  911. (* Obviously this is not as fast as it could be, but for polygons of       *)
  912. (* 4 vertices it should perform quite respectably.                         *)
  913. (*                                                                         *)
  914. (* Warning: Only works for convex polygons (convex polygons are such       *)
  915. (*  that if you draw a line from any two vertices, every point on that     *)
  916. (*  line will be within the polygon)                                       *)
  917. (*                                                                         *)
  918. (* Type Point see at the begin of this file.                               *)
  919.  
  920. procedure x_poly(Var P:Array of Point;num,Color:Word);
  921. var i:Word;
  922. begin;
  923.   for i:=1 to num-1 do
  924.     x_triangle(P[0].x,P[0].y,P[i].x,P[i].y,P[i+1].x,P[i+1].y,Color);
  925. end;
  926.  
  927. procedure x_polyCol(Var P:Array of Point;num:Word;Var Color);
  928. var i:Word;
  929. begin;
  930.   for i:=1 to num-1 do
  931.     x_triangleCol(P[0].x,P[0].y,P[i].x,P[i].y,P[i+1].x,P[i+1].y,Color);
  932. end;
  933.  
  934. end.