Author Topic: Re: Spritesheets  (Read 364 times)

0 Members and 1 Guest are viewing this topic.

Offline keybone

  • Forum Regular
  • Posts: 116
  • My name a Nursultan Tulyakbay.
    • View Profile
Re: Spritesheets
« on: April 20, 2020, 10:24:17 pm »
Word...
I am from a Kazakhstan, we follow the hawk.

Offline Unseen Machine

  • Forum Regular
  • Posts: 158
  • Make the game not the engine!
    • View Profile
Re: Spritesheets
« Reply #1 on: April 21, 2020, 03:34:54 am »
Hi [banned user],

Looks good for a first attempt. Have a look at the sprite/animation/vector/game object routines in this (and in terry's sprite library) and happy coding bro.

Unseen

Code: QB64: [Select]
  1. '\\ Unseen Game Deveopment Kit (GDK) - Version 1.8 - DEVELOPMENT VERSION - NOT FINISHED!!!
  2. '// Updated 30/7/2019
  3. '// Created By John Onyon a.k.a Unseen Machine
  4. '// Optimistation by CodeGuy and DarthWho
  5. '// ScanKeys% function by Cypherium
  6. '// Image rotation function by Galleon
  7. '// Rotated Rectangle Collision Detection By Richard Notley
  8.  
  9. '##########################################################################################################################
  10. '// Typdef's
  11. '##########################################################################################################################
  12.  
  13. SUB GDK_Types
  14.  
  15.   TYPE Sprite
  16.     File AS LONG
  17.     Height AS INTEGER
  18.     Alpha AS _UNSIGNED LONG
  19.     IsVisible AS _BYTE
  20.     XFrameCount AS _BYTE
  21.     YFrameCount AS _BYTE
  22.     TotalFrameCount AS INTEGER
  23.     RotationX AS SINGLE
  24.     RotationY AS SINGLE
  25.     Scale AS SINGLE
  26.     BitMask AS _MEM '// For pixel perfect collisions
  27.  
  28.   TYPE Vector
  29.     X AS SINGLE
  30.     Y AS SINGLE
  31.     Speed AS SINGLE
  32.     Rotation AS DOUBLE
  33.     Accel AS SINGLE
  34.     Decel AS SINGLE
  35.  
  36.   TYPE BoundingCircle
  37.     X AS INTEGER
  38.     Y AS INTEGER
  39.     Radius AS INTEGER
  40.  
  41.   TYPE MouseState
  42.     X AS INTEGER
  43.     Y AS INTEGER
  44.     LB AS _BYTE
  45.     RB AS _BYTE
  46.     MB AS _BYTE
  47.     MW AS _BYTE
  48.  
  49.   TYPE KeyBoardState
  50.     Left AS LONG
  51.     Right AS LONG
  52.     Down AS LONG
  53.     Up AS LONG
  54.     CTRL AS LONG
  55.     SHIFT AS LONG
  56.     ALT AS LONG
  57.     SPACE AS LONG
  58.     ENTER AS LONG
  59.     ESC AS LONG
  60.     Num1 AS LONG
  61.     Num2 AS LONG
  62.     Num3 AS LONG
  63.     Num4 AS LONG
  64.     Num5 AS LONG
  65.     Num6 AS LONG
  66.     Num7 AS LONG
  67.     Num8 AS LONG
  68.     Num9 AS LONG
  69.     Num0 AS LONG
  70.     PLUS AS LONG
  71.     MINUS AS LONG
  72.     BACKSPACE AS LONG
  73.     TAB AS LONG
  74.     A AS LONG
  75.     B AS LONG
  76.     C AS LONG
  77.     D AS LONG
  78.     E AS LONG
  79.     F AS LONG
  80.     G AS LONG
  81.     H AS LONG
  82.     I AS LONG
  83.     J AS LONG
  84.     K AS LONG
  85.     L AS LONG
  86.     M AS LONG
  87.     N AS LONG
  88.     O AS LONG
  89.     P AS LONG
  90.     Q AS LONG
  91.     R AS LONG
  92.     S AS LONG
  93.     T AS LONG
  94.     U AS LONG
  95.     V AS LONG
  96.     W AS LONG
  97.     X AS LONG
  98.     Y AS LONG
  99.     Z AS LONG
  100.  
  101.  
  102.   TYPE ANIMATION
  103.     Frame AS INTEGER
  104.     StartFrame AS INTEGER
  105.     ResetFrame AS INTEGER
  106.     Time AS DOUBLE
  107.     Dir AS _BYTE
  108.  
  109.   TYPE Emitter
  110.     X AS INTEGER
  111.     Y AS INTEGER
  112.     SpawnRate AS INTEGER
  113.     SpawnAngleMin AS SINGLE
  114.     SpawnAngleMax AS SINGLE
  115.     SpawnMaxVelocity AS SINGLE
  116.     SpawnMinVelocity AS SINGLE
  117.     MaxLifeTime AS DOUBLE
  118.     MinLifeTime AS DOUBLE
  119.     AccelMax AS SINGLE
  120.     DecelMax AS SINGLE
  121.     AccelMin AS SINGLE
  122.     DecelMIn AS SINGLE
  123.     Gravity AS SINGLE
  124.  
  125.   TYPE Particle
  126.     InitialCLR AS _UNSIGNED LONG
  127.     CurrentCLR AS _UNSIGNED LONG
  128.     ClrChange AS _UNSIGNED LONG
  129.     ClrChangeMode AS INTEGER
  130.     Vector AS Vector
  131.     BirthTime AS DOUBLE
  132.     LifeTime AS DOUBLE
  133.     Exists AS _BYTE
  134.     Accel AS SINGLE
  135.     Decel AS SINGLE
  136.     Gravity AS SINGLE
  137.  
  138.   TYPE Tileset
  139.     Sheet AS Sprite
  140.     THeight AS INTEGER
  141.     TWidth AS INTEGER
  142.  
  143.   TYPE XY
  144.     X AS INTEGER
  145.     Y AS INTEGER
  146.  
  147.   TYPE Rectangle
  148.     XY AS XY
  149.     WH AS XY
  150.     Rotation AS SINGLE
  151.     RotationPoint AS XY
  152.     C1 AS XY
  153.     C2 AS XY
  154.     C3 AS XY
  155.     C4 AS XY
  156.  
  157.   TYPE GameObject
  158.     Sprite AS Sprite
  159.     Vector AS Vector
  160.     Rect AS Rectangle
  161.  
  162.   TYPE Tile
  163.     RECT AS Rectangle
  164.     Tile AS INTEGER
  165.  
  166.   TYPE Path
  167.     Vector AS Vector
  168.     LastVector AS Vector
  169.     TargetVector AS Vector
  170.     NumPoints AS INTEGER
  171.     CurrentPoint AS INTEGER
  172.     HitTargetX AS INTEGER
  173.     HitTargetY AS INTEGER
  174.     Repeat AS INTEGER
  175.     Relative AS INTEGER
  176.     Reverse AS INTEGER
  177.     IsReversing AS INTEGER
  178.  
  179.   TYPE PathPoint
  180.     X AS INTEGER
  181.     Y AS INTEGER
  182.     Speed AS INTEGER
  183.  
  184.  
  185.  
  186. '##########################################################################################################################
  187. '// Collision detection
  188. '##########################################################################################################################
  189.  
  190. SUB GDK_Rectangle_New (RectRef AS Rectangle, x%, y%, Width%, Height%)
  191.   RectRef.XY.X = x%
  192.   RectRef.XY.Y = y%
  193.   RectRef.WH.X = Width%
  194.   RectRef.WH.Y = Height%
  195.  
  196. SUB GDK_Rectangle_Autosize (Sprite AS Sprite, Vector AS Vector, Rect AS Rectangle)
  197.   Rect.XY.X = Vector.X - (Sprite.RotationX * Sprite.Scale)
  198.   Rect.XY.Y = Vector.Y - (Sprite.RotationY * Sprite.Scale)
  199.   Rect.WH.X = (Sprite.Width / Sprite.XFrameCount) * Sprite.Scale
  200.   Rect.WH.Y = (Sprite.Height / Sprite.YFrameCount) * Sprite.Scale
  201.   Rect.Rotation = Vector.Rotation
  202.   Rect.RotationPoint.X = Sprite.RotationX * Sprite.Scale
  203.   Rect.RotationPoint.Y = Sprite.RotationY * Sprite.Scale
  204.   DIM pX(3) AS SINGLE, pY(3) AS SINGLE, W AS LONG, H AS LONG, I AS LONG, X AS LONG, Y AS LONG, X2 AS LONG, Y2 AS LONG, PointX AS LONG, PointY AS LONG
  205.   X = Vector.X
  206.   Y = Vector.Y
  207.   W = (Sprite.Width / Sprite.XFrameCount)
  208.   H = (Sprite.Height / Sprite.YFrameCount)
  209.   PointX = Sprite.RotationX
  210.   PointY = Sprite.RotationY
  211.   pX(0) = -PointX
  212.   pY(0) = -PointY
  213.   pX(1) = -PointX
  214.   pY(1) = -PointY + H - 1
  215.   pX(2) = -PointX + W - 1
  216.   pY(2) = -PointY + H - 1
  217.   pX(3) = -PointX + W - 1
  218.   pY(3) = -PointY 'Set dest screen points
  219.   SINr = SIN(Vector.Rotation)
  220.   COSr = COS(Vector.Rotation) 'Precalculate SIN & COS of angle
  221.   FOR I = 0 TO 3
  222.     pX(I) = pX(I) * Sprite.Scale
  223.     pY(I) = pY(I) * Sprite.Scale 'Scale
  224.     X2 = pX(I) * COSr + SINr * pY(I)
  225.     pY(I) = pY(I) * COSr - pX(I) * SINr
  226.     pX(I) = X2 'Rotate Dest Points
  227.     pX(I) = pX(I) + X
  228.     pY(I) = pY(I) + Y 'Translate Dest Points
  229.     SELECT CASE I
  230.       CASE 0
  231.         Rect.C1.X = pX(I)
  232.         Rect.C1.Y = pY(I)
  233.       CASE 1
  234.         Rect.C2.X = pX(I)
  235.         Rect.C2.Y = pY(I)
  236.       CASE 2
  237.         Rect.C3.X = pX(I)
  238.         Rect.C3.Y = pY(I)
  239.       CASE 3
  240.         Rect.C4.X = pX(I)
  241.         Rect.C4.Y = pY(I)
  242.     END SELECT
  243.   NEXT
  244.  
  245.  
  246. FUNCTION GDK_Rectangle_Intersect (Rect1 AS Rectangle, Rect2 AS Rectangle)
  247.   'IF Rect1.Rotation = 0 AND Rect2.Rotation = 0 THEN '// No rotation do standard collision check'''
  248. '
  249. '    IF Rect1.XY.X <= Rect2.XY.X + Rect2.WH.X THEN
  250. '      IF Rect1.XY.X + Rect1.WH.X >= Rect2.XY.X THEN
  251. '        IF Rect1.XY.Y <= Rect2.XY.Y + Rect2.WH.Y THEN
  252. '          IF Rect1.XY.Y + Rect1.WH.Y >= Rect2.XY.Y THEN
  253. '            GDK_Rectangle_Intersect = -1
  254. '            EXIT FUNCTION
  255. '          END IF
  256. '        END IF
  257. '      END IF
  258. '    END IF'
  259.  
  260. '  ELSE '// Rotated rectangles
  261.  
  262.     '// Adapted from code created by Richard Notley
  263.     '// http://www.[abandoned, outdated and now likely malicious qb64 dot net website - don’t go there]/forum/index.php?topic=12564.0
  264.     REDIM sngCorners1!(3, 1), sngCorners2!(3, 1), sngCorners2A!(3, 1), sngCentre!(1, 1)
  265.  
  266.     '// Put rect data into arrays
  267.     sngCorners1!(0, 0) = Rect1.C1.X
  268.     sngCorners1!(0, 1) = Rect1.C1.Y
  269.     sngCorners1!(1, 0) = Rect1.C2.X
  270.     sngCorners1!(1, 1) = Rect1.C2.Y
  271.     sngCorners1!(2, 0) = Rect1.C3.X
  272.     sngCorners1!(2, 1) = Rect1.C3.Y
  273.     sngCorners1!(3, 0) = Rect1.C4.X
  274.     sngCorners1!(3, 1) = Rect1.C4.Y
  275.  
  276.     sngCorners2!(0, 0) = Rect2.C1.X
  277.     sngCorners2!(0, 1) = Rect2.C1.Y
  278.     sngCorners2!(1, 0) = Rect2.C2.X
  279.     sngCorners2!(1, 1) = Rect2.C2.Y
  280.     sngCorners2!(2, 0) = Rect2.C3.X
  281.     sngCorners2!(2, 1) = Rect2.C3.Y
  282.     sngCorners2!(3, 0) = Rect2.C4.X
  283.     sngCorners2!(3, 1) = Rect2.C4.Y
  284.  
  285.     'Extra copy of sngCorners2! used for second poke-through condition check
  286.     FOR bytN%% = 0 TO 3
  287.       FOR bytM%% = 0 TO 1
  288.         sngCorners2A!(bytN%%, bytM%%) = sngCorners2!(bytN%%, bytM%%)
  289.       NEXT bytM%%
  290.     NEXT bytN%%
  291.  
  292.     'Find Centres of Rectangles
  293.     sngCentre!(0, 0) = (sngCorners1!(0, 0) + sngCorners1!(1, 0) + sngCorners1!(2, 0) + sngCorners1!(3, 0)) / 4
  294.     sngCentre!(0, 1) = (sngCorners1!(0, 1) + sngCorners1!(1, 1) + sngCorners1!(2, 1) + sngCorners1!(3, 1)) / 4
  295.     sngCentre!(1, 0) = (sngCorners2!(0, 0) + sngCorners2!(1, 0) + sngCorners2!(2, 0) + sngCorners2!(3, 0)) / 4
  296.     sngCentre!(1, 1) = (sngCorners2!(0, 1) + sngCorners2!(1, 1) + sngCorners2!(2, 1) + sngCorners2!(3, 1)) / 4
  297.  
  298.     'Find lengths of rectangle diagonals
  299.     sngDiag1! = (SQR((sngCorners1!(2, 0) - sngCorners1!(0, 0)) * (sngCorners1!(2, 0) - sngCorners1!(0, 0)) + (sngCorners1!(2, 1) - sngCorners1!(0, 1)) * (sngCorners1!(2, 1) - sngCorners1!(0, 1)))) / 2
  300.     sngDiag2! = (SQR((sngCorners2!(2, 0) - sngCorners2!(0, 0)) * (sngCorners2!(2, 0) - sngCorners2!(0, 0)) + (sngCorners2!(2, 1) - sngCorners2!(0, 1)) * (sngCorners2!(2, 1) - sngCorners2!(0, 1)))) / 2
  301.     sngSepn! = SQR((sngCentre!(1, 0) - sngCentre!(0, 0)) * (sngCentre!(1, 0) - sngCentre!(0, 0)) + (sngCentre!(1, 1) - sngCentre!(0, 1)) * (sngCentre!(1, 1) - sngCentre!(0, 1)))
  302.  
  303.     IF sngSepn! <= sngDiag1! + sngDiag2! THEN
  304.       'Only need to do collision check if rectangles are closer than sum of half-diagonals
  305.  
  306.       'Check for intersect of diagonals
  307.       IF HF_CrossOver%%(sngCorners1!(0, 1), sngCorners1!(0, 0), sngCorners1!(2, 1), sngCorners1!(2, 0), sngCorners2!(0, 1), sngCorners2!(0, 0), sngCorners2!(2, 1), sngCorners2!(2, 0)) = -1 THEN
  308.         GDK_Rectangle_Intersect = -1
  309.         EXIT FUNCTION
  310.       ELSEIF HF_CrossOver%%(sngCorners1!(0, 1), sngCorners1!(0, 0), sngCorners1!(2, 1), sngCorners1!(2, 0), sngCorners2!(1, 1), sngCorners2!(1, 0), sngCorners2!(3, 1), sngCorners2!(3, 0)) = -1 THEN
  311.         GDK_Rectangle_Intersect = -1
  312.         EXIT FUNCTION
  313.       ELSEIF HF_CrossOver%%(sngCorners1!(1, 1), sngCorners1!(1, 0), sngCorners1!(3, 1), sngCorners1!(3, 0), sngCorners2!(0, 1), sngCorners2!(0, 0), sngCorners2!(2, 1), sngCorners2!(2, 0)) = -1 THEN
  314.         GDK_Rectangle_Intersect = -1
  315.         EXIT FUNCTION
  316.       ELSEIF HF_CrossOver%%(sngCorners1!(1, 1), sngCorners1!(1, 0), sngCorners1!(3, 1), sngCorners1!(3, 0), sngCorners2!(1, 1), sngCorners2!(1, 0), sngCorners2!(3, 1), sngCorners2!(3, 0)) = -1 THEN
  317.         GDK_Rectangle_Intersect = -1
  318.         EXIT FUNCTION
  319.       ELSE
  320.         'Check for poke-throughs
  321.  
  322.         'adjust sngCorners2! relative to sngArr1! centre
  323.  
  324.         FOR bytN%% = 0 TO 3
  325.           FOR bytM%% = 0 TO 1
  326.             sngCorners2!(bytN%%, bytM%%) = sngCorners2!(bytN%%, bytM%%) - sngCentre!(0, bytM%%)
  327.           NEXT bytM%%
  328.         NEXT bytN%%
  329.  
  330.         'rotate to sngArr1!
  331.  
  332.         'find Angle of sngCorners1!
  333.         sngAngRot! = HF_Angle!(sngCorners1!(3, 1) - sngCorners1!(0, 1), sngCorners1!(3, 0) - sngCorners1!(0, 0))
  334.  
  335.         FOR bytN%% = 0 TO 3
  336.           sngR! = SQR(sngCorners2!(bytN%%, 0) * sngCorners2!(bytN%%, 0) + sngCorners2!(bytN%%, 1) * sngCorners2!(bytN%%, 1)): sngPhi! = HF_Angle!(sngCorners2!(bytN%%, 1), sngCorners2!(bytN%%, 0))
  337.           sngCorners2!(bytN%%, 1) = sngR! * COS(sngPhi! - sngAngRot!)
  338.           sngCorners2!(bytN%%, 0) = sngR! * SIN(sngPhi! - sngAngRot!)
  339.         NEXT bytN%%
  340.  
  341.         'Find height and width of sngCorners1!
  342.         sngRWidth! = SQR((sngCorners1!(0, 0) - sngCorners1!(1, 0)) * (sngCorners1!(0, 0) - sngCorners1!(1, 0)) + (sngCorners1!(0, 1) - sngCorners1!(1, 1)) * (sngCorners1!(0, 1) - sngCorners1!(1, 1)))
  343.         sngRHeight! = SQR((sngCorners1!(0, 0) - sngCorners1!(3, 0)) * (sngCorners1!(0, 0) - sngCorners1!(3, 0)) + (sngCorners1!(0, 1) - sngCorners1!(3, 1)) * (sngCorners1!(0, 1) - sngCorners1!(3, 1)))
  344.  
  345.         FOR bytN%% = 0 TO 3
  346.           IF sngCorners2!(bytN%%, 1) <= sngRHeight! / 2 THEN
  347.             IF sngCorners2!(bytN%%, 1) >= -sngRHeight! / 2 THEN
  348.               IF sngCorners2!(bytN%%, 0) <= sngRWidth! / 2 THEN
  349.                 IF sngCorners2!(bytN%%, 0) >= -sngRWidth! / 2 THEN
  350.                   GDK_Rectangle_Intersect = -1
  351.                   EXIT FUNCTION
  352.                 END IF
  353.               END IF
  354.             END IF
  355.           END IF
  356.         NEXT
  357.  
  358.         'adjust sngCorners1! relative to sngArr2! centre
  359.  
  360.         FOR bytN%% = 0 TO 3
  361.           FOR bytM%% = 0 TO 1
  362.             sngCorners1!(bytN%%, bytM%%) = sngCorners1!(bytN%%, bytM%%) - sngCentre!(1, bytM%%)
  363.           NEXT bytM%%
  364.         NEXT bytN%%
  365.  
  366.         'rotate to sngArr2!
  367.  
  368.         'find Angle of sngCorners2A!
  369.         sngAngRot! = HF_Angle!(sngCorners2A!(3, 1) - sngCorners2A!(0, 1), sngCorners2A!(3, 0) - sngCorners2A!(0, 0))
  370.  
  371.         FOR bytN%% = 0 TO 3
  372.           sngR! = SQR(sngCorners1!(bytN%%, 0) * sngCorners1!(bytN%%, 0) + sngCorners1!(bytN%%, 1) * sngCorners1!(bytN%%, 1)): sngPhi! = HF_Angle!(sngCorners1!(bytN%%, 1), sngCorners1!(bytN%%, 0))
  373.           sngCorners1!(bytN%%, 1) = sngR! * COS(sngPhi! - sngAngRot!)
  374.           sngCorners1!(bytN%%, 0) = sngR! * SIN(sngPhi! - sngAngRot!)
  375.         NEXT bytN%%
  376.  
  377.         'Find height and width of sngCorners2!
  378.         sngRWidth! = SQR((sngCorners2A!(0, 0) - sngCorners2A!(1, 0)) * (sngCorners2A!(0, 0) - sngCorners2A!(1, 0)) + (sngCorners2A!(0, 1) - sngCorners2A!(1, 1)) * (sngCorners2A!(0, 1) - sngCorners2A!(1, 1)))
  379.         sngRHeight! = SQR((sngCorners2A!(0, 0) - sngCorners2A!(3, 0)) * (sngCorners2A!(0, 0) - sngCorners2A!(3, 0)) + (sngCorners2A!(0, 1) - sngCorners2A!(3, 1)) * (sngCorners2A!(0, 1) - sngCorners2A!(3, 1)))
  380.  
  381.         FOR bytN%% = 0 TO 3
  382.           IF sngCorners1!(bytN%%, 1) <= sngRHeight! / 2 THEN
  383.             IF sngCorners1!(bytN%%, 1) >= -sngRHeight! / 2 THEN
  384.               IF sngCorners1!(bytN%%, 0) <= sngRWidth! / 2 THEN
  385.                 IF sngCorners1!(bytN%%, 0) >= -sngRWidth! / 2 THEN
  386.                   GDK_Rectangle_Intersect = -1
  387.                   EXIT FUNCTION
  388.                 END IF
  389.               END IF
  390.             END IF
  391.           END IF
  392.         NEXT
  393.  
  394.       END IF
  395.     END IF
  396. '  END IF
  397.  
  398. FUNCTION HF_Angle! (X!, Y!) '// Helper function for collisions
  399.   IF X! = 0 THEN
  400.     IF Y! < 0 THEN
  401.       HF_Angle! = -_PI / 2
  402.     ELSE
  403.       HF_Angle! = _PI / 2
  404.     END IF
  405.   ELSE
  406.     HF_Angle! = ATN(Y! / X!)
  407.   END IF
  408.   IF X! < 0 THEN
  409.     HF_Angle! = HF_Angle! - _PI
  410.     IF HF_Angle! < -_PI THEN HF_Angle! = HF_Angle! + 2 * _PI
  411.   END IF
  412.  
  413. FUNCTION HF_CrossOver%% (sngXT1!, sngYT1!, sngXS1!, sngYS1!, sngXT2!, sngYT2!, sngXS2!, sngYS2!) '// Helper function
  414.   sngM1! = (sngYT1! - sngYS1!) / (sngXT1! - sngXS1!)
  415.   sngC1! = ((sngXT1! * sngYS1!) - (sngXS1! * sngYT1!)) / (sngXT1! - sngXS1!)
  416.   sngM2! = (sngYT2! - sngYS2!) / (sngXT2! - sngXS2!)
  417.   sngC2! = ((sngXT2! * sngYS2!) - (sngXS2! * sngYT2!)) / (sngXT2! - sngXS2!)
  418.   sngXCross! = (sngC1! - sngC2!) / (sngM2! - sngM1!) '!!! <- Possible Divide by zero
  419.   sngYCross! = (sngM1! * sngXCross!) + sngC1!
  420.   sngX1H! = sngXT1!: sngY1H! = sngYT1!
  421.   sngX1L! = sngXS1!: sngY1L! = sngYS1!
  422.   sngX2H! = sngXT2!: sngY2H! = sngYT2!
  423.   sngX2L! = sngXS2!: sngY2L! = sngYS2!
  424.   IF sngX1L! > sngX1H! THEN SWAP sngX1L!, sngX1H!
  425.   IF sngY1L! > sngY1H! THEN SWAP sngY1L!, sngY1H!
  426.   IF sngX2L! > sngX2H! THEN SWAP sngX2L!, sngX2H!
  427.   IF sngY2L! > sngY2H! THEN SWAP sngY2L!, sngY2H!
  428.   IF sngXCross! >= sngX1L! THEN
  429.     IF sngXCross! <= sngX1H! THEN
  430.       IF sngYCross! >= sngY1L! THEN
  431.         IF sngYCross! <= sngY1H! THEN
  432.           IF sngXCross! >= sngX2L! THEN
  433.             IF sngXCross! <= sngX2H! THEN
  434.               IF sngYCross! >= sngY2L! THEN
  435.                 IF sngYCross! <= sngY2H! THEN
  436.                   HF_CrossOver%% = -1
  437.                 END IF
  438.               END IF
  439.             END IF
  440.           END IF
  441.         END IF
  442.       END IF
  443.     END IF
  444.   END IF
  445.  
  446.  
  447.  
  448. FUNCTION GDK_BoundingCircle_Intersect (Circ1 AS BoundingCircle, Circ2 AS BoundingCircle)
  449.   LRAD% = Circ1.Radius + Circ2.Radius
  450.   CDist! = GDK_Distance(Circ1.X, Circ1.Y, Circ2.X, Circ2.Y)
  451.   IF CDist! > LRAD% THEN
  452.     GDK_BoundingCircle_Intersect = 0
  453.   ELSE
  454.     GDK_BoundingCircle_Intersect = -1
  455.   END IF
  456.  
  457. SUB GDK_BoundingCircle_New (Circ1 AS BoundingCircle, X%, Y%, Radius%)
  458.   Circ1.X = X%
  459.   Circ1.Y = Y%
  460.   Circ1.Radius = Radius%
  461.  
  462.  
  463. '##########################################################################################################################
  464. '//Vector stuff
  465. '##########################################################################################################################
  466.  
  467. SUB GDK_Vector_New (Vector AS Vector, X%, Y%, Speed!, Rotation#)
  468.   Vector.X = X%
  469.   Vector.Y = Y%
  470.   Vector.Speed = Speed!
  471.   Vector.Rotation = Rotation#
  472.  
  473. SUB GDK_Vector_SetPosition (Vector AS Vector, X%, Y%)
  474.   Vector.X = X%
  475.   Vector.Y = Y%
  476.  
  477. SUB GDK_Vector_SetRotation (Vector AS Vector, Rotation#)
  478.   Vector.Rotation = Rotation#
  479.  
  480. SUB GDK_Vector_SetSpeed (Vector AS Vector, Speed!)
  481.   Vector.Speed = Speed!
  482.  
  483. SUB GDK_Vector_SetAccelDecel (Vector AS Vector, Accel!, Decel!)
  484.   Vector.Accel = Accel!
  485.   Vector.Decel = Decel!
  486.  
  487. SUB GDK_Vector_Update (Vector AS Vector)
  488.   IF Vector.Decel > 0 THEN
  489.     IF Vector.Accel > 0 THEN
  490.       Vector.Accel = Vector.Accel - Vector.Decel
  491.     ELSE
  492.       IF Vector.Speed > (Vector.Decel) THEN Vector.Speed = Vector.Speed - Vector.Decel ELSE Vector.Speed = 0
  493.     END IF
  494.   END IF
  495.   IF Vector.Accel > 0 THEN Vector.Speed = Vector.Speed + Vector.Accel
  496.   GDK_Vector_Move Vector
  497.  
  498. SUB GDK_Vector_Move (Vector AS Vector)
  499.   Vector.X = Vector.X - SIN(Vector.Rotation) * Vector.Speed
  500.   Vector.Y = Vector.Y - COS(Vector.Rotation) * Vector.Speed
  501.  
  502. '##########################################################################################################################
  503. '// Sprite stuff
  504. '##########################################################################################################################
  505.  
  506. SUB GDK_Sprite_New (Sprite AS Sprite, FileSource$, XFrameCount%, YFrameCount%, TotalFrameCount%, Alpha&)
  507.   Sprite.File = _LOADIMAGE(FileSource$, 32)
  508.   Sprite.Width = _WIDTH(Sprite.File)
  509.   Sprite.Height = _HEIGHT(Sprite.File)
  510.   Sprite.XFrameCount = XFrameCount%
  511.   Sprite.YFrameCount = YFrameCount%
  512.   Sprite.TotalFrameCount = TotalFrameCount%
  513.   Sprite.Scale = 1
  514.   Sprite.IsVisible = -1
  515.   Sprite.Alpha = Alpha&
  516.  
  517. SUB GDK_Sprite_SetRotationPoint (Sprite AS Sprite, X!, Y!)
  518.   Sprite.RotationX = X!
  519.   Sprite.RotationY = Y!
  520.  
  521. SUB GDK_Sprite_SetVisibility (Sprite AS Sprite, OnOff AS _BYTE)
  522.   Sprite.IsVisible = OnOff
  523.  
  524. SUB GDK_Sprite_SetAlpha (Sprite AS Sprite, Alpha&)
  525.   Sprite.Alpha = Alpha&
  526.  
  527. SUB GDK_Sprite_DrawXY (Sprite AS Sprite, X%, Y%, Rotation!, AnimationFrame%)
  528.   DIM tempvect AS Vector
  529.   GDK_Vector_New tempvect, X%, Y%, 0, Rotation!
  530.   GDK_Sprite_Draw Sprite, tempvect, AnimationFrame%
  531.  
  532. SUB GDK_Sprite_Hide (Handle AS Sprite)
  533.   Handle.IsVisible = 0
  534.  
  535. SUB GDK_Sprite_Show (Handle AS Sprite)
  536.   Handle.IsVisible = -1
  537.  
  538. SUB GDK_Sprite_Free (Sprite AS Sprite)
  539.   _FREEIMAGE (Sprite.File)
  540.   Sprite.IsVisible = 0
  541.  
  542. SUB GDK_Sprite_Clone (SourceSprite AS Sprite, DestSprite AS Sprite)
  543.   DestSprite = SourceSprite
  544.  
  545. SUB GDK_Sprite_Clone_X (SourceSprite AS Sprite, DestSprite() AS Sprite, FirstClone%, NumberOfClones%)
  546.   FOR CloneCount% = FirstClone% TO FirstClone% + NumberOfClones% - 1
  547.     DestSprite(CloneCount%) = SourceSprite
  548.   NEXT
  549.  
  550. SUB GDK_Sprite_SetRotationAsCenter (Sprite AS Sprite)
  551.   GDK_Sprite_SetRotationPoint Sprite, Sprite.Width / (Sprite.XFrameCount * 2), Sprite.Height / (Sprite.YFrameCount * 2)
  552.  
  553. '// UPDATED VERSION!!
  554. SUB GDK_Sprite_Draw (Sprite AS Sprite, DestVector AS Vector, Frame%)
  555.   IF Frame% = 0 THEN Frame% = 1
  556.   _CLEARCOLOR Sprite.Alpha, Sprite.File
  557.   IF Sprite.IsVisible THEN
  558.     FrameXSize% = Sprite.Width / Sprite.XFrameCount
  559.     FrameYSize% = Sprite.Height / Sprite.YFrameCount
  560.     FrameXStart% = ((INT((Frame% - 1) MOD Sprite.XFrameCount)) * FrameXSize%)
  561.     FrameYStart% = ((INT((Frame% - 1) / Sprite.XFrameCount)) * FrameYSize%)
  562.     TmpImage& = _NEWIMAGE(FrameXSize%, FrameYSize%, 32)
  563.     _PUTIMAGE (0, 0), Sprite.File, TmpImage&, (FrameXStart%, FrameYStart%)-(FrameXStart% + FrameXSize%, FrameYStart% + FrameYSize%)
  564.     Rotate_Scale_AroundPoint DestVector.X, DestVector.Y, TmpImage&, -GDK_RadianToDegree(DestVector.Rotation), Sprite.Scale, Sprite.Scale, Sprite.RotationX, Sprite.RotationY
  565.     _FREEIMAGE TmpImage&
  566.   END IF
  567.  
  568.  
  569. '##########################################################################################################################
  570. '// SCREEN Stuff!
  571. '##########################################################################################################################
  572.  
  573. SUB GDK_Screen_SetRes (ScreenHandle&, width%, height%)
  574.   ScreenHandle& = _NEWIMAGE(width%, height%, 32)
  575.   SCREEN ScreenHandle&
  576.  
  577.  
  578. '##########################################################################################################################
  579. '// User input subs and functions.
  580. '##########################################################################################################################
  581.  
  582. SUB GDK_Keyboard_GetState (KeyboardRef AS KeyBoardState)
  583.   FOR x% = 1 TO 88 'read each key scancode from array
  584.     IF x% = 1 THEN KeyboardRef.ESC = ScanKey%(x%)
  585.     IF x% = 2 THEN KeyboardRef.Num1 = ScanKey%(x%)
  586.     IF x% = 3 THEN KeyboardRef.Num2 = ScanKey%(x%)
  587.     IF x% = 4 THEN KeyboardRef.Num3 = ScanKey%(x%)
  588.     IF x% = 5 THEN KeyboardRef.Num4 = ScanKey%(x%)
  589.     IF x% = 6 THEN KeyboardRef.Num5 = ScanKey%(x%)
  590.     IF x% = 7 THEN KeyboardRef.Num6 = ScanKey%(x%)
  591.     IF x% = 8 THEN KeyboardRef.Num7 = ScanKey%(x%)
  592.     IF x% = 9 THEN KeyboardRef.Num8 = ScanKey%(x%)
  593.     IF x% = 10 THEN KeyboardRef.Num9 = ScanKey%(x%)
  594.     IF x% = 11 THEN KeyboardRef.Num0 = ScanKey%(x%)
  595.     IF x% = 12 THEN KeyboardRef.MINUS = ScanKey%(x%)
  596.     IF x% = 13 THEN KeyboardRef.PLUS = ScanKey%(x%)
  597.     IF x% = 14 THEN KeyboardRef.BACKSPACE = ScanKey%(x%)
  598.     IF x% = 15 THEN KeyboardRef.TAB = ScanKey%(x%)
  599.     IF x% = 30 THEN KeyboardRef.A = ScanKey%(x%)
  600.     IF x% = 48 THEN KeyboardRef.B = ScanKey%(x%)
  601.     IF x% = 46 THEN KeyboardRef.C = ScanKey%(x%)
  602.     IF x% = 32 THEN KeyboardRef.D = ScanKey%(x%)
  603.     IF x% = 18 THEN KeyboardRef.E = ScanKey%(x%)
  604.     IF x% = 33 THEN KeyboardRef.F = ScanKey%(x%)
  605.     IF x% = 34 THEN KeyboardRef.G = ScanKey%(x%)
  606.     IF x% = 35 THEN KeyboardRef.H = ScanKey%(x%)
  607.     IF x% = 23 THEN KeyboardRef.I = ScanKey%(x%)
  608.     IF x% = 36 THEN KeyboardRef.J = ScanKey%(x%)
  609.     IF x% = 37 THEN KeyboardRef.K = ScanKey%(x%)
  610.     IF x% = 38 THEN KeyboardRef.L = ScanKey%(x%)
  611.     IF x% = 50 THEN KeyboardRef.M = ScanKey%(x%)
  612.     IF x% = 49 THEN KeyboardRef.N = ScanKey%(x%)
  613.     IF x% = 24 THEN KeyboardRef.O = ScanKey%(x%)
  614.     IF x% = 25 THEN KeyboardRef.P = ScanKey%(x%)
  615.     IF x% = 16 THEN KeyboardRef.Q = ScanKey%(x%)
  616.     IF x% = 19 THEN KeyboardRef.R = ScanKey%(x%)
  617.     IF x% = 31 THEN KeyboardRef.S = ScanKey%(x%)
  618.     IF x% = 20 THEN KeyboardRef.T = ScanKey%(x%)
  619.     IF x% = 22 THEN KeyboardRef.U = ScanKey%(x%)
  620.     IF x% = 47 THEN KeyboardRef.V = ScanKey%(x%)
  621.     IF x% = 17 THEN KeyboardRef.W = ScanKey%(x%)
  622.     IF x% = 45 THEN KeyboardRef.X = ScanKey%(x%)
  623.     IF x% = 21 THEN KeyboardRef.Y = ScanKey%(x%)
  624.     IF x% = 44 THEN KeyboardRef.Z = ScanKey%(x%)
  625.     IF x% = 72 THEN KeyboardRef.Up = ScanKey%(x%)
  626.     IF x% = 75 THEN KeyboardRef.Left = ScanKey%(x%)
  627.     IF x% = 77 THEN KeyboardRef.Right = ScanKey%(x%)
  628.     IF x% = 80 THEN KeyboardRef.Down = ScanKey%(x%)
  629.     IF x% = 28 THEN KeyboardRef.ENTER = ScanKey%(x%)
  630.     IF x% = 57 THEN KeyboardRef.SPACE = ScanKey%(x%)
  631.     IF x% = 29 THEN KeyboardRef.CTRL = ScanKey%(x%)
  632.     IF x% = 56 THEN KeyboardRef.ALT = ScanKey%(x%)
  633.     IF x% = 42 THEN KeyboardRef.SHIFT = ScanKey%(x%)
  634.   NEXT
  635.  
  636. FUNCTION ScanKey% (scancode%)
  637.   STATIC Ready%, keyflags%() 'retain values on procedure exit
  638.   IF NOT Ready% THEN REDIM keyflags%(0 TO 127): Ready% = -1 'create array on first use
  639.   i% = INP(&H60) 'read keyboard states
  640.   IF (i% AND 128) THEN keyflags%(i% XOR 128) = 0
  641.   IF (i% AND 128) = 0 THEN keyflags%(i%) = -1
  642.   K$ = INKEY$ 'clears key buffer to prevent beeps
  643.   ScanKey% = keyflags%(scancode%)
  644.   IF scancode% = 0 THEN Ready% = 0 'allows program to reset all values to 0 with a REDIM
  645.  
  646. SUB GDK_Mouse_GetState (MouseRef AS MouseState)
  647.   MouseRef.X = _MOUSEX
  648.   MouseRef.Y = _MOUSEY
  649.   MouseRef.LB = _MOUSEBUTTON(1)
  650.   MouseRef.RB = _MOUSEBUTTON(2)
  651.   MouseRef.MB = _MOUSEBUTTON(3)
  652.   MouseRef.MW = _MOUSEWHEEL
  653. '##########################################################################################################################
  654. '//Particle engine v.03
  655. '##########################################################################################################################
  656.  
  657. SUB GDK_Emitter_New (EmitRef AS Emitter, x%, y%, SpawnRate%, AngleMin!, AngleMax!, VelMin!, VelMax!, MinLifeTime#, MaxLifeTime#)
  658.   EmitRef.X = x%
  659.   EmitRef.Y = y%
  660.   EmitRef.SpawnRate = SpawnRate%
  661.   EmitRef.SpawnAngleMin = AngleMin!
  662.   EmitRef.SpawnAngleMax = AngleMax!
  663.   EmitRef.SpawnMaxVelocity = VelMax!
  664.   EmitRef.SpawnMinVelocity = VelMin!
  665.   EmitRef.MaxLifeTime = MaxLifeTime#
  666.   EmitRef.MinLifeTime = MinLifeTime#
  667.  
  668. SUB GDK_Emitter_SetGravity (EmitRef AS Emitter, Gravity!)
  669.   EmitRef.Gravity = Gravity!
  670.  
  671. SUB GDK_Emitter_SetAccelDecel (EmitRef AS Emitter, AccelMin!, AccelMax!, DecelMin!, DecelMax!)
  672.   EmitRef.AccelMin = AccelMin!
  673.   EmitRef.AccelMax = AccelMax!
  674.   EmitRef.DecelMIn = DecelMin!
  675.   EmitRef.DecelMax! = DecelMax!
  676.  
  677. SUB GDK_Particles_Spawn (EmitRef AS Emitter, PartRef() AS Particle, ParticleMax&, InitialColor&, ColorChange&, ChangeMode%)
  678.   PBTime# = TIMER(.001)
  679.   FOR i& = 0 TO ParticleMax&
  680.     IF NOT PartRef(i&).Exists THEN
  681.       PartRef(i&).Vector.X = EmitRef.X
  682.       PartRef(i&).Vector.Y = EmitRef.Y
  683.       PartRef(i&).Exists = -1
  684.       PartRef(i&).Vector.Rotation = (RND * EmitRef.SpawnAngleMax) + EmitRef.SpawnAngleMin
  685.       PartRef(i&).Vector.Speed = (RND * EmitRef.SpawnMaxVelocity) + EmitRef.SpawnMinVelocity
  686.       PartRef(i&).LifeTime = (RND * EmitRef.MaxLifeTime) + EmitRef.MinLifeTime
  687.       PartRef(i&).InitialCLR = InitialColor&
  688.       PartRef(i&).CurrentCLR = InitialColor&
  689.       PartRef(i&).ClrChange = ColorChange&
  690.       PartRef(i&).BirthTime = PBTime#
  691.       PartRef(i&).ClrChangeMode = ChangeMode%
  692.       IF EmitRef.AccelMax > 0 THEN
  693.         PartRef(i&).Accel = (RND * EmitRef.AccelMax) + EmitRef.AccelMin
  694.       END IF
  695.       IF EmitRef.DecelMax > 0 THEN
  696.         PartRef(i&).Decel = (RND * EmitRef.DecelMax) + EmitRef.DecelMIn
  697.       END IF
  698.       IF SuccessfulSpawns& = EmitRef.SpawnRate THEN EXIT FOR ELSE SuccessfulSpawns& = SuccessfulSpawns& + 1
  699.     END IF
  700.   NEXT
  701.  
  702. SUB GDK_Particles_Update (PartRef() AS Particle, ParticleMax&)
  703.   FOR i& = 0 TO ParticleMax&
  704.     IF PartRef(i&).Exists THEN
  705.       IF TIMER(.001) - PartRef(i&).BirthTime >= PartRef(i&).LifeTime THEN
  706.         PartRef(i&).Exists = 0
  707.       ELSE
  708.         IF PartRef(i&).Vector.Speed > 0 THEN
  709.           IF PartRef(i&).Decel > 0 THEN
  710.             IF PartRef(i&).Accel > 0 THEN
  711.               PartRef(i&).Accel = PartRef(i&).Accel - PartRef(i&).Decel
  712.             ELSE
  713.               PartRef(i&).Vector.Speed = PartRef(i&).Vector.Speed - PartRef(i&).Decel
  714.             END IF
  715.           END IF
  716.           IF PartRef(i&).Accel > 0 THEN PartRef(i&).Vector.Speed = PartRef(i&).Vector.Speed + PartRef(i&).Accel
  717.           IF PartRef(i&).ClrChangeMode = 1 THEN
  718.             PartRef(i&).CurrentCLR = _RGB32(_RED(PartRef(i&).CurrentCLR) - _RED(PartRef(i&).ClrChange), _GREEN(PartRef(i&).CurrentCLR) - _GREEN(PartRef(i&).ClrChange), _BLUE(PartRef(i&).CurrentCLR) - _BLUE(PartRef(i&).ClrChange))
  719.           ELSE
  720.             PartRef(i&).CurrentCLR = _RGB32(_RED(PartRef(i&).CurrentCLR) + _RED(PartRef(i&).ClrChange), _GREEN(PartRef(i&).CurrentCLR) + _GREEN(PartRef(i&).ClrChange), _BLUE(PartRef(i&).CurrentCLR) + _BLUE(PartRef(i&).ClrChange))
  721.           END IF
  722.           GDK_Vector_Move PartRef(i&).Vector
  723.         ELSE
  724.           PartRef(i&).Exists = 0
  725.         END IF
  726.       END IF
  727.     END IF
  728.   NEXT
  729.  
  730. SUB GDK_Particles_Draw (PartRef() AS Particle, ParticleMax&)
  731.   FOR i& = 0 TO ParticleMax&
  732.     IF PartRef(i&).Exists THEN
  733.       PSET (PartRef(i&).Vector.X, PartRef(i&).Vector.Y), PartRef(i&).CurrentCLR
  734.     END IF
  735.   NEXT
  736.  
  737. '##########################################################################################################################
  738. '// MATH FUNCTIONS
  739. '##########################################################################################################################
  740.  
  741. FUNCTION GDK_Distance! (X%, Y%, XX%, YY%)
  742.   xd% = XX% - X%
  743.   yd% = YY% - Y%
  744.   GDK_Distance! = SQR((xd% * xd%) + (yd% * yd%))
  745.  
  746. FUNCTION GDK_RadianToDegree! (Radians!)
  747.   GDK_RadianToDegree! = Radians! * (180 / (4 * ATN(1)))
  748.  
  749. FUNCTION GDK_DegreeToRadian! (Degrees!)
  750.   GDK_DegreeToRadian! = Degrees! * ((4 * ATN(1)) / 180)
  751.  
  752. SUB GDK_MathX
  753.     FUNCTION atan2# (BYVAL y#, BYVAL x#)
  754.     FUNCTION acos# (BYVAL x#)
  755.     FUNCTION asin# (BYVAL x#)
  756.     FUNCTION cosh# (BYVAL x#)
  757.     FUNCTION sinh# (BYVAL x#)
  758.     FUNCTION tanh# (BYVAL x#)
  759.     FUNCTION pow# (BYVAL base#, BYVAL exponent#)
  760.  
  761. '##########################################################################################################################
  762. '// Tile engine
  763. '##########################################################################################################################
  764.  
  765. SUB GDK_TileSet_New (TileRef AS Tileset, File$, XTiles%, YTiles%, Alpha&)
  766.   GDK_Sprite_New TileRef.Sheet, File$, XTiles%, YTiles%, XTiles% * YTiles%, Alpha&
  767.   TileRef.TWidth = (TileRef.Sheet.Width / XTiles%)
  768.   TileRef.THeight = (TileRef.Sheet.Height / YTiles%)
  769.  
  770. SUB GDK_TileMap_Load (Level() AS Tile, XTiles%, YTiles%)
  771.   FOR j% = 0 TO YTiles% - 1
  772.     FOR i% = 0 TO XTiles% - 1
  773.       READ tile%
  774.       Level(i%, j%).Tile = tile%
  775.     NEXT
  776.   NEXT
  777.  
  778. SUB GDK_TileMap_Draw (TileRef AS Tileset, Level() AS Tile, X%, Y%, XCnt%, YCnt%, XMax%, YMax%)
  779.   Tx% = X%
  780.   Ty% = Y%
  781.   sx% = _WIDTH(_DEST)
  782.   sy% = _HEIGHT(_DEST)
  783.   FOR j% = YCnt% TO YMax% - 1
  784.     FOR i% = XCnt% TO XMax% - 1
  785.       IF Tx% < sx% THEN
  786.         IF Level(i%, j%).Tile > 0 THEN
  787.           GDK_Sprite_DrawXY TileRef.Sheet, Tx%, Ty%, 0, Level(i%, j%).Tile
  788.         END IF
  789.         Tx% = Tx% + (TileRef.TWidth * TileRef.Sheet.Scale)
  790.       ELSE
  791.         EXIT FOR
  792.       END IF
  793.     NEXT
  794.     Tx% = X%
  795.     IF Ty% < sy% THEN Ty% = Ty% + (TileRef.THeight * TileRef.Sheet.Scale) ELSE EXIT FOR
  796.   NEXT
  797.  
  798.  
  799. SUB GDK_TileMap_Load_FromFile (GameFile$, Level() AS Tile, YTiles%)
  800.   X& = FREEFILE
  801.   OPEN GameFile$ FOR INPUT AS #X&
  802.   FOR i% = 0 TO YTiles% - 1
  803.     LINE INPUT #X&, DataLine$
  804.     Cnt% = 0
  805.     FOR j% = 0 TO LEN(DataLine$)
  806.       IF INSTR(j%, DataLine$, ",") > 0 THEN
  807.         Level(Cnt%, i%).Tile = VAL(MID$(DataLine$, j%, INSTR(j%, DataLine$, ",") - j%))
  808.         j% = INSTR(j%, DataLine$, ",")
  809.         Cnt% = Cnt% + 1
  810.       ELSE
  811.         Level(Cnt%, i%).Tile = VAL(MID$(DataLine$, j%))
  812.       END IF
  813.     NEXT
  814.   NEXT
  815.   CLOSE #X&
  816.  
  817. SUB GDK_Tileset_SetScale (TileRef AS Tileset, Scale!)
  818.   TileRef.Sheet.Scale = Scale!
  819.  
  820. 'SUB GDK_Tiles_Draw_ISO (TileRef AS Tileset, XYRef() AS XY, Level() AS Tile, X%, Y%, XCnt%, YCnt%, XMax%, YMax%)
  821. '  Tx% = X%
  822. '  Ty% = Y%
  823. '  YCntr% = 0
  824. '  FOR j% = YCnt% TO YMax% - 1
  825. '    FOR i% = XCnt% TO XMax% - 1
  826. '            IF Level(i%, j%).Tile > 0 THEN GDK_Tile_Draw TileRef, Level(i%, j%).Tile, XYRef(), Tx%, Ty%
  827. '            Tx% = Tx% + (TileRef.TWidth / 2)
  828. '            Ty% = Ty% + (TileRef.THeight / 4)
  829. '        NEXT
  830. '        YCntr% = YCntr% + 1
  831. '        Ty% = Y% + YCntr% * (TileRef.THeight / 4)
  832. '        Tx% = X% - (YCntr% * (TileRef.TWidth / 2))
  833. '    NEXT
  834. 'END SUB
  835.  
  836.  
  837. '##########################################################################################################################
  838. '// GameObject Subs and Functions - SUper fast prototyping commands for games
  839. '##########################################################################################################################
  840.  
  841. SUB GDK_GameObject_New (Handle AS GameObject, File$, XframeCount%, YFrameCount%, X%, Y%, Speed!, Rotation!)
  842.   GDK_Sprite_New Handle.Sprite, File$, XframeCount%, YFrameCount%, XframeCount% * YFrameCount%, 1
  843.   GDK_Vector_New Handle.Vector, X%, Y%, Speed!, Rotation!
  844.   GDK_Sprite_SetVisibility Handle.Sprite, -1
  845.   GDK_Sprite_SetAlpha Handle.Sprite, _RGB(255, 0, 255)
  846.  
  847. SUB GDK_GameObject_Draw (GameObject AS GameObject, AnimationFrame%)
  848.   GDK_Sprite_Draw GameObject.Sprite, GameObject.Vector, AnimationFrame%
  849.  
  850. SUB GDK_GameObject_Update (Handle AS GameObject)
  851.   GDK_Vector_Update Handle.Vector
  852.   GDK_Rectangle_Autosize Handle.Sprite, Handle.Vector, Handle.Rect
  853.  
  854. SUB GDK_GameObject_Rotate (Handle AS GameObject, Rot!)
  855.   Handle.Vector.Rotation = Handle.Vector.Rotation + Rot!
  856.  
  857. SUB GDK_GameObject_Hide (Handle AS GameObject)
  858.   Handle.Sprite.IsVisible = 0
  859.  
  860. SUB GDK_GameObject_Show (Handle AS GameObject)
  861.   Handle.Sprite.IsVisible = -1
  862.  
  863. FUNCTION GDK_GameObject_Intersect (Handle AS GameObject, Handle2 AS GameObject)
  864.   IF GDK_Rectangle_Intersect(Handle.Rect, Handle2.Rect) THEN
  865.     GDK_GameObject_Intersect = -1
  866.   ELSE
  867.     GDK_GameObject_Intersect = 0
  868.   END IF
  869.  
  870. '##########################################################################################################################
  871. '// Animation routines - Taken from GDK_GL
  872. '##########################################################################################################################
  873.  
  874. SUB GDK_ANIMATION_NEW (Anim AS ANIMATION, Frame%, StartFrame%, ResetFrame%, AnimTime#, AnimTimer#)
  875.   Anim.Frame = Frame%
  876.   Anim.StartFrame = StartFrame%
  877.   Anim.ResetFrame = ResetFrame%
  878.   Anim.Time = AnimTime#
  879.   Anim.Timer = AnimTimer#
  880.   IF ResetFrame% < StartFrame% THEN Anim.Dir = -1 ELSE Anim.Dir = 0
  881.  
  882. SUB GDK_ANIMATION_UPDATE (Anim AS ANIMATION)
  883.   IF Anim.Dir = -1 THEN
  884.     IF Anim.Frame > Anim.StartFrame OR Anim.Frame < Anim.ResetFrame THEN
  885.       Anim.Frame = Anim.StartFrame
  886.       Anim.Timer = TIMER(.001)
  887.     ELSE
  888.       IF TIMER(.001) - Anim.Timer >= Anim.Time THEN
  889.         IF Anim.Frame = Anim.ResetFrame THEN
  890.           Anim.Frame = Anim.StartFrame
  891.         ELSE
  892.           Anim.Frame = Anim.Frame - 1
  893.         END IF
  894.         Anim.Timer = TIMER(.001)
  895.       END IF
  896.     END IF
  897.   ELSE
  898.     IF Anim.Frame < Anim.StartFrame OR Anim.Frame > Anim.ResetFrame THEN
  899.       Anim.Frame = Anim.StartFrame
  900.       Anim.Timer = TIMER(.001)
  901.     ELSE
  902.       IF TIMER(.001) - Anim.Timer >= Anim.Time THEN
  903.         IF Anim.Frame = Anim.ResetFrame THEN
  904.           Anim.Frame = Anim.StartFrame
  905.         ELSE
  906.           Anim.Frame = Anim.Frame + 1
  907.         END IF
  908.         Anim.Timer = TIMER(.001)
  909.       END IF
  910.     END IF
  911.   END IF
  912. '##########################################################################################################################
  913. '// Image ROTATION/ZOOM FUNCTION BY GALLEON
  914. '##########################################################################################################################
  915.  
  916. SUB Rotate_Scale_AroundPoint (X AS LONG, Y AS LONG, Image AS LONG, Rotation AS SINGLE, ScaleX AS SINGLE, ScaleY AS SINGLE, PointX AS LONG, PointY AS LONG)
  917.   DEFSNG A-Z
  918.   DIM pX(3) AS SINGLE: DIM pY(3) AS SINGLE
  919.   DIM W AS LONG, H AS LONG, I AS LONG, X2 AS LONG, Y2 AS LONG
  920.   W = _WIDTH(Image): H = _HEIGHT(Image)
  921.   pX(0) = -PointX: pY(0) = -PointY: pX(1) = -PointX: pY(1) = -PointY + H - 1: pX(2) = -PointX + W - 1: pY(2) = -PointY + H - 1: pX(3) = -PointX + W - 1: pY(3) = -PointY 'Set dest screen points
  922.   Radians = -Rotation / 57.29578: SINr = SIN(Radians): COSr = COS(Radians) 'Precalculate SIN & COS of angle
  923.   FOR I = 0 TO 3
  924.     pX(I) = pX(I) * ScaleX: pY(I) = pY(I) * ScaleY 'Scale
  925.     X2 = pX(I) * COSr + SINr * pY(I): pY(I) = pY(I) * COSr - pX(I) * SINr: pX(I) = X2 'Rotate Dest Points
  926.     pX(I) = pX(I) + X: pY(I) = pY(I) + Y 'Translate Dest Points
  927.   NEXT
  928.   _MAPTRIANGLE (0, 0)-(0, H - 1)-(W - 1, H - 1), Image TO(pX(0), pY(0))-(pX(1), pY(1))-(pX(2), pY(2))
  929.   _MAPTRIANGLE (0, 0)-(W - 1, 0)-(W - 1, H - 1), Image TO(pX(0), pY(0))-(pX(3), pY(3))-(pX(2), pY(2))
  930.  
  931.  
  932.  
  933.  
  934.  
  935. '##########################################################################################################################
  936. '// Path based movement v.02
  937. '##########################################################################################################################
  938.  
  939. SUB GDK_Path_New (Path AS Path, PathPoint() AS PathPoint, NumPoints%, Reverse%, Repeat%, Relative%)
  940.   IF Relative% THEN READ Path.Vector.X, Path.Vector.Y, Path.Vector.Speed
  941.   FOR i% = 0 TO NumPoints% - 1
  942.     READ PathPoint(i%).X, PathPoint(i%).Y, PathPoint(i%).Speed
  943.   NEXT
  944.   IF Relative% THEN
  945.     Path.TargetVector.X = Path.Vector.X + PathPoint(0).X
  946.     Path.TargetVector.Y = Path.Vector.Y + PathPoint(0).Y
  947.     Path.Vector.Rotation = -atan2(Path.Vector.Y - Path.TargetVector.Y, Path.Vector.X - Path.TargetVector.X) + (2 * ATN(1))
  948.   ELSE
  949.     Path.Vector.X = PathPoint(0).X
  950.     Path.Vector.Y = PathPoint(0).Y
  951.     Path.Vector.Speed = PathPoint(0).Speed
  952.     Path.Vector.Rotation = -atan2(PathPoint(0).Y - PathPoint(1).Y, PathPoint(0).X - PathPoint(1).X) + (2 * ATN(1))
  953.     Path.TargetVector.X = PathPoint(1).X
  954.     Path.TargetVector.Y = PathPoint(1).Y
  955.   END IF
  956.   Path.LastVector = Path.Vector
  957.   Path.NumPoints = NumPoints%
  958.   Path.Reverse = Reverse%
  959.   Path.Repeat = Repeat%
  960.   Path.Relative = Relative%
  961.  
  962.  
  963. SUB GDK_Path_Update (Path AS Path, PathPoint() AS PathPoint)
  964.   IF Path.Relative THEN '// Relative movement
  965.     IF NOT Path.HitTargetX THEN IF IsWithinRange(Path.TargetVector.X, Path.LastVector.X, Path.Vector.X) THEN Path.HitTargetX = -1
  966.     IF NOT Path.HitTargetY THEN IF IsWithinRange(Path.TargetVector.Y, Path.LastVector.Y, Path.Vector.Y) THEN Path.HitTargetY = -1
  967.     IF Path.HitTargetX AND Path.HitTargetY THEN
  968.       IF Path.CurrentPoint < Path.NumPoints - 1 THEN
  969.         Path.TargetVector.X = Path.Vector.X + PathPoint(Path.CurrentPoint + 1).X
  970.         Path.TargetVector.Y = Path.Vector.Y + PathPoint(Path.CurrentPoint + 1).Y
  971.         Path.Vector.Rotation = -atan2(Path.Vector.Y - Path.TargetVector.Y, Path.Vector.X - Path.TargetVector.X) + (2 * ATN(1))
  972.         Path.Vector.Speed = PathPoint(Path.CurrentPoint).Speed
  973.         Path.CurrentPoint = Path.CurrentPoint + 1
  974.       ELSE '// Last point
  975.         IF Path.Repeat THEN
  976.           Path.CurrentPoint = 0
  977.           Path.TargetVector.X = Path.Vector.X + PathPoint(0).X
  978.           Path.TargetVector.Y = Path.Vector.Y + PathPoint(0).Y
  979.           Path.Vector.Rotation = -atan2(Path.Vector.Y - Path.TargetVector.Y, Path.Vector.X - Path.TargetVector.X) + (2 * ATN(1))
  980.           Path.Vector.Speed = PathPoint(0).Speed
  981.         ELSE
  982.           Path.Vector.Speed = 0
  983.         END IF
  984.       END IF
  985.       Path.HitTargetX = 0
  986.       Path.HitTargetY = 0
  987.     END IF
  988.   ELSE '// Co-ordinate based movement
  989.     IF Path.IsReversing THEN
  990.       IF Path.CurrentPoint > 0 THEN
  991.         IF NOT Path.HitTargetX THEN IF IsWithinRange(PathPoint(Path.CurrentPoint - 1).X, Path.LastVector.X, Path.Vector.X) THEN Path.HitTargetX = -1
  992.         IF NOT Path.HitTargetY THEN IF IsWithinRange(PathPoint(Path.CurrentPoint - 1).Y, Path.LastVector.Y, Path.Vector.Y) THEN Path.HitTargetY = -1
  993.         IF Path.HitTargetX AND Path.HitTargetY THEN
  994.           IF Path.CurrentPoint > 1 THEN
  995.             Path.CurrentPoint = Path.CurrentPoint - 1
  996.             Path.Vector.Rotation = -atan2(Path.Vector.Y - PathPoint(Path.CurrentPoint - 1).Y, Path.Vector.X - PathPoint(Path.CurrentPoint - 1).X) + (2 * ATN(1))
  997.           ELSE '// First point
  998.             Path.CurrentPoint = 0
  999.             IF Path.Reverse THEN
  1000.               Path.IsReversing = 0
  1001.               Path.Vector.Rotation = -atan2(Path.Vector.Y - PathPoint(Path.CurrentPoint + 1).Y, Path.Vector.X - PathPoint(Path.CurrentPoint + 1).X) + (2 * ATN(1))
  1002.             END IF
  1003.           END IF
  1004.           Path.HitTargetX = 0
  1005.           Path.HitTargetY = 0
  1006.           Path.Vector.Speed = PathPoint(Path.CurrentPoint).Speed
  1007.         END IF
  1008.       END IF
  1009.     ELSE
  1010.       IF Path.CurrentPoint <= Path.NumPoints - 1 THEN
  1011.         IF NOT Path.HitTargetX THEN IF IsWithinRange(PathPoint(Path.CurrentPoint + 1).X, Path.LastVector.X, Path.Vector.X) THEN Path.HitTargetX = -1
  1012.         IF NOT Path.HitTargetY THEN IF IsWithinRange(PathPoint(Path.CurrentPoint + 1).Y, Path.LastVector.Y, Path.Vector.Y) THEN Path.HitTargetY = -1
  1013.         IF Path.HitTargetX AND Path.HitTargetY THEN
  1014.           IF Path.CurrentPoint < Path.NumPoints - 2 THEN
  1015.             Path.CurrentPoint = Path.CurrentPoint + 1
  1016.             Path.Vector.Rotation = -atan2(Path.Vector.Y - PathPoint(Path.CurrentPoint + 1).Y, Path.Vector.X - PathPoint(Path.CurrentPoint + 1).X) + (2 * ATN(1))
  1017.           ELSE '// Last point
  1018.             Path.CurrentPoint = Path.NumPoints - 1
  1019.             IF Path.Reverse THEN
  1020.               Path.IsReversing = -1
  1021.               Path.Vector.Rotation = -atan2(Path.Vector.Y - PathPoint(Path.CurrentPoint - 1).Y, Path.Vector.X - PathPoint(Path.CurrentPoint - 1).X) + (2 * ATN(1))
  1022.             ELSEIF Path.Repeat THEN
  1023.               Path.CurrentPoint = 0
  1024.               IF Path.Repeat THEN
  1025.                 FOR i% = 1 TO Path.NumPoints - 1
  1026.                   XDif% = PathPoint(i%).X - PathPoint(i% - 1).X
  1027.                   YDif% = PathPoint(i%).Y - PathPoint(i% - 1).Y
  1028.                   IF i% = 1 THEN
  1029.                     PathPoint(0).X = Path.Vector.X
  1030.                     PathPoint(0).Y = Path.Vector.Y
  1031.                   END IF
  1032.                   PathPoint(i%).X = PathPoint(i% - 1).X + XDif%
  1033.                   PathPoint(i%).Y = PathPoint(i% - 1).Y + YDif%
  1034.                 NEXT
  1035.               END IF
  1036.               Path.Vector.Rotation = -atan2(Path.Vector.Y - PathPoint(Path.CurrentPoint + 1).Y, Path.Vector.X - PathPoint(Path.CurrentPoint + 1).X) + (2 * ATN(1))
  1037.             ELSE '// Stop at end
  1038.               PathPoint(Path.CurrentPoint).Speed = 0
  1039.             END IF
  1040.           END IF
  1041.           Path.Vector.Speed = PathPoint(Path.CurrentPoint).Speed
  1042.           Path.HitTargetX = 0
  1043.           Path.HitTargetY = 0
  1044.         END IF
  1045.       END IF
  1046.     END IF
  1047.   END IF
  1048.   Path.LastVector = Path.Vector
  1049.   GDK_Vector_Update Path.Vector
  1050.  
  1051. '// GDK_Path_Update helper function
  1052. FUNCTION IsWithinRange% (Target%, MinRange%, MaxRange%)
  1053.   IF Target% >= MinRange% AND Target% <= MaxRange% THEN
  1054.     IsWithinRange% = -1
  1055.   ELSEIF Target% <= MinRange% AND Target% >= MaxRange% THEN
  1056.     IsWithinRange% = -1
  1057.   ELSE
  1058.     IsWithinRange% = 0
  1059.   END IF
  1060.  
  1061.  
  1062. '##########################################################################################################################
  1063. '// END OF LIBRARY!!!
  1064. '##########################################################################################################################
  1065.  
  1066.  

« Last Edit: April 21, 2020, 03:35:59 am by Unseen Machine »