Advertisement
Guest User

Untitled

a guest
Feb 24th, 2012
300
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 8.84 KB | None | 0 0
  1. --[[
  2.     PHYSICS LIBRARY THING
  3.     WRITTEN BY MAURICE GUÉGAN FOR MARI0
  4.     DON'T STEAL MY SHIT
  5.     Licensed under the same license as the game itself.
  6.     http://creativecommons.org/licenses/by-nc-sa/3.0/
  7. ]]--
  8.  
  9. function physicsupdate(dt)
  10.     local lobjects = objects
  11.    
  12.     for j, w in pairs(lobjects) do
  13.         if j ~= "tile" then
  14.             for i, v in pairs(w) do
  15.                 if v.static == false and v.active then
  16.                     --GRAVITY
  17.                     v.speedy = v.speedy + (v.gravity or yacceleration)*dt
  18.                     if v.speedy > maxyspeed then
  19.                         v.speedy = maxyspeed
  20.                     end
  21.                    
  22.                     --COLLISIONS ROFL
  23.                     local horcollision = false
  24.                     local vercollision = false
  25.                    
  26.                     --VS OTHER OBJECTS --but not portalwall
  27.                     for h, u in pairs(lobjects) do
  28.                         if h ~= "tile" and h ~= "portalwall" then
  29.                             local hor, ver = handlegroup(i, h, u, v, j, dt)
  30.                             if hor then
  31.                                 horcollision = true
  32.                             end
  33.                             if ver then
  34.                                 vercollision = true
  35.                             end
  36.                         end
  37.                     end
  38.                    
  39.                     --VS TILES (Because I only wanna check close ones)
  40.                     local xstart = math.floor(v.x+v.speedx*dt-2/16)+1
  41.                     local ystart = math.floor(v.y+v.speedy*dt-2/16)+1
  42.                    
  43.                     if tiledebug then
  44.                         debugchecked = {}
  45.                     end
  46.                    
  47.                     for x = xstart, xstart+math.ceil(v.width) do
  48.                         for y = ystart, ystart+math.ceil(v.height) do
  49.                             if tiledebug then
  50.                                 table.insert(debugchecked, x)
  51.                                 table.insert(debugchecked, y)
  52.                                 deb = false
  53.                             end
  54.                             local t = lobjects["tile"][x .. "-" .. y]
  55.                             if t then
  56.                                 --    Same object          Active        Not masked
  57.                                 if (i ~= g or j ~= h) and t.active and v.mask[t.category] ~= true then
  58.                                     local collision1, collision2 = checkcollision(v, t, "tile", x .. "-" .. y, j, i, dt)
  59.                                     if collision1 then
  60.                                         horcollision = true
  61.                                         if tiledebug then
  62.                                             deb = true
  63.                                         end
  64.                                     elseif collision2 then
  65.                                         vercollision = true
  66.                                         if tiledebug then
  67.                                             deb = true
  68.                                         end
  69.                                     end
  70.                                 end
  71.                             end
  72.                             if tiledebug then
  73.                                 table.insert(debugchecked, deb)
  74.                             end
  75.                         end
  76.                     end
  77.                    
  78.                     --VS PORTALWALL
  79.                     local h = portalwall
  80.                     local u = objects["portalwall"]
  81.                     local hor, ver = handlegroup(i, h, u, v, j, dt)
  82.                     if hor then
  83.                         horcollision = true
  84.                     end
  85.                     if ver then
  86.                         vercollision = true
  87.                     end
  88.                    
  89.                     --Check for emancipation grill
  90.                     if v.emancipatecheck then
  91.                         for h, u in pairs(emancipationgrills) do
  92.                             if u.dir == "hor" then
  93.                                 if inrange(v.x+6/16, u.startx-1, u.endx, true) and inrange(u.y-14/16, v.y, v.y+v.speedy*dt, true) then
  94.                                     v:emancipate(h)
  95.                                 end
  96.                             else
  97.                                 if inrange(v.y+6/16, u.starty-1, u.endy, true) and inrange(u.x-14/16, v.x, v.x+v.speedx*dt, true) then
  98.                                     v:emancipate(h)
  99.                                 end
  100.                             end
  101.                         end
  102.                     end
  103.                    
  104.                     --Move the object
  105.                     if vercollision == false then
  106.                         v.y = v.y + v.speedy*dt
  107.                         if v.gravity then
  108.                             if v.speedy == v.gravity*dt and v.startfall then
  109.                                 v:startfall(i)
  110.                             end
  111.                         else
  112.                             if v.speedy == yacceleration*dt and v.startfall then
  113.                                 v:startfall(i)
  114.                             end
  115.                         end
  116.                     end
  117.                    
  118.                     if horcollision == false then
  119.                         v.x = v.x + v.speedx*dt
  120.                     end
  121.                 end
  122.             end
  123.         end
  124.     end
  125. end
  126.  
  127. function handlegroup(i, h, u, v, j, dt)
  128.     local horcollision = false
  129.     local vercollision = false
  130.     for g, t in pairs(u) do
  131.         --    Same object?          Active                 Not masked
  132.         if (i ~= g or j ~= h) and t.active and (v.mask == nil or v.mask[t.category] ~= true) and (t.mask == nil or t.mask[v.category] ~= true) then
  133.             local collision1, collision2 = checkcollision(v, t, h, g, j, i, dt)
  134.             if collision1 then
  135.                 horcollision = true
  136.             elseif collision2 then
  137.                 vercollision = true
  138.             end
  139.         end
  140.     end
  141.    
  142.     return horcollision, vercollision
  143. end
  144.  
  145. function passivecollision(v, t, h, g, j, i, dt)
  146.     if v.passivecollide then
  147.         v:passivecollide(h, t)
  148.         if t.passivecollide then
  149.             t:passivecollide(j, v)
  150.         end
  151.     else
  152.         if v.floorcollide then
  153.             if v:floorcollide(h, t, dt) ~= false then
  154.                 if v.speedy > 0 then
  155.                     v.speedy = 0
  156.                 end
  157.                 v.y = t.y - v.height
  158.                 return true
  159.             end
  160.         else
  161.             if v.speedy > 0 then
  162.                 v.speedy = 0
  163.             end
  164.             v.y = t.y - v.height
  165.             return true
  166.         end
  167.     end
  168.    
  169.     return false
  170. end
  171.  
  172. function horcollision(v, t, h, g, j, i, dt)
  173.     if v.speedx < 0 then
  174.         --move object RIGHT (because it was moving left)
  175.        
  176.         if t.rightcollide then
  177.             if t:rightcollide(j, v) ~= false then
  178.                 if t.speedx and t.speedx > 0 then
  179.                     t.speedx = 0
  180.                 end
  181.             end
  182.         else
  183.             if t.speedx and t.speedx > 0 then
  184.                 t.speedx = 0
  185.             end
  186.         end
  187.         if v.leftcollide then
  188.             if v:leftcollide(h, t) ~= false then
  189.                 if v.speedx < 0 then
  190.                     v.speedx = 0
  191.                 end
  192.                 v.x = t.x + t.width
  193.                 return true
  194.             end
  195.         else
  196.             if v.speedx < 0 then
  197.                 v.speedx = 0
  198.             end
  199.             v.x = t.x + t.width
  200.             return true
  201.         end
  202.     else
  203.         --move object LEFT (because it was moving right)
  204.        
  205.         if t.leftcollide then
  206.             if t:leftcollide(j, v) ~= false then
  207.                 if t.speedx and t.speedx < 0 then
  208.                     t.speedx = 0
  209.                 end
  210.             end
  211.         else
  212.             if t.speedx and t.speedx < 0 then
  213.                 t.speedx = 0
  214.             end
  215.         end
  216.        
  217.         if v.rightcollide then
  218.             if v:rightcollide(h, t) ~= false then
  219.                 if v.speedx > 0 then
  220.                     v.speedx = 0
  221.                 end
  222.                 v.x = t.x - v.width
  223.                 return true
  224.             end
  225.         else
  226.             if v.speedx > 0 then
  227.                 v.speedx = 0
  228.             end
  229.             v.x = t.x - v.width
  230.             return true
  231.         end
  232.     end
  233.    
  234.     return false
  235. end
  236.  
  237. function vercollision(v, t, h, g, j, i, dt)
  238.     if v.speedy < 0 then
  239.         --move object DOWN (because it was moving up)
  240.         if t.floorcollide then
  241.             if t:floorcollide(j, v) ~= false then
  242.                 if t.speedy and t.speedy > 0 then
  243.                     t.speedy = 0
  244.                 end
  245.             end
  246.         else
  247.             if t.speedy and t.speedy > 0 then
  248.                 t.speedy = 0
  249.             end
  250.         end
  251.        
  252.         if v.ceilcollide then
  253.             if v:ceilcollide(h, t) ~= false then
  254.                 if v.speedy < 0 then
  255.                     v.speedy = 0
  256.                 end
  257.                 v.y = t.y  + t.height
  258.                 return true
  259.             end
  260.         else
  261.             if v.speedy < 0 then
  262.                 v.speedy = 0
  263.             end
  264.             v.y = t.y  + t.height
  265.             return true
  266.         end
  267.     else                   
  268.         if t.ceilcollide then
  269.             if t:ceilcollide(j, v) ~= false then
  270.                 if t.speedy and t.speedy < 0 then
  271.                     t.speedy = 0
  272.                 end
  273.             end
  274.         else
  275.             if t.speedy and t.speedy < 0 then
  276.                 t.speedy = 0
  277.             end
  278.         end
  279.         if v.floorcollide then
  280.             if v:floorcollide(h, t, dt) ~= false then
  281.                 if v.speedy > 0 then
  282.                     v.speedy = 0
  283.                 end
  284.                 v.y = t.y - v.height
  285.                 return true
  286.             end
  287.         else
  288.             if v.speedy > 0 then
  289.                 v.speedy = 0
  290.             end
  291.             v.y = t.y - v.height
  292.             return true
  293.         end
  294.     end
  295.     return false
  296. end
  297.  
  298. function checkcollision(v, t, h, g, j, i, dt) --v: b1table | t: b2table | h: b2type | g: b2id | j: b1type | i: b1id
  299.     local hadhorcollision = false
  300.     local hadvercollision = false
  301.    
  302.     if true then --math.abs(v.x-t.x)+math.abs(v.y-t.y) < 5 then
  303.         --check if it's a passive collision (Object is colliding anyway)
  304.         if aabb(v.x, v.y, v.width, v.height, t.x, t.y, t.width, t.height) then --passive collision! (oh noes!)
  305.             if passivecollision(v, t, h, g, j, i, dt) then
  306.                 hadvercollision = true
  307.             end
  308.            
  309.         elseif aabb(v.x + v.speedx*dt, v.y + v.speedy*dt, v.width, v.height, t.x, t.y, t.width, t.height) then
  310.             if aabb(v.x + v.speedx*dt, v.y, v.width, v.height, t.x, t.y, t.width, t.height) then --Collision is horizontal!
  311.                 if horcollision(v, t, h, g, j, i, dt) then
  312.                     hadhorcollision = true
  313.                 end
  314.                
  315.             elseif aabb(v.x, v.y+v.speedy*dt, v.width, v.height, t.x, t.y, t.width, t.height) then --Collision is vertical!
  316.                 if vercollision(v, t, h, g, j, i, dt) then
  317.                     hadvercollision = true
  318.                 end
  319.                
  320.             else
  321.                 --We're fucked, it's a diagonal collision! run!
  322.                 --Okay actually let's take this slow okay. Let's just see if we're moving faster horizontally than vertically, aight?
  323.                 local grav = yacceleration
  324.                 if self and self.gravity then
  325.                     grav = self.gravity
  326.                 end
  327.                 if math.abs(v.speedy-grav*dt) < math.abs(v.speedx) then
  328.                     --vertical collision it is.
  329.                     if vercollision(v, t, h, g, j, i, dt) then
  330.                         hadvercollision = true
  331.                     end
  332.                 else
  333.                     --okay so we're moving mainly vertically, so let's just pretend it was a horizontal collision? aight cool.
  334.                     if horcollision(v, t, h, g, j, i, dt) then
  335.                         hadhorcollision = true
  336.                     end
  337.                 end
  338.             end
  339.         end
  340.     end
  341.    
  342.     return hadhorcollision, hadvercollision
  343. end
  344.  
  345. function aabb(ax, ay, awidth, aheight, bx, by, bwidth, bheight)
  346.     return ax+awidth > bx and ax < bx+bwidth and ay+aheight > by and ay < by+bheight
  347. end
  348.  
  349. function aabbOLD(ax, ay, awidth, aheight, bx, by, bwidth, bheight) --old.
  350.     if math.abs((ay+aheight/2) - (by+bheight/2)) < bheight/2+aheight/2 and
  351.         math.abs((ax+awidth/2) - (bx+bwidth/2)) < bwidth/2+awidth/2 then
  352.         return true
  353.     else
  354.         return false
  355.     end
  356. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement