shapes-0.1.0.0: src/Physics/Scenes/Stacks.hs
module Physics.Scenes.Stacks where
import Control.Lens
import Control.Monad
import Data.Proxy
import Physics.Engine.Class
import Physics.Scenes.Scene
import Physics.World.Class
box :: (PhysicsEngine e)
=> Proxy e
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> PEPhysicalObj e
box p (x, y) (vx, vy) =
makePhysicalObj p (vx, vy) 0 (x, y) 0 (2, 1)
boxFloor :: (PhysicsEngine e) => Proxy e -> PEPhysicalObj e
boxFloor p =
makePhysicalObj p (0, 0) 0 (0, -6) 0 (0, 0)
box' :: (PhysicsEngine e)
=> Proxy e
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> PEExternalObj e
-> PEWorldObj' e
box' p (w, h) center velocity =
makeWorldObj p (box p center velocity) 0.2 (makeRectangleHull p w h)
boxFloor' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> PEWorldObj' e
boxFloor' p =
makeWorldObj p (boxFloor p) 0.2 (makeRectangleHull p 18 1)
boxStack :: (PhysicsEngine e)
=> Proxy e
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> PENumber e
-> Int
-> PEExternalObj e
-> [PEWorldObj' e]
boxStack _ _ _ _ _ 0 _ = []
boxStack p size@(_, h) bottom vel spacing n ext =
box' p size bottom vel ext : boxStack p size bottom' vel spacing (n - 1) ext
where bottom' = bottom & _2 %~ (+ (h + spacing))
stacks :: (PhysicsEngine e)
=> Proxy e
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> (PENumber e, PENumber e)
-> PENumber e
-> (Int, Int)
-> PEExternalObj e
-> [PEWorldObj' e]
stacks p size@(w, _) (center, bottom) vel spacing (n_w, n_h) ext =
join . fmap f . take n_w $ iterate (+ w) leftmost
where leftmost = center - (w * fromIntegral (n_w - 1) / 2)
f left = boxStack p size (left, bottom) vel spacing n_h ext
world :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> PEWorld' e
world p ext = makeWorld p $ concat [ [boxFloor' p ext]
, boxStack p (2, 2) (8 , -4.5) (-1, 0) 0 5 ext
, boxStack p (2, 2) (5.5, -4.5) (-2, 0) 0 5 ext
]
world' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> PEWorld' e
world' p ext = makeWorld p $ concat [ [boxFloor' p ext]
, boxStack p (2, 2) (0, -4.5) (0, 0) 0 5 ext
, [box' p (2, 2) (8, 0) (-6, 0) ext]
]
world'' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> PEWorld' e
world'' p ext =
makeWorld p (boxFloor' p ext : stacks p (1, 1) (0, -4.5) (0, 0) 1 (10, 10) ext)
world''' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> PEWorld' e
world''' p ext =
makeWorld p (boxFloor' p ext : stacks p (0.75, 0.75) (0, -4.5) (0, 0) 1 (15, 15) ext)
externals :: (PhysicsEngine e) => Proxy e -> [External]
externals p = [makeConstantAccel p (0, -2)]
contactBehavior :: (PhysicsEngine e) => Proxy e -> PEContactBehavior e
contactBehavior p = makeContactBehavior p 0.01 0.02
scene :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> Scene e
scene p ext = Scene (world p ext) (externals p) (contactBehavior p)
scene' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> Scene e
scene' p ext = Scene (world' p ext) (externals p) (contactBehavior p)
scene'' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> Scene e
scene'' p ext = Scene (world'' p ext) (externals p) (contactBehavior p)
scene''' :: (PhysicsEngine e) => Proxy e -> PEExternalObj e -> Scene e
scene''' p ext = Scene (world''' p ext) (externals p) (contactBehavior p)
makeScene :: (PhysicsEngine e) => (Int, Int) -> PENumber e -> Proxy e -> PEExternalObj e -> Scene e
makeScene dims spacing p ext = Scene w (externals p) (contactBehavior p)
where w = makeWorld p (boxFloor' p ext : stacks p (0.2, 0.2) (0, -4.5) (0, 0) spacing dims ext)