diff options
Diffstat (limited to 'src/Update/CloudUpdate.elm')
-rw-r--r-- | src/Update/CloudUpdate.elm | 106 |
1 files changed, 106 insertions, 0 deletions
diff --git a/src/Update/CloudUpdate.elm b/src/Update/CloudUpdate.elm new file mode 100644 index 0000000..86f7e13 --- /dev/null +++ b/src/Update/CloudUpdate.elm @@ -0,0 +1,106 @@ +module Update.CloudUpdate + ( cloudUpdate + ) where + +import List +import Random (..) + +import Model.Vec2 (..) +import Model.Player (..) +import Model.Board (boardSize, boardDiagonal) +import Model.Point (..) +import Model.Cloud (..) +import Model.Config (..) + +import Utils.Geometry (..) +import Utils.Physics (getMove, getWaveMove) + +cloudUpdate : Float -> Seed -> Player -> Cloud -> (Cloud, Int, Seed) +cloudUpdate time seed player {points, spawn, lastSpawn} = + let pointsToCatch = presentPoints time (points player.config) + presentAndNotCaughtPoints = List.filter (not << (playerPointCollision time player)) pointsToCatch + addScore = (List.length pointsToCatch) - (List.length presentAndNotCaughtPoints) + presentOtherPoints = presentPoints time (points (otherConfig player.config)) + (newCloud, seed''') = + if time > lastSpawn + spawn then + let (newPoint1, seed') = getNewPoint time seed + (newPoint2, seed'') = getNewPoint time seed' + in ( { points config = + if(config == player.config) + then + newPoint1 :: presentAndNotCaughtPoints + else + newPoint2 :: presentOtherPoints + , spawn = spawn - sqrt(spawn) / 50 + , lastSpawn = time + } + , seed'' + ) + else + ( { points config = + if(config == player.config) then + presentAndNotCaughtPoints + else + presentOtherPoints + , spawn = spawn + , lastSpawn = lastSpawn + } + , seed + ) + in (newCloud, addScore, seed''') + +presentPoints : Float -> List Point -> List Point +presentPoints time points = + let isPresent point = (distance (pointMove point time) originVec) < pointAwayDist + in List.filter isPresent points + + +getNewPoint : Float -> Seed -> (Point, Seed) +getNewPoint time seed = + let (initPos, seed') = pointInitPos seed + (initDest, seed'') = pointDestination seed' + in ( { initTime = time + , initPos = initPos + , initDest = initDest + , move initTime initPos initDest time = + let delta = time - initTime + move = getWaveMove (pointSpeed delta) (initDest `sub` initPos) 10 10 + in initPos `add` move + } + , seed'' + ) + +pointInitPos : Seed -> (Vec2, Seed) +pointInitPos seed = + let (rand, seed') = generate floatGen seed + angle = rand * (degrees 360) + dist = boardDiagonal * 3 / 5 + in (polarToCartesian angle dist, seed') + +pointDestination : Seed -> (Vec2, Seed) +pointDestination seed = + let ([r1, r2, r3, r4], seed') = generateMany 4 floatGen seed + in ( randomBoardPosition (r1, r2) (r3, r4) + , seed' + ) + +generateMany : Int -> Generator a -> Seed -> (List a, Seed) +generateMany count gen seed = + if count == 0 + then + ([], seed) + else + let (rand, seed') = generate gen seed + (randList, seed'') = generateMany (count - 1) gen seed' + in (rand :: randList, seed'') + +floatGen : Generator Float +floatGen = float 0 1 + +randomBoardPosition : (Float, Float) -> (Float, Float) -> Vec2 +randomBoardPosition (randomX, randomY) (percentX, percentY) = + let width = boardSize.x * percentX + height = boardSize.y * percentY + in { x = width * randomX - width / 2 + , y = height * randomY - height / 2 + } |