home *** CD-ROM | disk | FTP | other *** search
/ Amiga ACS 1998 #6 / amigaacscoverdisc1998-061998.iso / games / descent / source / 3d / rod.asm < prev    next >
Assembly Source File  |  1998-06-08  |  10KB  |  431 lines

  1. ;THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
  2. ;SOFTWARE CORPORATION ("PARALLAX").  PARALLAX, IN DISTRIBUTING THE CODE TO
  3. ;END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
  4. ;ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
  5. ;IN USING, DISPLAYING,  AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
  6. ;SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
  7. ;FREE PURPOSES.  IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
  8. ;CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES.  THE END-USER UNDERSTANDS
  9. ;AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.  
  10. ;COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION.  ALL RIGHTS RESERVED.
  11. ;
  12. ; $Source: f:/miner/source/3d/rcs/rod.asm $
  13. ; $Revision: 1.22 $
  14. ; $Author: matt $
  15. ; $Date: 1995/02/09 22:00:51 $
  16. ; Code to draw rods (facing bitmaps).
  17. ; $Log: rod.asm $
  18. ; Revision 1.22  1995/02/09  22:00:51  matt
  19. ; Removed dependence on divide overflow handler; we now check for overflow
  20. ; before dividing.  This fixed problems on some TI chips.
  21. ; Revision 1.21  1994/11/27  12:55:14  matt
  22. ; Tooks out some unused code
  23. ; Revision 1.20  1994/09/01  15:34:49  matt
  24. ; Fixed stack mess-up when rod projection overflows
  25. ; Revision 1.19  1994/09/01  10:41:46  matt
  26. ; Blob routine, renamed g3_draw_bitmap(), now takes seperate 3d width & height.
  27. ; Revision 1.18  1994/08/01  17:23:27  matt
  28. ; Check for overflow after project in blob code
  29. ; Revision 1.17  1994/07/25  15:47:13  matt
  30. ; Cleaned up code, and made long-broken flat-shaded rods work.
  31. ; Revision 1.16  1994/07/25  00:00:05  matt
  32. ; Made 3d no longer deal with point numbers, but only with pointers.
  33. ; Revision 1.15  1994/07/22  17:58:01  matt
  34. ; Changed the name of the rod functions, and took out some debugging code
  35. ; Revision 1.14  1994/07/21  12:49:41  mike
  36. ; Create _blob_vertices so powerups can be outlined when selected in editor.
  37. ; Revision 1.13  1994/06/16  09:07:29  matt
  38. ; Move in UV values for rods to prevent the texture mapper from reading
  39. ; past the edges of the bitmaps.
  40. ; Revision 1.12  1994/05/31  18:35:29  matt
  41. ; Added light value to g3_draw_facing_bitmap()
  42. ; Revision 1.11  1994/05/19  23:11:54  matt
  43. ; Support new uvl value ranges
  44. ; Revision 1.10  1994/05/13  10:18:07  matt
  45. ; Fixed bug introduced last time
  46. ; Revision 1.9  1994/05/11  10:10:35  matt
  47. ; Changed a little code in attempt to avoid overflows
  48. ; Revision 1.8  1994/05/07  16:43:26  matt
  49. ; Made rods work right, maybe.
  50. ; Revision 1.7  1994/03/23  10:25:04  matt
  51. ; Fixed stack messup with blob overflow, and removed debug_brk
  52. ; Revision 1.6  1994/03/15  21:22:11  matt
  53. ; Put in check for div overflow in blob code
  54. ; Revision 1.5  1994/02/21  11:04:15  matt
  55. ; Added check for zero-length vector
  56. ; Revision 1.4  1994/02/15  17:37:23  matt
  57. ; New function, g3_draw_blob()
  58. ; Revision 1.3  1994/02/11  20:15:04  matt
  59. ; Fixed matrix scale problem, removed unneeded debug_brk
  60. ; Revision 1.2  1994/02/09  11:49:32  matt
  61. ; Added code for texture-mapped and flat-shaded rods
  62. ; Revision 1.1  1994/02/02  11:27:21  matt
  63. ; Initial revision
  64.  
  65. ALWAYS_USE_SCALER = 0    ;if true, use scaler even when banked
  66.  
  67.  
  68. .386
  69.     option    oldstructs
  70.  
  71.     .nolist
  72.     include    types.inc
  73.     include    psmacros.inc
  74.     include    gr.inc
  75.     include    3d.inc
  76.     .list
  77.  
  78.     assume    cs:_TEXT, ds:_DATA
  79.  
  80.     public    _blob_vertices
  81.  
  82. _DATA    segment    dword public USE32 'DATA'
  83.  
  84. rcsid    db    "$Id: rod.asm 1.22 1995/02/09 22:00:51 matt Exp $"
  85.     align    4
  86.  
  87. bot_width    fix    ?
  88. top_width    fix    ?
  89.  
  90. rod_points    db    4*size g3s_point dup (?)
  91.  
  92. delta_x    fix    ?
  93. delta_y    fix    ?
  94.  
  95. edge_vec_x    fix    ?
  96. edge_vec_y    fix    ?
  97.  
  98. vertbuf    fix    4 dup (?,?)
  99. _blob_vertices    fix    4 dup (?,?)
  100.  
  101. bitmap_ptr    dd    ?
  102.  
  103. delta_vec    vms_vector <>
  104. rod_norm    vms_vector <>
  105. temp_vec    vms_vector <>
  106. top_pnt    dd    ?
  107. bot_pnt    dd    ?
  108.  
  109. rod_point_list    dd    rod_points
  110.     dd    rod_points+(size g3s_point)
  111.     dd    rod_points+(size g3s_point)*2
  112.     dd    rod_points+(size g3s_point)*3
  113.  
  114. ;values here are set to be half a pixel in from the edges so the texture
  115. ;mapper doesn't read past the bitmap  
  116. uvl_list    fix    200h,200h,0
  117.     fix    0fe00h,200h,0
  118.     fix    0fe00h,0fe00h,0
  119.     fix    200h,0fe00h,0
  120.  
  121. ;;uvl_list    fix    0,0,0
  122. ;;    fix    10000h,0,0
  123. ;;    fix    10000h,10000h,0
  124. ;;    fix    0,10000h,0
  125.  
  126. _DATA    ends
  127.  
  128.  
  129.  
  130. _TEXT    segment    dword public USE32 'CODE'
  131.  
  132.     extn    scale_bitmap_
  133.  
  134. ;draws a polygon that's always facing the viewer
  135. ;takes esi,edi=bottom & top points (g3s_point *), eax,edx=3d width at bottom,top
  136. g3_draw_rod_flat:    pushm    eax,ebx,ecx,edx,esi,edi
  137.  
  138.     call    calc_rod_corners
  139.     or    cl,cl    ;check codes
  140.     jnz    no_draw
  141.  
  142.     mov    ecx,4    ;4 corners
  143.     lea    esi,rod_point_list
  144.     call    g3_draw_poly
  145.  
  146.     popm    eax,ebx,ecx,edx,esi,edi
  147.     ret
  148.  
  149. ;draws bitmap that's always facing the viewer
  150. ;takes esi,edi=bottom & top points (g3s_point *), eax,edx=3d width at bottom,top
  151. ;ebx = bitmap
  152. ;points must be rotated
  153. g3_draw_rod_tmap:
  154.     pushm    eax,ebx,ecx,edx,esi,edi
  155.  
  156.     mov    bitmap_ptr,ebx
  157.  
  158.     ;save lighting values
  159.     mov    uvl_list+8,ecx
  160.     mov    uvl_list+20,ecx
  161.     mov    uvl_list+32,ecx
  162.     mov    uvl_list+44,ecx
  163.  
  164.     call    calc_rod_corners
  165.     or    cl,cl    ;check codes
  166.     jnz    no_draw
  167.  
  168.     mov    ecx,4
  169.     lea    esi,rod_point_list
  170.     lea    ebx,uvl_list
  171.     mov    edx,bitmap_ptr
  172.     call    g3_draw_tmap
  173.  
  174.     jmp    no_draw
  175.  
  176.  
  177. ;;@@;can use use scaler?
  178. ;;@@if not ALWAYS_USE_SCALER
  179. ;;@@    mov    eax,vertbuf+4    ;point 0 y
  180. ;;@@    cmp    eax,vertbuf+12    ;point 1 y
  181. ;;@@    jne    must_roll
  182. ;;@@;use the scaler!
  183. ;;@@endif
  184. ;;@@    mov    eax,bitmap_ptr
  185. ;;@@    lea    edx,vertbuf
  186. ;;@@    call    scale_bitmap_
  187. ;;@@    jmp    no_draw
  188. ;;@@
  189. ;;@@;can't call the scaler
  190. ;;@@must_roll:    mov    eax,bitmap_ptr
  191. ;;@@    lea    edx,vertbuf
  192. ;;@@    mov    ebx,15        ;light value
  193. ;;@@    call    rotate_bitmap_
  194.  
  195. no_draw:
  196.     popm    eax,ebx,ecx,edx,esi,edi
  197.     ret
  198.  
  199.  
  200.  
  201.  
  202. ;draws a bitmap with the specified 3d width & height 
  203. ;takes esi=position, ebx=width, ecx=height, eax=bitmap
  204. ;modifies eax,esi,ecx
  205. g3_draw_bitmap:    pushm    edx,edi
  206.  
  207.     mov    bitmap_ptr,eax    ;save bitmap
  208.  
  209.     push    ebx    ;save width
  210.     lea    edi,rod_points    ;get dest point
  211.     call    g3_rotate_point
  212.     or    bl,bl    ;off screen?
  213.     pop    ebx    ;restore width
  214.     js    blob_off_screen
  215.  
  216. ;we should check if off screen based on rad
  217.  
  218.     mov    esi,edi
  219.     call    g3_project_point
  220.     test    [esi].p3_flags,PF_OVERFLOW
  221.     jnz    blob_off_screen
  222.  
  223. ;get 2d width & height
  224.  
  225.     mov    eax,ebx    ;get width
  226.     imul    Canv_w2
  227. blob_div0:    divcheck    [esi].z,blob_overflow_handler
  228.     idiv    [esi].z    ;width3d*canv_w/z
  229.     fixmul    Matrix_scale.x    ;*scale
  230.     mov    edi,eax    ;save width
  231.  
  232.     mov    eax,ecx    ;get height
  233.     imul    Canv_h2
  234. blob_div1:    divcheck    [esi].z,blob_overflow_handler
  235.     idiv    [esi].z    ;height3d*canv_h/z
  236.     fixmul    Matrix_scale.y    ;*scale
  237.     mov    ecx,eax    ;save height
  238.  
  239. ;copy 2d points into buffer
  240.  
  241.     lea    edx,_blob_vertices
  242.  
  243.     mov    eax,[esi].p3_sx
  244.     sub    eax,edi    ;- width
  245.     mov    [edx],eax    ;p0.x
  246.     lea    eax,[eax+edi*2]    ;+ 2*width
  247.     mov    8[edx],eax    ;p1.x
  248.     mov    16[edx],eax    ;p2.x
  249.  
  250.     mov    eax,[esi].p3_sy
  251.     sub    eax,ecx    ;- height
  252.     mov    4[edx],eax    ;p0.y
  253.     mov    12[edx],eax    ;p1.y
  254.     lea    eax,[eax+ecx*2]    ;+ 2*height
  255.     mov    20[edx],eax    ;p2.y
  256.  
  257. ;now draw
  258.     mov    eax,bitmap_ptr    ;get bitmap ptr
  259.     call    scale_bitmap_    ;vertbuf in edx
  260.  
  261. blob_off_screen:    popm    edx,edi
  262.     ret
  263.  
  264. blob_overflow_handler:
  265.     ;debug_brk    "blob overflow - get Matt"
  266.     jmp    blob_off_screen
  267.  
  268.  
  269.  
  270.  
  271. ;compute the corners of a rod.  fills in vertbuf. ret codes in al.
  272. ;points in esi,edi, widths in eax,edx  
  273. ;trashes piles of registers
  274. calc_rod_corners:
  275.  
  276.     mov    bot_width,eax
  277.     mov    top_width,edx
  278.  
  279.     mov    bot_pnt,esi
  280.     mov    top_pnt,edi
  281.  
  282. ;compute vector from one point to other, do cross product with vector
  283. ;from eye to get perpendiclar
  284.  
  285.     lea    eax,delta_vec
  286.     call    vm_vec_sub
  287.  
  288. ;unscale for aspect
  289.     mov    eax,delta_vec.x
  290.     fixdiv    matrix_scale.x
  291.     mov    delta_vec.x,eax
  292.     mov    eax,delta_vec.y
  293.     fixdiv    matrix_scale.y
  294.     mov    delta_vec.y,eax
  295.  
  296.  
  297. ;calc perp vector
  298.  
  299. ;do lots of normalizing to prevent overflowing.  When this code works,
  300. ;it should be optimized
  301.  
  302.     lea    esi,delta_vec
  303.     call    vm_vec_normalize
  304.  
  305.     vm_copy    temp_vec,edi
  306.     mov    edi,esi
  307.     lea    esi,temp_vec
  308.     call    vm_vec_normalize
  309.  
  310.     xchg    esi,edi    
  311.     lea    eax,rod_norm
  312.     call    vm_vec_crossprod
  313.  
  314.     mov    esi,eax
  315.     call    vm_vec_normalize
  316.  
  317. ;scale for aspect
  318.  
  319.     mov    eax,rod_norm.x
  320.     fixmul    matrix_scale.x
  321.     mov    rod_norm.x,eax
  322.     mov    eax,rod_norm.y
  323.     fixmul    matrix_scale.y
  324.     mov    rod_norm.y,eax
  325.  
  326.  
  327. ;now we have the usable edge.  generate four points
  328.  
  329.     mov    cl,0ffh    ;codes and
  330.  
  331.     push    ebp
  332.     lea    ebp,rod_points
  333.  
  334. ;top points
  335.     lea    edi,temp_vec
  336.     lea    ebx,rod_norm
  337.     mov    ecx,top_width
  338.     call    vm_vec_copy_scale
  339.  mov temp_vec.z,0
  340.  
  341.     mov    eax,ebp
  342.     mov    esi,top_pnt    ;temp vec in edi
  343.     call    vm_vec_add
  344.  
  345.     add    eax,size g3s_point
  346.     call    vm_vec_sub
  347.  
  348.     lea    ebp,size g3s_point[eax]
  349.  
  350. ;bot points
  351.     lea    edi,temp_vec
  352.     lea    ebx,rod_norm
  353.     mov    ecx,bot_width
  354.     call    vm_vec_copy_scale
  355.  mov temp_vec.z,0
  356.  
  357.     mov    eax,ebp
  358.     mov    esi,bot_pnt    ;temp vec in edi
  359.     call    vm_vec_sub
  360.  
  361.     add    eax,size g3s_point
  362.     call    vm_vec_add
  363.  
  364.     pop    ebp
  365.  
  366. ;now code the four points
  367.  
  368.     mov    cl,0ffh    ;codes and
  369.  
  370.     lea    eax,rod_points
  371.     call    code_point
  372.     and    cl,bl
  373.     add    eax,size g3s_point
  374.     call    code_point
  375.     and    cl,bl
  376.     add    eax,size g3s_point
  377.     call    code_point
  378.     and    cl,bl
  379.     add    eax,size g3s_point
  380.     call    code_point
  381.     and    cl,bl
  382.     jnz    new_new_off_screen
  383.  
  384.     push    ecx    ;save codes
  385.  
  386. ;clear flags for new points (not projected)
  387.  
  388.     lea    esi,rod_points
  389.     mov    [esi].p3_flags,0
  390.     mov    [esi+size g3s_point].p3_flags,0
  391.     mov    [esi+(size g3s_point)*2].p3_flags,0
  392.     mov    [esi+(size g3s_point)*3].p3_flags,0
  393.  
  394.     pop    ecx    ;restore codes
  395.  
  396.     ret
  397.  
  398. new_new_off_screen:
  399.     ret
  400.  
  401.  
  402. _TEXT    ends
  403.  
  404.     end
  405.  
  406.