Subversion Repositories Kolibri OS

Rev

Rev 6134 | Rev 6243 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ; fill triangle profile
  2. ; #define PROFILE
  3.  
  4. CLIP_XMIN equ (1<<0)
  5. CLIP_XMAX equ (1<<1)
  6. CLIP_YMIN equ (1<<2)
  7. CLIP_YMAX equ (1<<3)
  8. CLIP_ZMIN equ (1<<4)
  9. CLIP_ZMAX equ (1<<5)
  10.  
  11. align 16
  12. proc gl_transform_to_viewport uses eax ebx ecx, context:dword,v:dword
  13. locals
  14.         point dd ?
  15. endl
  16.         mov eax,[context]
  17.         mov ebx,[v]
  18.  
  19.         ; coordinates
  20.         fld1
  21.         fdiv dword[ebx+offs_vert_pc+offs_W] ;st0 = 1/v.pc.W
  22.  
  23.         fld dword[ebx+offs_vert_pc+offs_X] ;st0 = v.pc.X
  24.         fmul st0,st1
  25.         fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_X]
  26.         fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_X]
  27.         fistp dword[ebx+offs_vert_zp] ;v.zp.x = st0, st0 = st1
  28.  
  29.         fld dword[ebx+offs_vert_pc+offs_Y] ;st0 = v.pc.Y
  30.         fmul st0,st1
  31.         fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_Y]
  32.         fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_Y]
  33.         fistp dword[ebx+offs_vert_zp+offs_zbup_y] ;v.zp.y = st0, st0 = st1
  34.  
  35.         fld dword[ebx+offs_vert_pc+offs_Z] ;st0 = v.pc.Z
  36.         fmulp
  37.         fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_Z]
  38.         fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_Z]
  39.         fistp dword[ebx+offs_vert_zp+offs_zbup_z] ;v.zp.z = st0, st0 = st1
  40.  
  41.         ; color
  42.         cmp dword[eax+offs_cont_lighting_enabled],0 ;if (context.lighting_enabled)
  43.         je @f
  44.                 mov ecx,ebx
  45.                 add ecx,offs_vert_zp+offs_zbup_b
  46.                 push ecx
  47.                 add ecx,offs_zbup_g-offs_zbup_b
  48.                 push ecx
  49.                 add ecx,offs_zbup_r-offs_zbup_g
  50.                 push ecx
  51.                 stdcall RGBFtoRGBI, dword[ebx+offs_vert_color],dword[ebx+offs_vert_color+4],dword[ebx+offs_vert_color+8]
  52.                 jmp .end_if
  53. align 4
  54.         @@:
  55.                 ; no need to convert to integer if no lighting : take current color
  56.                 mov ecx,[eax+offs_cont_longcurrent_color]
  57.                 mov dword[ebx+offs_vert_zp+offs_zbup_r],ecx
  58.                 mov ecx,[eax+offs_cont_longcurrent_color+4]
  59.                 mov dword[ebx+offs_vert_zp+offs_zbup_g],ecx
  60.                 mov ecx,[eax+offs_cont_longcurrent_color+8]
  61.                 mov dword[ebx+offs_vert_zp+offs_zbup_b],ecx
  62.         .end_if:
  63.  
  64.         ; texture
  65.         cmp dword[eax+offs_cont_texture_2d_enabled],0
  66.         je @f
  67.                 mov dword[point],dword(ZB_POINT_S_MAX - ZB_POINT_S_MIN)
  68.                 fild dword[point]
  69.                 fmul dword[ebx+offs_vert_tex_coord] ;st0 *= v.tex_coord.X
  70.                 fistp dword[ebx+offs_vert_zp+offs_zbup_s]
  71.                 add dword[ebx+offs_vert_zp+offs_zbup_s],ZB_POINT_S_MIN
  72.  
  73.                 mov dword[point],dword(ZB_POINT_T_MAX - ZB_POINT_T_MIN)
  74.                 fild dword[point]
  75.                 fmul dword[ebx+offs_vert_tex_coord+offs_Y] ;st0 *= v.tex_coord.Y
  76.                 fistp dword[ebx+offs_vert_zp+offs_zbup_t]
  77.                 add dword[ebx+offs_vert_zp+offs_zbup_t],ZB_POINT_T_MIN
  78.         @@:
  79.         ret
  80. endp
  81.  
  82. align 16
  83. proc gl_add_select1 uses eax ebx ecx, context:dword, z1:dword,z2:dword,z3:dword
  84.         mov eax,[z1]
  85.         mov ebx,eax
  86.         cmp [z2],eax
  87.         jge @f
  88.                 mov eax,[z2]
  89.         @@:
  90.         cmp [z3],eax
  91.         jge @f
  92.                 mov eax,[z3]
  93.         @@:
  94.         cmp [z2],ebx
  95.         jle @f
  96.                 mov ebx,[z2]
  97.         @@:
  98.         cmp [z3],ebx
  99.         jle @f
  100.                 mov ebx,[z3]
  101.         @@:
  102.         mov ecx,0xffffffff
  103.         sub ecx,ebx
  104.         push ecx
  105.         mov ecx,0xffffffff
  106.         sub ecx,eax
  107.         push ecx
  108.         stdcall gl_add_select, [context] ;,0xffffffff-eax,0xffffffff-ebx
  109.         ret
  110. endp
  111.  
  112. ; point
  113.  
  114. align 16
  115. proc gl_draw_point uses eax ebx, context:dword, p0:dword
  116.         mov ebx,[p0]
  117.         cmp dword[ebx+offs_vert_clip_code],0 ;if (p0.clip_code == 0)
  118.         jne @f
  119.         mov eax,[context]
  120.         cmp dword[eax+offs_cont_render_mode],GL_SELECT
  121.         jne .els
  122.                 stdcall gl_add_select, eax,dword[ebx+offs_vert_zp+offs_zbup_z],dword[ebx+offs_vert_zp+offs_zbup_z] ;p0.zp.z,p0.zp.z
  123.                 jmp @f
  124. align 4
  125.         .els:
  126.                 add ebx,offs_vert_zp
  127.                 stdcall ZB_plot, dword[eax+offs_cont_zb],ebx
  128.         @@:
  129.         ret
  130. endp
  131.  
  132. ; line
  133.  
  134. align 16
  135. proc interpolate uses eax ebx ecx, q:dword,p0:dword,p1:dword,t:dword
  136.         mov eax,[q]
  137.         mov ebx,[p0]
  138.         mov ecx,[p1]
  139.         fld dword[t]
  140.  
  141.         ; интерполяция по координатам
  142.         fld dword[ecx+offs_vert_pc]
  143.         fsub dword[ebx+offs_vert_pc]
  144.         fmul st0,st1
  145.         fadd dword[ebx+offs_vert_pc]
  146.         fstp dword[eax+offs_vert_pc] ;q.pc.X = p0.pc.X + (p1.pc.X - p0.pc.X) * t
  147.  
  148.         fld dword[ecx+offs_vert_pc+offs_Y]
  149.         fsub dword[ebx+offs_vert_pc+offs_Y]
  150.         fmul st0,st1
  151.         fadd dword[ebx+offs_vert_pc+offs_Y]
  152.         fstp dword[eax+offs_vert_pc+offs_Y]
  153.  
  154.         fld dword[ecx+offs_vert_pc+offs_Z]
  155.         fsub dword[ebx+offs_vert_pc+offs_Z]
  156.         fmul st0,st1
  157.         fadd dword[ebx+offs_vert_pc+offs_Z]
  158.         fstp dword[eax+offs_vert_pc+offs_Z]
  159.  
  160.         fld dword[ecx+offs_vert_pc+offs_W]
  161.         fsub dword[ebx+offs_vert_pc+offs_W]
  162.         fmul st0,st1
  163.         fadd dword[ebx+offs_vert_pc+offs_W]
  164.         fstp dword[eax+offs_vert_pc+offs_W]
  165.  
  166.         ; интерполяция по цвету
  167.         fld dword[ecx+offs_vert_color]
  168.         fsub dword[ebx+offs_vert_color]
  169.         fmul st0,st1
  170.         fadd dword[ebx+offs_vert_color]
  171.         fstp dword[eax+offs_vert_color]
  172.  
  173.         fld dword[ecx+offs_vert_color+4]
  174.         fsub dword[ebx+offs_vert_color+4]
  175.         fmul st0,st1
  176.         fadd dword[ebx+offs_vert_color+4]
  177.         fstp dword[eax+offs_vert_color+4]
  178.  
  179.         fld dword[ecx+offs_vert_color+8]
  180.         fsub dword[ebx+offs_vert_color+8]
  181.         fmulp
  182.         fadd dword[ebx+offs_vert_color+8]
  183.         fstp dword[eax+offs_vert_color+8]
  184.         ret
  185. endp
  186.  
  187. ;
  188. ; Line Clipping
  189. ;
  190.  
  191. ; Line Clipping algorithm from 'Computer Graphics', Principles and
  192. ; Practice
  193. ; tmin,tmax -> &float
  194. align 16
  195. proc ClipLine1 uses ebx, denom:dword,num:dword,tmin:dword,tmax:dword
  196.         fld dword[denom]
  197.         ftst
  198.         fstsw ax
  199.         sahf
  200.         jbe .els_0 ;if (denom>0)
  201.                 fld dword[num]
  202.                 fxch st1
  203.                 fdivp ;t=num/denom
  204.                 mov ebx,[tmax]
  205.                 fcom dword[ebx]
  206.                 fstsw ax
  207.                 sahf
  208.                 ja .r0_f1 ;if (t>*tmax) return 0
  209.                 mov ebx,[tmin]
  210.                 fcom dword[ebx]
  211.                 fstsw ax
  212.                 sahf
  213.                 jbe .r1_f1 ;if (t>*tmin) *tmin=t
  214.                         fstp dword[ebx]
  215.                 jmp .r1
  216. align 4
  217.         .els_0: ;else if (denom<0)
  218.                 jae .els_1
  219.                 fld dword[num]
  220.                 fxch st1
  221.                 fdivp ;t=num/denom
  222.                 mov ebx,[tmin]
  223.                 fcom dword[ebx]
  224.                 fstsw ax
  225.                 sahf
  226.                 jb .r0_f1 ;if (t<*tmin) return 0
  227.                 mov ebx,[tmax]
  228.                 fcom dword[ebx]
  229.                 fstsw ax
  230.                 sahf
  231.                 jae .r1_f1
  232.                         fstp dword[ebx] ;if (t<*tmin) *tmax=t
  233.                 jmp .r1
  234. align 4
  235.         .els_1: ;else if (num>0)
  236.                 ffree st0 ;denom
  237.                 fincstp
  238.                 fld dword[num]
  239.                 ftst
  240.                 fstsw ax
  241.                 sahf
  242.                 ja .r0_f1 ;if (num>0) return 0
  243.                 jmp .r1_f1
  244. align 4
  245.         .r0_f1: ;return 0 & free st0
  246.                 ffree st0
  247.                 fincstp
  248.         .r0: ;return 0
  249.                 xor eax,eax
  250.                 jmp .end_f
  251. align 4
  252.         .r1_f1: ;return 1 & free st0
  253.                 ffree st0
  254.                 fincstp
  255.         .r1: ;return 1
  256.                 xor eax,eax
  257.                 inc eax
  258.         .end_f:
  259.         ret
  260. endp
  261.  
  262. align 16
  263. proc gl_draw_line, context:dword, p1:dword, p2:dword
  264. locals
  265.         d_x dd ?
  266.         d_y dd ?
  267.         d_z dd ?
  268.         d_w dd ?
  269.         x1 dd ?
  270.         y1 dd ?
  271.         z1 dd ?
  272.         w1 dd ?
  273.         q1 GLVertex ?
  274.         q2 GLVertex ?
  275.         tmin dd ? ;ebp-8
  276.         tmax dd ? ;ebp-4
  277. endl
  278. pushad
  279.         mov edx,[context]
  280.         mov edi,[p1]
  281.         mov esi,[p2]
  282.  
  283.         cmp dword[edi+offs_vert_clip_code],0
  284.         jne .els_i
  285.         cmp dword[esi+offs_vert_clip_code],0
  286.         jne .els_i
  287.                 ;if ( (p1.clip_code | p2.clip_code) == 0)
  288.                 cmp dword[edx+offs_cont_render_mode],GL_SELECT ;if (context.render_mode == GL_SELECT)
  289.                 jne .els_1
  290.                         stdcall gl_add_select1, edx,dword[edi+offs_vert_zp+offs_zbup_z],\
  291.                                 dword[esi+offs_vert_zp+offs_zbup_z],dword[esi+offs_vert_zp+offs_zbup_z]
  292.                         jmp .end_f
  293. align 4
  294.                 .els_1:
  295.                         add edi,offs_vert_zp
  296.                         add esi,offs_vert_zp
  297.                         push esi
  298.                         push edi
  299.                         push dword[edx+offs_cont_zb]
  300.                         cmp dword[edx+offs_cont_depth_test],0
  301.                         je .els_2
  302.                                 ;if (context.depth_test)
  303.                                 call ZB_line_z ;, dword[edx+offs_cont_zb],edi,esi
  304.                                 jmp .end_f
  305. align 4
  306.                         .els_2:
  307.                                 call ZB_line ;, dword[edx+offs_cont_zb],edi,esi
  308.                                 jmp .end_f
  309. align 4
  310.         .els_i:
  311.                 ;else if ( (p1.clip_code & p2.clip_code) != 0 )
  312.                 mov eax,[edi+offs_vert_clip_code]
  313.                 and eax,[esi+offs_vert_clip_code]
  314.                 or eax,eax
  315.                 jnz .end_f
  316.         .els_0:
  317.  
  318.         fld dword[esi+offs_vert_pc+offs_X]
  319.         fsub dword[edi+offs_vert_pc+offs_X]
  320.         fstp dword[d_x] ;d_x = p2.pc.X - p1.pc.X
  321.         fld dword[esi+offs_vert_pc+offs_Y]
  322.         fsub dword[edi+offs_vert_pc+offs_Y]
  323.         fstp dword[d_y] ;d_y = p2.pc.Y - p1.pc.Y
  324.         fld dword[esi+offs_vert_pc+offs_Z]
  325.         fsub dword[edi+offs_vert_pc+offs_Z]
  326.         fstp dword[d_z] ;d_z = p2.pc.Z - p1.pc.Z
  327.         fld dword[esi+offs_vert_pc+offs_W]
  328.         fsub dword[edi+offs_vert_pc+offs_W]
  329.         fstp dword[d_w] ;d_w = p2.pc.W - p1.pc.W
  330.  
  331.         mov eax,[edi+offs_vert_pc+offs_X]
  332.         mov [x1],eax ;x1 = p1.pc.X
  333.         mov eax,[edi+offs_vert_pc+offs_Y]
  334.         mov [y1],eax ;y1 = p1.pc.Y
  335.         mov eax,[edi+offs_vert_pc+offs_Z]
  336.         mov [z1],eax ;z1 = p1.pc.Z
  337.         mov eax,[edi+offs_vert_pc+offs_W]
  338.         mov [w1],eax ;w1 = p1.pc.W
  339.  
  340.         mov dword[tmin],0.0
  341.         mov dword[tmax],1.0
  342.  
  343.         mov eax,ebp
  344.         sub eax,4
  345.         push eax ;толкаем в стек адрес &tmax
  346.         sub eax,4
  347.         push eax ;толкаем в стек адрес &tmin
  348.         fld dword[x1]
  349.         fadd dword[w1]
  350.         fchs
  351.         fstp dword[esp-4]
  352.         fld dword[d_x]
  353.         fadd dword[d_w]
  354.         fstp dword[esp-8]
  355.         sub esp,8
  356.         call ClipLine1 ;d_x+d_w,-x1-w1,&tmin,&tmax
  357.         bt eax,0
  358.         jnc .end_f
  359.  
  360.         sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
  361.         fld dword[x1]
  362.         fsub dword[w1]
  363.         fstp dword[esp-4]
  364.         fld dword[d_w]
  365.         fsub dword[d_x]
  366.         fstp dword[esp-8]
  367.         sub esp,8
  368.         call ClipLine1 ;-d_x+d_w,x1-w1,&tmin,&tmax
  369.         bt eax,0
  370.         jnc .end_f
  371.  
  372.         sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
  373.         fld dword[y1]
  374.         fadd dword[w1]
  375.         fchs
  376.         fstp dword[esp-4]
  377.         fld dword[d_y]
  378.         fadd dword[d_w]
  379.         fstp dword[esp-8]
  380.         sub esp,8
  381.         call ClipLine1 ;d_y+d_w,-y1-w1,&tmin,&tmax
  382.         bt eax,0
  383.         jnc .end_f
  384.  
  385.         sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
  386.         fld dword[y1]
  387.         fsub dword[w1]
  388.         fstp dword[esp-4]
  389.         fld dword[d_w]
  390.         fsub dword[d_y]
  391.         fstp dword[esp-8]
  392.         sub esp,8
  393.         call ClipLine1 ;-d_y+d_w,y1-w1,&tmin,&tmax
  394.         bt eax,0
  395.         jnc .end_f
  396.  
  397.         sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
  398.         fld dword[z1]
  399.         fadd dword[w1]
  400.         fchs
  401.         fstp dword[esp-4]
  402.         fld dword[d_z]
  403.         fadd dword[d_w]
  404.         fstp dword[esp-8]
  405.         sub esp,8
  406.         call ClipLine1 ;d_z+d_w,-z1-w1,&tmin,&tmax
  407.         bt eax,0
  408.         jnc .end_f
  409.  
  410.         sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
  411.         fld dword[z1]
  412.         fsub dword[w1]
  413.         fstp dword[esp-4]
  414.         fld dword[d_w]
  415.         fsub dword[d_z]
  416.         fstp dword[esp-8]
  417.         sub esp,8
  418.         call ClipLine1 ;-d_z+d_w,z1-w1,&tmin,&tmax
  419.         bt eax,0
  420.         jnc .end_f
  421.  
  422.         mov eax,ebp
  423.         sub eax,8+2*sizeof.GLVertex ;eax = &q1
  424.         stdcall interpolate, eax,edi,esi,[tmin]
  425.         stdcall gl_transform_to_viewport, edx,eax
  426.         add eax,sizeof.GLVertex ;eax = &q2
  427.         stdcall interpolate, eax,edi,esi,[tmax]
  428.         stdcall gl_transform_to_viewport, edx,eax
  429.  
  430.         sub eax,sizeof.GLVertex ;eax = &q1
  431.         mov ebx,eax
  432.         add ebx,offs_vert_zp+offs_zbup_b
  433.         push ebx
  434.         add ebx,offs_zbup_g-offs_zbup_b
  435.         push ebx
  436.         add ebx,offs_zbup_r-offs_zbup_g
  437.         push ebx
  438.         stdcall RGBFtoRGBI, dword[eax+offs_vert_color],dword[eax+offs_vert_color+4],dword[eax+offs_vert_color+8]
  439.  
  440.         add eax,sizeof.GLVertex ;eax = &q2
  441.         mov ebx,eax
  442.         add ebx,offs_vert_zp+offs_zbup_b
  443.         push ebx
  444.         add ebx,offs_zbup_g-offs_zbup_b
  445.         push ebx
  446.         add ebx,offs_zbup_r-offs_zbup_g
  447.         push ebx
  448.         stdcall RGBFtoRGBI, dword[eax+offs_vert_color],dword[eax+offs_vert_color+4],dword[eax+offs_vert_color+8]
  449.  
  450.         add eax,offs_vert_zp ;eax = &q2.zp
  451.         push eax
  452.         sub eax,sizeof.GLVertex ;eax = &q1.zp
  453.         push eax
  454.         push dword[edx+offs_cont_zb]
  455.         cmp dword[edx+offs_cont_depth_test],0
  456.         je .els_3
  457.                 call ZB_line_z ;(context.zb,&q1.zp,&q2.zp)
  458.                 jmp .end_f
  459. align 4
  460.         .els_3:
  461.                 call ZB_line ;(context.zb,&q1.zp,&q2.zp)
  462.         .end_f:
  463. popad
  464.         ret
  465. endp
  466.  
  467. ; triangle
  468.  
  469. ;
  470. ; Clipping
  471. ;
  472.  
  473. ; We clip the segment [a,b] against the 6 planes of the normal volume.
  474. ; We compute the point 'c' of intersection and the value of the parameter 't'
  475. ; of the intersection if x=a+t(b-a).
  476. ;
  477. ; sign: 0 -> '-', 1 -> '+'
  478. macro clip_func sign,dir,dir1,dir2
  479. {
  480. locals
  481.         t dd ?
  482.         d_X dd ?
  483.         d_Y dd ?
  484.         d_Z dd ?
  485.         d_W dd ?
  486. endl
  487.         mov edx,[a]
  488.         mov ebx,[b]
  489.         mov ecx,[c]
  490.         fld dword[ebx+offs_X]
  491.         fsub dword[edx+offs_X]
  492.         fstp dword[d_X] ;d_X = (b.X - a.X)
  493.         fld dword[ebx+offs_Y]
  494.         fsub dword[edx+offs_Y]
  495.         fstp dword[d_Y] ;d_Y = (b.Y - a.Y)
  496.         fld dword[ebx+offs_Z]
  497.         fsub dword[edx+offs_Z]
  498.         fstp dword[d_Z] ;d_Z = (b.Z - a.Z)
  499.         fld dword[ebx+offs_W]
  500.         fsub dword[edx+offs_W]
  501.         fst dword[d_W] ;d_W = (b.W - a.W)
  502. if sign eq 0
  503.         fadd dword[d#dir]
  504. else
  505.         fsub dword[d#dir]
  506. end if
  507.  
  508.         ftst
  509.         fstsw ax
  510.         sahf
  511.         jne @f
  512.                 fldz
  513.                 fst dword[t] ;t=0
  514.                 jmp .e_zero
  515. align 4
  516.         @@: ;else
  517.                 fld dword[edx+offs#dir]
  518. if sign eq 0           
  519.                 fchs
  520. end if
  521.                 fsub dword[edx+offs_W]
  522.                 fdiv st0,st1
  523.                 fst dword[t] ;t = ( sign a.dir - a.W) / den
  524.         .e_zero:
  525.  
  526.         fmul dword[d#dir1] ;st0 = t * d.dir1
  527.         fadd dword[edx+offs#dir1]
  528.         fstp dword[ecx+offs#dir1] ;c.dir1 = a.dir1 + t * d.dir1
  529.  
  530.         ffree st0
  531.         fincstp
  532.  
  533.         fld dword[t]
  534.         fmul dword[d#dir2] ;st0 = t * d.dir2
  535.         fadd dword[edx+offs#dir2]
  536.         fstp dword[ecx+offs#dir2] ;c.dir2 = a.dir2 + t * d.dir2
  537.  
  538.         fld dword[t]
  539.         fmul dword[d_W]
  540.         fadd dword[edx+offs_W]
  541.         fst dword[ecx+offs_W] ;c.W = a.W + t * d_W
  542.  
  543. if sign eq 0           
  544.                 fchs
  545. end if
  546.         fstp dword[ecx+offs#dir] ;c.dir = sign c.W
  547.         mov eax,[t]
  548. }
  549.  
  550. align 16
  551. proc clip_xmin uses ebx ecx edx, c:dword, a:dword, b:dword
  552.         clip_func 0,_X,_Y,_Z
  553.         ret
  554. endp
  555.  
  556. align 16
  557. proc clip_xmax uses ebx ecx edx, c:dword, a:dword, b:dword
  558.         clip_func 1,_X,_Y,_Z
  559.         ret
  560. endp
  561.  
  562. align 16
  563. proc clip_ymin uses ebx ecx edx, c:dword, a:dword, b:dword
  564.         clip_func 0,_Y,_X,_Z
  565.         ret
  566. endp
  567.  
  568. align 16
  569. proc clip_ymax uses ebx ecx edx, c:dword, a:dword, b:dword
  570.         clip_func 1,_Y,_X,_Z
  571.         ret
  572. endp
  573.  
  574. align 16
  575. proc clip_zmin uses ebx ecx edx, c:dword, a:dword, b:dword
  576.         clip_func 0,_Z,_X,_Y
  577.         ret
  578. endp
  579.  
  580. align 16
  581. proc clip_zmax uses ebx ecx edx, c:dword, a:dword, b:dword
  582.         clip_func 1,_Z,_X,_Y
  583.         ret
  584. endp
  585.  
  586. align 4
  587. clip_proc dd clip_xmin,clip_xmax, clip_ymin,clip_ymax, clip_zmin,clip_zmax
  588.  
  589. align 16
  590. proc updateTmp uses eax ebx ecx edx, context:dword, q:dword, p0:dword, p1:dword, t:dword
  591.         mov ebx,[q]
  592.         mov edx,[context]
  593.         mov eax,[p0]
  594.         cmp dword[edx+offs_cont_current_shade_model],GL_SMOOTH ;if (context.current_shade_model == GL_SMOOTH)
  595.         jne .els_0
  596.                 mov ecx,[p1]
  597.                 fld dword[ecx+offs_vert_color]
  598.                 fsub dword[eax+offs_vert_color]
  599.                 fmul dword[t]
  600.                 fadd dword[eax+offs_vert_color]
  601.                 fstp dword[ebx+offs_vert_color] ;q.color.v[0]=p0.color.v[0] + (p1.color.v[0]-p0.color.v[0])*t
  602.                 fld dword[ecx+offs_vert_color+4]
  603.                 fsub dword[eax+offs_vert_color+4]
  604.                 fmul dword[t]
  605.                 fadd dword[eax+offs_vert_color+4]
  606.                 fstp dword[ebx+offs_vert_color+4] ;q.color.v[1]=p0.color.v[1] + (p1.color.v[1]-p0.color.v[1])*t
  607.                 fld dword[ecx+offs_vert_color+8]
  608.                 fsub dword[eax+offs_vert_color+8]
  609.                 fmul dword[t]
  610.                 fadd dword[eax+offs_vert_color+8]
  611.                 fstp dword[ebx+offs_vert_color+8] ;q.color.v[2]=p0.color.v[2] + (p1.color.v[2]-p0.color.v[2])*t
  612.                 jmp @f
  613. align 4
  614.         .els_0:
  615.                 mov ecx,[eax+offs_vert_color]
  616.                 mov [ebx+offs_vert_color],ecx ;q.color.v[0]=p0.color.v[0]
  617.                 mov ecx,[eax+offs_vert_color+4]
  618.                 mov [ebx+offs_vert_color+4],ecx ;q.color.v[1]=p0.color.v[1]
  619.                 mov ecx,[eax+offs_vert_color+8]
  620.                 mov [ebx+offs_vert_color+8],ecx ;q.color.v[2]=p0.color.v[2]
  621.         @@:
  622.  
  623.         cmp dword[edx+offs_cont_texture_2d_enabled],0 ;if (context.texture_2d_enabled)
  624.         je @f
  625.                 mov ecx,[p1]
  626.                 fld dword[ecx+offs_vert_tex_coord+offs_X]
  627.                 fsub dword[eax+offs_vert_tex_coord+offs_X]
  628.                 fmul dword[t]
  629.                 fadd dword[eax+offs_vert_tex_coord+offs_X]
  630.                 fstp dword[ebx+offs_vert_tex_coord+offs_X] ;q.tex_coord.X=p0.tex_coord.X + (p1.tex_coord.X-p0.tex_coord.X)*t
  631.                 fld dword[ecx+offs_vert_tex_coord+offs_Y]
  632.                 fsub dword[eax+offs_vert_tex_coord+offs_Y]
  633.                 fmul dword[t]
  634.                 fadd dword[eax+offs_vert_tex_coord+offs_Y]
  635.                 fstp dword[ebx+offs_vert_tex_coord+offs_Y] ;q.tex_coord.Y=p0.tex_coord.Y + (p1.tex_coord.Y-p0.tex_coord.Y)*t
  636.         @@:
  637.  
  638.         stdcall gl_clipcode, [ebx+offs_vert_pc+offs_X],[ebx+offs_vert_pc+offs_Y],\
  639.                 [ebx+offs_vert_pc+offs_Z],[ebx+offs_vert_pc+offs_W]
  640.         mov dword[ebx+offs_vert_clip_code],eax
  641.         or eax,eax ;if (q.clip_code==0)
  642.         jnz @f
  643.                 stdcall gl_transform_to_viewport,[context],ebx
  644.                 mov eax,ebx
  645.                 add eax,offs_vert_zp+offs_zbup_b
  646.                 push eax
  647.                 add eax,offs_zbup_g-offs_zbup_b
  648.                 push eax
  649.                 add eax,offs_zbup_r-offs_zbup_g
  650.                 push eax
  651.                 stdcall RGBFtoRGBI, dword[ebx+offs_vert_color],dword[ebx+offs_vert_color+4],dword[ebx+offs_vert_color+8]
  652.         @@:
  653.         ret
  654. endp
  655.  
  656. align 16
  657. proc gl_draw_triangle, context:dword, p0:dword, p1:dword, p2:dword
  658. locals
  659.         cc rd 3
  660.         front dd ?
  661.         norm dd ? ;float
  662. endl
  663. pushad
  664.         mov ebx,[p0]
  665.         mov ecx,[p1]
  666.         mov edx,[p2]
  667.         mov edi,[ebx+offs_vert_clip_code]
  668.         mov dword[cc],edi
  669.         mov eax,[ecx+offs_vert_clip_code]
  670.         mov dword[cc+4],eax
  671.         or edi,eax
  672.         mov eax,[edx+offs_vert_clip_code]
  673.         mov dword[cc+8],eax
  674.         or edi,eax ;co = cc[0] | cc[1] | cc[2]
  675.  
  676.         ; we handle the non clipped case here to go faster
  677.         ;or edi,___ - было выше
  678.         jnz .els_0
  679.                 ;if (co==0)
  680.                 mov edi,dword[edx+offs_vert_zp+offs_zbup_x]
  681.                 sub edi,dword[ebx+offs_vert_zp+offs_zbup_x]
  682.                 mov dword[norm],edi ;p2.x-p0.x
  683.                 fild dword[norm]
  684.                 mov edi,dword[ecx+offs_vert_zp+offs_zbup_y]
  685.                 sub edi,dword[ebx+offs_vert_zp+offs_zbup_y]
  686.                 mov dword[norm],edi ;p1.y-p0.y
  687.                 fimul dword[norm]
  688.                 fchs
  689.                 mov edi,dword[ecx+offs_vert_zp+offs_zbup_x]
  690.                 sub edi,dword[ebx+offs_vert_zp+offs_zbup_x]
  691.                 mov dword[norm],edi ;p1.x-p0.x
  692.                 fild dword[norm]
  693.                 mov edi,dword[edx+offs_vert_zp+offs_zbup_y]
  694.                 sub edi,dword[ebx+offs_vert_zp+offs_zbup_y]
  695.                 mov dword[norm],edi ;p2.y-p0.y
  696.                 fimul dword[norm]
  697.                 faddp
  698.                 ;st0 = (p1.zp.x-p0.zp.x)*(p2.zp.y-p0.zp.y) - (p2.zp.x-p0.zp.x)*(p1.zp.y-p0.zp.y)
  699.  
  700.                 mov dword[front],0
  701.                 ftst
  702.                 fstsw ax
  703.                 ffree st0
  704.                 fincstp
  705.                 sahf
  706.                 je .end_f
  707.                 jae @f
  708.                         inc dword[front] ;front = norm < 0.0
  709.                 @@:
  710.                 mov edi,[context]
  711.                 mov eax,dword[edi+offs_cont_current_front_face]
  712.                 xor dword[front],eax ;front ^= context.current_front_face
  713.  
  714.                 ; back face culling
  715.                 cmp dword[edi+offs_cont_cull_face_enabled],0
  716.                 je .els_1
  717.                         ; most used case first
  718.                         cmp dword[edi+offs_cont_current_cull_face],GL_BACK
  719.                         jne @f
  720.                                 cmp dword[front],0
  721.                                 je .end_f
  722.                                         stdcall dword[edi+offs_cont_draw_triangle_front], edi,ebx,ecx,edx
  723.                                 jmp .end_f
  724. align 4
  725.                         @@:
  726.                         cmp dword[edi+offs_cont_current_cull_face],GL_FRONT
  727.                         jne .end_f
  728.                                 cmp dword[front],0
  729.                                 jne .end_f
  730.                                         stdcall dword[edi+offs_cont_draw_triangle_back], edi,ebx,ecx,edx
  731.                         jmp .end_f
  732. align 4
  733.                 .els_1:
  734.                         ; no culling
  735.                         cmp dword[front],0
  736.                         je @f
  737.                                 stdcall dword[edi+offs_cont_draw_triangle_front], edi,ebx,ecx,edx
  738.                                 jmp .end_f
  739. align 4
  740.                         @@:
  741.                                 stdcall dword[edi+offs_cont_draw_triangle_back], edi,ebx,ecx,edx
  742.                 jmp .end_f
  743. align 4
  744.         .els_0:
  745.                 ;eax = cc[2]
  746.                 and eax,[cc]
  747.                 and eax,[cc+4] ;eax = c_and = cc[0] & cc[1] & cc[2]
  748.                 or eax,eax ;if (c_and==0)
  749.                 jnz .end_f
  750.                         stdcall gl_draw_triangle_clip, [context],ebx,ecx,edx,0
  751.         .end_f:
  752. popad
  753.         ret
  754. endp
  755.  
  756. align 16
  757. proc gl_draw_triangle_clip, context:dword, p0:dword, p1:dword, p2:dword, clip_bit:dword
  758. locals
  759.         co dd ?
  760.         cc rd 3
  761.         edge_flag_tmp dd ?
  762.         clip_mask dd ?
  763.         q rd 3 ;GLVertex*
  764.         tmp1 GLVertex ?
  765.         tmp2 GLVertex ?
  766. endl
  767. pushad
  768.         mov ebx,[p0]
  769.         mov ecx,[p1]
  770.         mov edx,[p2]
  771.  
  772.         mov edi,[ebx+offs_vert_clip_code]
  773.         mov [cc],edi
  774.         mov eax,[ecx+offs_vert_clip_code]
  775.         mov [cc+4],eax
  776.         or edi,eax
  777.         mov eax,[edx+offs_vert_clip_code]
  778.         mov [cc+8],eax
  779.         or edi,eax
  780.         mov [co],edi ;co = cc[0] | cc[1] | cc[2]
  781.  
  782.         or edi,edi ;if (co == 0)
  783.         jnz .els_0
  784.                 stdcall gl_draw_triangle, [context],ebx,ecx,edx
  785.                 jmp .end_f
  786. align 4
  787.         .els_0:
  788.                 ;eax = cc[2]
  789.                 and eax,[cc]
  790.                 and eax,[cc+4] ;c_and = cc[0] & cc[1] & cc[2]
  791.  
  792.                 ; the triangle is completely outside
  793.                 or eax,eax ;if (c_and!=0) return
  794.                 jnz .end_f
  795.  
  796.                 ; find the next direction to clip
  797.                 .cycle_0: ;while (clip_bit < 6 && (co & (1 << clip_bit)) == 0)
  798.                 cmp dword[clip_bit],6
  799.                 jge .cycle_0_end
  800.                 xor eax,eax
  801.                 inc eax
  802.                 mov ecx,[clip_bit]
  803.                 shl eax,cl
  804.                 and eax,[co]
  805.                 or eax,eax
  806.                 jnz .cycle_0_end
  807.                         inc dword[clip_bit]
  808.                         jmp .cycle_0
  809. align 4
  810.                 .cycle_0_end:
  811.  
  812.         ; this test can be true only in case of rounding errors
  813.         cmp dword[clip_bit],6
  814. if 0
  815.         jne @f
  816. ;      printf("Error:\n");
  817. ;      printf("%f %f %f %f\n",p0->pc.X,p0->pc.Y,p0->pc.Z,p0->pc.W);
  818. ;      printf("%f %f %f %f\n",p1->pc.X,p1->pc.Y,p1->pc.Z,p1->pc.W);
  819. ;      printf("%f %f %f %f\n",p2->pc.X,p2->pc.Y,p2->pc.Z,p2->pc.W);
  820.                 jmp .end_f
  821.         @@:
  822. end if
  823. if 1
  824.         je .end_f
  825. end if
  826.  
  827.         xor eax,eax
  828.         inc eax
  829.         mov ecx,[clip_bit]
  830.         shl eax,cl
  831.         mov [clip_mask],eax ;1 << clip_bit
  832.         mov edi,[cc]
  833.         xor edi,[cc+4]
  834.         xor edi,[cc+8]
  835.         and eax,edi ;eax = co1 = (cc[0] ^ cc[1] ^ cc[2]) & clip_mask
  836.  
  837.         mov ecx,[p1] ;востанавливаем после shl ___,cl
  838.  
  839.         or eax,eax ;if (co1)
  840.         jz .els_1
  841.                 ; one point outside
  842.                 mov eax,[cc]
  843.                 and eax,[clip_mask]
  844.                 or eax,eax ;if (cc[0] & clip_mask)
  845.                 jz .els_2
  846.                         ;q[0]=p0 q[1]=p1 q[2]=p2
  847.                         mov [q],ebx
  848.                         mov [q+4],ecx
  849.                         mov [q+8],edx
  850.                         jmp .els_2_end
  851. align 4
  852.                 .els_2:
  853.                 mov eax,[cc+4]
  854.                 and eax,[clip_mask]
  855.                 or eax,eax ;else if (cc[1] & clip_mask)
  856.                 jz .els_3
  857.                         ;q[0]=p1 q[1]=p2 q[2]=p0
  858.                         mov [q],ecx
  859.                         mov [q+4],edx
  860.                         mov [q+8],ebx
  861.                         jmp .els_2_end
  862. align 4
  863.                 .els_3:
  864.                         ;q[0]=p2 q[1]=p0 q[2]=p1
  865.                         mov [q],edx
  866.                         mov [q+4],ebx
  867.                         mov [q+8],ecx
  868.                 .els_2_end:
  869.  
  870.                 mov ebx,[q]
  871.                 add ebx,offs_vert_pc
  872.                 mov ecx,[q+4]
  873.                 add ecx,offs_vert_pc
  874.                 mov edx,[q+8]
  875.                 add edx,offs_vert_pc
  876.  
  877.                 lea eax,[clip_proc]
  878.                 mov edi,[clip_bit]
  879.                 shl edi,2
  880.                 add eax,edi
  881.                 mov edi,ebp
  882.                 sub edi,(2*sizeof.GLVertex)-offs_vert_pc
  883.                 stdcall dword[eax],edi,ebx,ecx ;clip_proc[clip_bit](&tmp1.pc,&q[0].pc,&q[1].pc)
  884.                 sub edi,offs_vert_pc
  885.  
  886.                 sub ebx,offs_vert_pc
  887.                 sub ecx,offs_vert_pc
  888.                 stdcall updateTmp,[context],edi,ebx,ecx,eax ;updateTmp(c,&tmp1,q[0],q[1],tt)
  889.                 add ebx,offs_vert_pc
  890.  
  891.                 lea eax,[clip_proc]
  892.                 mov edi,[clip_bit]
  893.                 shl edi,2
  894.                 add eax,edi
  895.                 mov edi,ebp
  896.                 sub edi,sizeof.GLVertex-offs_vert_pc
  897.                 stdcall dword[eax],edi,ebx,edx ;clip_proc[clip_bit](&tmp2.pc,&q[0].pc,&q[2].pc)
  898.                 sub edi,offs_vert_pc
  899.                 sub ebx,offs_vert_pc
  900.                 sub edx,offs_vert_pc
  901.                 stdcall updateTmp,[context],edi,ebx,edx,eax ;updateTmp(c,&tmp2,q[0],q[2],tt)
  902.  
  903.                 mov eax,[ebx+offs_vert_edge_flag]
  904.                 mov [tmp1.edge_flag],eax ;q[0].edge_flag
  905.                 mov eax,[edx+offs_vert_edge_flag]
  906.                 mov [edge_flag_tmp],eax ;q[2].edge_flag
  907.                 mov dword[edx+offs_vert_edge_flag],0 ;q[2].edge_flag=0
  908.                 mov eax,[clip_bit]
  909.                 inc eax
  910.                 push eax ;для вызова нижней функции
  911.                 mov edi,ebp
  912.                 sub edi,2*sizeof.GLVertex
  913.                 stdcall gl_draw_triangle_clip,[context],edi,ecx,edx,eax ;gl_draw_triangle_clip(c,&tmp1,q[1],q[2],clip_bit+1)
  914.  
  915.                 mov dword[tmp2.edge_flag],0
  916.                 mov dword[tmp1.edge_flag],0
  917.                 mov eax,[edge_flag_tmp]
  918.                 mov [edx+offs_vert_edge_flag],eax ;q[2].edge_flag=edge_flag_tmp
  919.                 push edx
  920.                 push edi
  921.                 add edi,sizeof.GLVertex ;edi = &tmp2
  922.                 stdcall gl_draw_triangle_clip,[context],edi ;gl_draw_triangle_clip(c,&tmp2,&tmp1,q[2],clip_bit+1)
  923.                 jmp .end_f
  924. align 4
  925.         .els_1:
  926.                 ; two points outside
  927.                 mov eax,[cc]
  928.                 and eax,[clip_mask]
  929.                 cmp eax,0 ;if (cc[0] & clip_mask)==0
  930.                 jne .els_4
  931.                         ;q[0]=p0 q[1]=p1 q[2]=p2
  932.                         mov [q],ebx
  933.                         mov [q+4],ecx
  934.                         mov [q+8],edx
  935.                         jmp .els_4_end
  936. align 4
  937.                 .els_4:
  938.                 mov eax,[cc+4]
  939.                 and eax,[clip_mask]
  940.                 cmp eax,0 ;else if (cc[1] & clip_mask)==0
  941.                 jne .els_5
  942.                         ;q[0]=p1 q[1]=p2 q[2]=p0
  943.                         mov [q],ecx
  944.                         mov [q+4],edx
  945.                         mov [q+8],ebx
  946.                         jmp .els_4_end
  947. align 4
  948.                 .els_5:
  949.                         ;q[0]=p2 q[1]=p0 q[2]=p1
  950.                         mov [q],edx
  951.                         mov [q+4],ebx
  952.                         mov [q+8],ecx
  953.                 .els_4_end:
  954.  
  955.                 mov ebx,[q]
  956.                 add ebx,offs_vert_pc
  957.                 mov ecx,[q+4]
  958.                 add ecx,offs_vert_pc
  959.                 mov edx,[q+8]
  960.                 add edx,offs_vert_pc
  961.  
  962.                 lea eax,[clip_proc]
  963.                 mov edi,[clip_bit]
  964.                 shl edi,2
  965.                 add eax,edi
  966.                 mov edi,ebp
  967.                 sub edi,(2*sizeof.GLVertex)-offs_vert_pc
  968.                 stdcall dword[eax],edi,ebx,ecx ;clip_proc[clip_bit](&tmp1.pc,&q[0].pc,&q[1].pc)
  969.                 sub edi,offs_vert_pc
  970.                 stdcall updateTmp,[context],edi,[q],[q+4],eax
  971.  
  972.                 lea eax,[clip_proc]
  973.                 mov edi,[clip_bit]
  974.                 shl edi,2
  975.                 add eax,edi
  976.                 mov edi,ebp
  977.                 sub edi,sizeof.GLVertex-offs_vert_pc
  978.                 stdcall dword[eax],edi,ebx,edx ;clip_proc[clip_bit](&tmp2.pc,&q[0].pc,&q[2].pc)
  979.                 sub edi,offs_vert_pc
  980.                 stdcall updateTmp,[context],edi,[q],[q+8],eax
  981.  
  982.                 mov dword[tmp1.edge_flag],1
  983.                 mov eax,[edx+offs_vert_edge_flag-offs_vert_pc]
  984.                 mov dword[tmp2.edge_flag],eax ;tmp2.edge_flag = q[2].edge_flag
  985.                 mov eax,[clip_bit]
  986.                 inc eax
  987.                 push eax
  988.                 push edi
  989.                 sub edi,sizeof.GLVertex
  990.                 stdcall gl_draw_triangle_clip,[context],[q],edi ;gl_draw_triangle_clip(c,q[0],&tmp1,&tmp2,clip_bit+1)
  991.         .end_f:
  992. popad
  993.         ret
  994. endp
  995.  
  996. align 16
  997. proc gl_draw_triangle_select uses eax, context:dword, p0:dword,p1:dword,p2:dword
  998.         mov eax,[p2]
  999.         push dword[eax+offs_vert_zp+offs_Z]
  1000.         mov eax,[p1]
  1001.         push dword[eax+offs_vert_zp+offs_Z]
  1002.         mov eax,[p0]
  1003.         push dword[eax+offs_vert_zp+offs_Z]
  1004.         stdcall gl_add_select1, [context] ;,p0.zp.z, p1.zp.z, p2.zp.z
  1005.         ret
  1006. endp
  1007.  
  1008. if PROFILE eq 1
  1009.         count_triangles dd ?
  1010.         count_triangles_textured dd ?
  1011.         count_pixels dd ?
  1012. end if
  1013.  
  1014. align 16
  1015. proc gl_draw_triangle_fill, context:dword, p0:dword,p1:dword,p2:dword
  1016. pushad
  1017. if PROFILE eq 1
  1018. ;    int norm;
  1019. ;    assert(p0->zp.x >= 0 && p0->zp.x < c->zb->xsize);
  1020. ;    assert(p0->zp.y >= 0 && p0->zp.y < c->zb->ysize);
  1021. ;    assert(p1->zp.x >= 0 && p1->zp.x < c->zb->xsize);
  1022. ;    assert(p1->zp.y >= 0 && p1->zp.y < c->zb->ysize);
  1023. ;    assert(p2->zp.x >= 0 && p2->zp.x < c->zb->xsize);
  1024. ;    assert(p2->zp.y >= 0 && p2->zp.y < c->zb->ysize);
  1025.    
  1026. ;    norm=(p1->zp.x-p0->zp.x)*(p2->zp.y-p0->zp.y)-
  1027. ;      (p2->zp.x-p0->zp.x)*(p1->zp.y-p0->zp.y);
  1028. ;    count_pixels+=abs(norm)/2;
  1029.         inc dword[count_triangles]
  1030. end if
  1031.  
  1032.         mov ebx,[p1]
  1033.         add ebx,offs_vert_zp
  1034.         mov ecx,[p2]
  1035.         add ecx,offs_vert_zp
  1036.         mov edx,[context]
  1037.         cmp dword[edx+offs_cont_texture_2d_enabled],0
  1038.         je .els_i
  1039.                 ;if (context.texture_2d_enabled)
  1040. if PROFILE eq 1
  1041.         inc dword[count_triangles_textured]
  1042. end if
  1043.                 mov eax,dword[edx+offs_cont_current_texture]
  1044.                 mov eax,[eax] ;переход по указателю
  1045.                 ;так как offs_text_images+offs_imag_pixmap = 0 то context.current_texture.images[0].pixmap = [eax]
  1046.                 stdcall ZB_setTexture, dword[edx+offs_cont_zb],dword[eax]
  1047.                 mov eax,[p0]
  1048.                 add eax,offs_vert_zp
  1049.                 push ecx
  1050.                 push ebx
  1051.                 push eax
  1052.                 push dword[edx+offs_cont_zb]
  1053.                 cmp dword[edx+offs_cont_matrix_model_projection_no_w_transform],0
  1054.                 je @f
  1055.                         call ZB_fillTriangleMappingPerspective
  1056.                         jmp .end_f
  1057. align 4
  1058.                 @@:
  1059.                         call ZB_fillTriangleMapping
  1060.                 jmp .end_f
  1061. align 4
  1062.         .els_i:
  1063.                 mov eax,[p0]
  1064.                 add eax,offs_vert_zp
  1065.                 cmp dword[edx+offs_cont_current_shade_model],GL_SMOOTH
  1066.                 jne .els
  1067.                         ;else if (context.current_shade_model == GL_SMOOTH)
  1068.                         stdcall ZB_fillTriangleSmooth, dword[edx+offs_cont_zb],eax,ebx,ecx
  1069.                         jmp .end_f
  1070. align 4
  1071.                 .els:
  1072.                         stdcall ZB_fillTriangleFlat, dword[edx+offs_cont_zb],eax,ebx,ecx
  1073.         .end_f:
  1074. popad
  1075.         ret
  1076. endp
  1077.  
  1078. ; Render a clipped triangle in line mode
  1079.  
  1080. align 16
  1081. proc gl_draw_triangle_line uses eax ebx ecx edx, context:dword, p0:dword,p1:dword,p2:dword
  1082.         mov edx,[context]
  1083.         cmp dword[edx+offs_cont_depth_test],0
  1084.         je .els
  1085.                 lea ecx,[ZB_line_z]
  1086.                 jmp @f
  1087. align 4
  1088.         .els:
  1089.                 lea ecx,[ZB_line]
  1090.         @@:
  1091.  
  1092.         ;if (p0.edge_flag) ZB_line_z(context.zb,&p0.zp,&p1.zp)
  1093.         mov eax,[p0]
  1094.         cmp dword[eax+offs_vert_edge_flag],0
  1095.         je @f
  1096.                 mov ebx,eax
  1097.                 add ebx,offs_vert_zp
  1098.                 mov eax,[p1]
  1099.                 add eax,offs_vert_zp
  1100.                 stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
  1101.         @@:
  1102.         ;if (p1.edge_flag) ZB_line_z(context.zb,&p1.zp,&p2.zp)
  1103.         mov eax,[p1]
  1104.         cmp dword[eax+offs_vert_edge_flag],0
  1105.         je @f
  1106.                 mov ebx,eax
  1107.                 add ebx,offs_vert_zp
  1108.                 mov eax,[p2]
  1109.                 add eax,offs_vert_zp
  1110.                 stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
  1111.         @@:
  1112.         ;if (p2.edge_flag) ZB_line_z(context.zb,&p2.zp,&p0.zp);
  1113.         mov eax,[p2]
  1114.         cmp dword[eax+offs_vert_edge_flag],0
  1115.         je @f
  1116.                 mov ebx,eax
  1117.                 add ebx,offs_vert_zp
  1118.                 mov eax,[p0]
  1119.                 add eax,offs_vert_zp
  1120.                 stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
  1121.         @@:
  1122.  
  1123.         ret
  1124. endp
  1125.  
  1126. ; Render a clipped triangle in point mode
  1127. align 16
  1128. proc gl_draw_triangle_point uses eax ebx edx, context:dword, p0:dword,p1:dword,p2:dword
  1129.         mov edx,[context]
  1130.         mov eax,[p0]
  1131.         cmp dword[eax+offs_vert_edge_flag],0
  1132.         je @f
  1133.                 mov ebx,eax
  1134.                 add ebx,offs_vert_zp
  1135.                 stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
  1136.         @@:
  1137.         mov eax,[p1]
  1138.         cmp dword[eax+offs_vert_edge_flag],0
  1139.         je @f
  1140.                 mov ebx,eax
  1141.                 add ebx,offs_vert_zp
  1142.                 stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
  1143.         @@:
  1144.         mov eax,[p2]
  1145.         cmp dword[eax+offs_vert_edge_flag],0
  1146.         je @f
  1147.                 mov ebx,eax
  1148.                 add ebx,offs_vert_zp
  1149.                 stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
  1150.         @@:
  1151.         ret
  1152. endp
  1153.  
  1154.  
  1155.  
  1156.  
  1157.