Subversion Repositories Kolibri OS

Rev

Rev 2881 | Blame | Last modification | View Log | Download | RSS feed

  1. ;-procedure draws smooth shaded lines (I mean interpolation 24 bit--
  2. ;-color), with z coord interpolation--------------------------------
  3. ;-author: Maciej Guba (www.macgub.hekko.pl)-------------------------
  4. ;-in : -------------------------------------------------------------
  5. ;----- edi - pointer to screen buffer ------------------------------
  6. ;----- esi - pointer to Z buffer -----------------------------------
  7. ;------ constans : SIZE_X, SIZE_Y - screen width and height---------
  8. ;----------------- ROUND - fixed point shift------------------------
  9. ;------ other parameters via stack----------------------------------
  10. smooth_line:
  11. .x1  equ  ebp+4
  12. .y1  equ  ebp+6
  13. .z1  equ  ebp+8
  14. .r1  equ  ebp+10
  15. .g1  equ  ebp+12
  16. .b1  equ  ebp+14
  17. .x2  equ  ebp+16
  18. .y2  equ  ebp+18
  19. .z2  equ  ebp+20
  20. .r2  equ  ebp+22
  21. .g2  equ  ebp+24
  22. .b2  equ  ebp+26
  23.  
  24.  
  25. .line_lenght    equ ebp-2
  26. .delta          equ ebp-6
  27. .delta_x        equ ebp-10
  28. .delta_y        equ ebp-14
  29. .dr             equ ebp-18
  30. .dg             equ ebp-22
  31. .db             equ ebp-26
  32. .dz             equ ebp-30
  33. .cr             equ ebp-34
  34. .cg             equ ebp-38
  35. .cb             equ ebp-42
  36. .cz             equ ebp-46
  37.  
  38. ;.line_lenght    equ ebp-48
  39. .screen         equ ebp-52
  40. .zbuffer        equ ebp-56
  41. .ccoord         equ ebp-60  ;current coordinate
  42. .czbuf          equ ebp-64
  43. .cscr           equ ebp-68
  44. ;.lasty          equ ebp-72
  45. macro .update_cur_var
  46. {
  47. if Ext=NON
  48.      mov         ebx,[.dz]
  49.      add         [.cz],ebx
  50.      mov         ebx,[.dr]
  51.      add         [.cr],ebx
  52.      mov         ebx,[.dg]
  53.      add         [.cg],ebx
  54.      mov         ebx,[.db]
  55.      add         [.cb],ebx
  56. elseif Ext=MMX
  57.      movq        mm0,[.cz]
  58.      movq        mm1,[.cg]
  59.      paddd       mm0,mm2 ;[.dz]
  60.      paddd       mm1,mm3 ;[.dg]
  61.      movq        [.cz],mm0
  62.      movq        [.cg],mm1
  63. elseif Ext >= SSE2
  64. ;     movups      xmm1,[.cz]
  65.      paddd       xmm1,xmm0
  66. ;     movups      [.cz],xmm1
  67. end if
  68. }
  69. macro .draw_pixel
  70. {
  71.     mov         [esi],ebx              ; actualize Z buffer
  72. if Ext=SSE2
  73.     movaps      xmm7,xmm1 ;[.cb] ;;xmm1
  74.     shufps      xmm7,xmm7,00111001b
  75.     psrld       xmm7,ROUND
  76.     packssdw    xmm7,xmm7
  77.     packuswb    xmm7,xmm7
  78.     pand        xmm7,xmm6 ;[.mask]
  79.     movd        [edi],xmm7
  80. else
  81.  
  82.     mov         eax,[.cb]
  83.     sar         eax,ROUND
  84.     mov         [edi],al
  85. ;    and         eax,0x000000ff         ; clean unused bits
  86.     mov         ebx,[.cg]
  87.     sar         ebx,ROUND
  88.     mov         [edi+1],bl
  89. ;    mov         ah,bl
  90.     mov         edx,[.cr]
  91.     sar         edx,ROUND
  92.     mov         [edi+2],dl
  93. end if
  94. ;    shl         ebx,16
  95. ;    or          eax,ebx
  96. ;    mov         [edi],eax
  97. }
  98. macro .sort
  99. {
  100.  
  101. if Ext >= MMX
  102.     movq        mm0,[.x1]
  103.     movq        mm1,[.x2]
  104.     movq        [.x1],mm1
  105.     movq        [.x2],mm0
  106. else
  107.     mov         edx,[.x1]
  108.     xchg        edx,[.x2]
  109.     mov         [.x1],edx
  110.     mov         edx,[.z1]
  111.     xchg        edx,[.z2]
  112.     mov         [.z1],edx
  113. end if
  114.     mov         edx,[.g1]
  115.     xchg        edx,[.g2]
  116.     mov         [.g1],edx
  117. }
  118.  
  119.  
  120.  
  121.     emms
  122.     mov         ebp,esp
  123.     sub         esp,128
  124.     mov         eax,[.x1]      ; check if parameters exceedes screen area
  125.     mov         ebx,[.x2]
  126.     or          eax,ebx
  127.     test        eax,80008000h
  128.     jne         .end_line
  129.     cmp         word[.x1],SIZE_X
  130.     jg          .end_line
  131.     cmp         word[.x2],SIZE_X
  132.     jg          .end_line
  133.     cmp         word[.y1],SIZE_Y
  134.     jg          .end_line
  135.     cmp         word[.y2],SIZE_Y
  136.     jg          .end_line
  137.  
  138.  
  139.     mov         [.screen],edi
  140.     mov         cx,[.x1]
  141.     cmp         cx,[.x2]
  142.     je          .vertical_l
  143.     mov         cx,[.y1]
  144.     cmp         cx,[.y2]
  145.     je          .horizontal_l
  146.     mov         ax,[.x1]
  147.     sub         ax,[.x2]
  148.     cmp         ax,0
  149.     jg          @f
  150.     neg         ax    ; calc absolute value
  151.  @@:
  152.     mov         [.delta_x],ax
  153.     mov         bx,[.y1]
  154.     sub         bx,[.y2]
  155.     cmp         bx,0
  156.     jg          @f
  157.     neg         bx
  158.  @@:
  159.     mov         [.delta_y],bx
  160.     cmp         ax,bx
  161.     je          .deg45_l
  162.     jl          .more_vertical_l
  163.     jg          .more_horizon_l
  164.     jmp         .end_line
  165.                                                                   ;
  166. .horizontal_l:
  167.     mov         ax,[.x1]
  168.     mov         bx,[.x2]
  169.     cmp         bx,ax
  170.     jge         @f
  171.  
  172.     .sort
  173. @@:
  174.  
  175.     mov         bx,[.x2]
  176.     sub         bx,[.x1]
  177.     movsx       ebx,bx
  178.     cmp         ebx,0    ;line lenght equql 0
  179.     je          .end_line
  180.     mov         [.delta_x],ebx
  181.  
  182.     call        .calc_delta
  183.  
  184.     mov         eax,SIZE_X
  185.     movsx       ebx,word[.y1]
  186.     mul         ebx
  187.     add         esi,eax
  188.     lea         eax,[eax*3]
  189.     add         esi,eax
  190.     add         edi,eax
  191.     movsx       eax,word[.x1]
  192.     add         esi,eax
  193.     lea         eax,[eax*3]
  194.     add         edi,eax
  195.     add         esi,eax
  196.  
  197.     mov         ecx,[.delta_x]
  198.  
  199.     movsx       ebx,word[.r1]
  200.     shl         ebx,ROUND
  201.     mov         [.cr],ebx
  202.     movsx       ebx,word[.g1]
  203.     shl         ebx,ROUND
  204.     mov         [.cg],ebx
  205.     movsx       ebx,word[.b1]
  206.     shl         ebx,ROUND
  207.     mov         [.cb],ebx
  208.     movsx       ebx,word[.z1]
  209.     shl         ebx,ROUND
  210.     mov         [.cz],ebx
  211. if Ext = SSE2
  212.     movups      xmm1,[.cz]
  213. end if
  214. .hdraw:
  215. if Ext = SSE2
  216.     movd        ebx,xmm1
  217. else
  218.     mov         ebx,[.cz]
  219. end if
  220.     cmp         [esi],ebx
  221.     jle         .skip
  222.  
  223.     .draw_pixel
  224.  
  225. .skip:
  226.     add         edi,3
  227.     add         esi,4
  228.  
  229.     .update_cur_var
  230.  
  231.     loop        .hdraw
  232.     jmp         .end_line
  233.  
  234. .vertical_l:
  235.     mov         ax,[.y1]
  236.     cmp         [.y2],ax
  237.     jge         @f
  238.  
  239.     .sort
  240. @@:
  241.     mov         bx,[.y2]
  242.     sub         bx,[.y1]
  243.     movsx       ebx,bx
  244.     cmp         ebx,0
  245.     je          .end_line
  246.     mov         [.delta_y],ebx
  247.  
  248.     call        .calc_delta
  249.  
  250.     mov         eax,SIZE_X
  251.     movsx       ebx,word[.y1]
  252.     mul         ebx
  253.     add         esi,eax
  254.     lea         eax,[eax*3]
  255.     add         edi,eax
  256.     add         esi,eax
  257.     movsx       eax,word[.x1]
  258.     add         esi,eax
  259.     lea         eax,[eax*3]
  260.     add         esi,eax
  261.     add         edi,eax
  262.  
  263.     mov         ecx,[.delta_y]
  264.  
  265.     movsx       ebx,word[.r1]
  266.     shl         ebx,ROUND
  267.     mov         [.cr],ebx
  268.     movsx       ebx,word[.g1]
  269.     shl         ebx,ROUND
  270.     mov         [.cg],ebx
  271.     movsx       ebx,word[.b1]
  272.     shl         ebx,ROUND
  273.     mov         [.cb],ebx
  274.     movsx       ebx,word[.z1]
  275.     shl         ebx,ROUND
  276.     mov         [.cz],ebx
  277. if Ext = SSE2
  278.     movups      xmm1,[.cz]
  279. end if
  280.  
  281. .v_draw:
  282. if Ext = SSE2
  283.     movd        ebx,xmm1
  284. else
  285.     mov         ebx,[.cz]
  286. end if
  287.     cmp         [esi],ebx
  288.     jle         @f
  289.  
  290.     .draw_pixel
  291.  
  292. @@:
  293.     add         edi,SIZE_X*3
  294.     add         esi,SIZE_X*4
  295.  
  296.     .update_cur_var
  297.  
  298.     loop        .v_draw
  299.     jmp         .end_line
  300. .deg45_l:
  301.     mov         word[.line_lenght],ax
  302.     mov         ax,[.x1]
  303.     cmp         [.x2],ax
  304.     jge         @f
  305.  
  306.     .sort
  307. @@:
  308.     mov         bx,[.y2]
  309.     sub         bx,[.y1]
  310.     movsx       ebx,bx
  311.     cmp         ebx,0
  312.     je          .end_line
  313.     mov         [.delta_y],ebx
  314.     mov         bx,[.x2]
  315.     sub         bx,[.x1]
  316.     movsx       ebx,bx
  317.     mov         [.delta_x],ebx
  318.  
  319.     call        .calc_delta
  320.  
  321.     mov         eax,SIZE_X
  322.     movsx       ebx,word[.y1] ;calc begin values in screen and Z buffers
  323.     mul         ebx
  324.     lea         ebx,[3*eax]
  325.     add         edi,ebx
  326.     shl         eax,2
  327.     add         esi,eax
  328.     movsx       eax,word[.x1]
  329.     lea         ebx,[eax*3]
  330.     add         edi,ebx
  331.     shl         eax,2
  332.     add         esi,eax
  333.  
  334.     movzx       ecx,word[.line_lenght]
  335.  
  336.     movsx       ebx,word[.r1]
  337.     shl         ebx,ROUND
  338.     mov         [.cr],ebx
  339.     movsx       ebx,word[.g1]
  340.     shl         ebx,ROUND
  341.     mov         [.cg],ebx
  342.     movsx       ebx,word[.b1]
  343.     shl         ebx,ROUND
  344.     mov         [.cb],ebx
  345.     movsx       ebx,word[.z1]
  346.     shl         ebx,ROUND
  347.     mov         [.cz],ebx
  348. .d45_draw:
  349. if Ext = SSE2
  350.     movd        ebx,xmm1
  351. else
  352.     mov         ebx,[.cz]
  353. end if
  354.     cmp         [esi],ebx
  355.     jle         @f
  356.  
  357.     .draw_pixel
  358.  
  359. @@:
  360.     cmp         dword[.delta_y],0
  361.     jl          @f
  362.     add         edi,SIZE_X*3+3
  363.     add         esi,SIZE_X*4+4
  364.     jmp         .d45_1
  365. @@:
  366.     sub         edi,(SIZE_X*3)-3
  367.     sub         esi,(SIZE_X*4)-4
  368. .d45_1:
  369.     .update_cur_var
  370.  
  371.     loop        .d45_draw
  372.     jmp         .end_line
  373.  
  374. .more_vertical_l:
  375.     mov         word[.line_lenght],bx
  376.     mov         ax,[.y1]
  377.     cmp         [.y2],ax
  378.     jge         @f
  379.     .sort
  380. @@:
  381.     mov         bx,[.y2]
  382.     sub         bx,[.y1]
  383.     movsx       ebx,bx
  384.     cmp         ebx,0
  385.     je          .end_line   ;=======================
  386.     mov         [.delta_y],ebx
  387.  
  388.     mov         ax,[.x2]
  389.     sub         ax,[.x1]
  390.     cwde
  391.     shl         eax,ROUND
  392.     cdq
  393.     idiv        ebx
  394.     mov         [.delta],eax
  395.  
  396.     call        .calc_delta
  397.  
  398.     mov         eax,SIZE_X
  399.     movsx       ebx,word[.y1] ;calc begin values in screen and Z buffers
  400.     mul         ebx
  401.     lea         ebx,[3*eax]
  402.     add         esi,ebx
  403.     add         esi,eax
  404.     add         edi,ebx
  405.     mov         [.cscr],edi
  406.     mov         [.czbuf],esi
  407.  
  408.     movzx       ecx,word[.line_lenght]
  409.  
  410.     movsx       ebx,word[.r1]
  411.     shl         ebx,ROUND
  412.     mov         [.cr],ebx
  413.     movsx       ebx,word[.g1]
  414.     shl         ebx,ROUND
  415.     mov         [.cg],ebx
  416.     movsx       ebx,word[.b1]
  417.     shl         ebx,ROUND
  418.     mov         [.cb],ebx
  419.     movsx       ebx,word[.z1]
  420.     shl         ebx,ROUND
  421.     mov         [.cz],ebx
  422. if Ext = SSE2
  423.     movups      xmm1,[.cz]
  424. end if
  425.     movsx       ebx,word[.x1]
  426.     shl         ebx,ROUND
  427.     mov         [.ccoord],ebx    ; .ccoord -> x coordinate
  428. .draw_m_v:
  429.     mov         edi,[.cscr]
  430.     mov         esi,[.czbuf]
  431.     mov         eax,[.ccoord]
  432.     sar         eax,ROUND
  433.     lea         ebx,[eax*3]
  434.     add         edi,ebx
  435.     add         esi,ebx
  436.     add         esi,eax
  437. if Ext = SSE2
  438.     movd        ebx,xmm1
  439. else
  440.     mov         ebx,[.cz]
  441. end if
  442.     cmp         [esi],ebx
  443.     jle         @f
  444.  
  445.     .draw_pixel
  446.  
  447. @@:
  448.     mov         eax,[.delta]
  449.     add         [.ccoord],eax
  450.     add         dword[.cscr],SIZE_X*3  ;
  451.     add         dword[.czbuf],SIZE_X*4
  452. .d_m_v1:
  453.  
  454.     .update_cur_var
  455.  
  456.     dec         ecx
  457.     jnz         .draw_m_v
  458.     jmp         .end_line
  459.  
  460. .more_horizon_l:
  461.     mov         word[.line_lenght],ax
  462.     mov         ax,[.x1]
  463.     cmp         [.x2],ax
  464.     jge         @f
  465.  
  466.     .sort
  467. @@:
  468.     mov         bx,[.x2]
  469.     sub         bx,[.x1]
  470.     movsx       ebx,bx
  471.     cmp         ebx,0;=======================
  472.     je          .end_line
  473.     mov         [.delta_x],ebx
  474.  
  475.     mov         ax,[.y2]
  476.     sub         ax,[.y1]
  477.     cwde
  478.     shl         eax,ROUND
  479.     cdq
  480.     idiv        ebx
  481.     mov         [.delta],eax
  482.  
  483.     call        .calc_delta
  484.  
  485.  ;calc begin values in screen and Z buffers
  486.     movsx       ebx,word[.x1]
  487.     mov         eax,ebx
  488.     add         esi,ebx
  489.     lea         ebx,[3*ebx]
  490.     add         esi,ebx
  491.     add         edi,ebx
  492.     mov         [.cscr],edi
  493.     mov         [.czbuf],esi
  494.  
  495.     movzx       ecx,word[.line_lenght]
  496.  
  497.     movsx       ebx,word[.r1]
  498.     shl         ebx,ROUND
  499.     mov         [.cr],ebx
  500.     movsx       ebx,word[.g1]
  501.     shl         ebx,ROUND
  502.     mov         [.cg],ebx
  503.     movsx       ebx,word[.b1]
  504.     shl         ebx,ROUND
  505.     mov         [.cb],ebx
  506.     movsx       ebx,word[.z1]
  507.     shl         ebx,ROUND
  508.     mov         [.cz],ebx
  509. if Ext = SSE2
  510.     movups      xmm1,[.cz]
  511. end if
  512.     movsx       ebx,word[.y1]
  513.     shl         ebx,ROUND
  514.     mov         [.ccoord],ebx    ; .ccoord -> y coordinate
  515.  
  516. .draw_m_h:
  517.     mov         edi,[.cscr]
  518.     mov         esi,[.czbuf]
  519.     mov         eax,[.ccoord]    ; ccoord - cur y coordinate
  520.     sar         eax,ROUND
  521.     mov         ebx,SIZE_X
  522.     mul         ebx
  523.     add         esi,eax
  524.     lea         eax,[eax*3]
  525.     add         esi,eax
  526.     add         edi,eax
  527. if Ext = SSE2
  528.     movd        ebx,xmm1
  529. else
  530.     mov         ebx,[.cz]
  531. end if
  532.     cmp         [esi],ebx
  533.     jle         @f
  534.  
  535.     .draw_pixel
  536.  
  537. @@:
  538.     mov         eax,[.delta]
  539.     add         [.ccoord],eax
  540.     add         dword[.cscr],3  ;
  541.     add         dword[.czbuf],4
  542.  
  543.     .update_cur_var
  544.  
  545.     dec         ecx
  546.     jnz         .draw_m_h
  547.  
  548. .end_line:
  549.      mov       esp,ebp
  550.      ret       24
  551.  
  552. .calc_delta:
  553.     mov         ax,[.z2]
  554.     sub         ax,[.z1]
  555.     cwde
  556.     shl         eax,ROUND
  557.     cdq
  558.     idiv        ebx
  559.     mov         [.dz],eax
  560.  
  561.     mov         ax,[.r2]
  562.     sub         ax,[.r1]
  563.     cwde
  564.     shl         eax,ROUND
  565.     cdq
  566.     idiv        ebx
  567.     mov         [.dr],eax
  568.  
  569.     mov         ax,[.g2]
  570.     sub         ax,[.g1]
  571.     cwde
  572.     shl         eax,ROUND
  573.     cdq
  574.     idiv        ebx
  575.     mov         [.dg],eax
  576.  
  577.     mov         ax,[.b2]
  578.     sub         ax,[.b1]
  579.     cwde
  580.     shl         eax,ROUND
  581.     cdq
  582.     idiv        ebx
  583.     mov         [.db],eax
  584. if Ext=MMX | Ext = SSE
  585.     movq        mm2,[.dz]
  586.     movq        mm3,[.dg]
  587. else if Ext >= SSE2
  588.     movups      xmm0,[.dz]
  589.     movups      xmm6,[.mask]
  590. end if
  591. ret
  592. .mask:
  593.            dq 0xffffffff00ffffff
  594.            dq 0xffffffffffffffff
  595.  
  596.  
  597.  
  598.  
  599.  
  600.  
  601.  
  602.  
  603.  
  604.  
  605.  
  606.  
  607.  
  608.