From cabfc3696035db2cbc015c42b69da0a796ba010d Mon Sep 17 00:00:00 2001 From: Jafet Date: Thu, 16 Nov 2017 18:47:52 +0800 Subject: [PATCH] flappy: add bird images --- examples/flappy/Main.hs | 41 +++++++++++++++++++++++++++++++--------- helm.cabal | 6 ++++++ images/bird-dead.png | Bin 0 -> 3418 bytes images/bird-flap.png | Bin 0 -> 3922 bytes images/bird.png | Bin 0 -> 3408 bytes 5 files changed, 38 insertions(+), 9 deletions(-) create mode 100644 images/bird-dead.png create mode 100644 images/bird-flap.png create mode 100644 images/bird.png diff --git a/examples/flappy/Main.hs b/examples/flappy/Main.hs index cb3078c..b1975d8 100644 --- a/examples/flappy/Main.hs +++ b/examples/flappy/Main.hs @@ -4,11 +4,13 @@ module Main where import Data.List (find) +import qualified Data.Map as M import Data.Maybe (isJust) import Debug.Trace (traceShow) import Text.Printf (printf) import Linear.V2 (V2(V2)) +import System.FilePath (()) import qualified System.Random as Rand import Helm @@ -24,6 +26,8 @@ import qualified Helm.Sub as Sub import qualified Helm.Time as Time import Helm.Time (Time) +import qualified Paths_helm as Paths + -- | Represents the game actions for our game. data Action = DoNothing -- ^ Do nothing. @@ -55,10 +59,12 @@ data Model = Model , obstacles :: [Obstacle] , timeScore :: Time , timeSpeed :: Double + -- not really part of game state, but most convenient to stuff it here + , assets :: M.Map String (Image SDLEngine) } -initial :: (Model, Cmd SDLEngine Action) -initial = +initial :: M.Map String (Image SDLEngine) -> (Model, Cmd SDLEngine Action) +initial assets = ( Model { flapperPos = V2 0 0 , flapperVel = V2 0 0 @@ -66,6 +72,7 @@ initial = , obstacles = [] , timeScore = 0 , timeSpeed = 1 + , assets = assets } , Cmd.execute Rand.newStdGen SetupObstacles ) @@ -377,7 +384,11 @@ view model@Model { .. } = Graphics2D $ overlay Waiting _ = waitingOverlay overlayColor overlay Dead model = deadOverlay overlayColor model overlay Playing model = playingOverlay overlayColor model - flapper = filled (rgb 0.36 0.25 0.22) $ rect flapperDims + --flapper = filled (rgb 0.36 0.25 0.22) $ rect flapperDims + flapper | playerStatus == Dead = image flapperDims (assets M.! "birdDead") + | dy < -10 = image flapperDims (assets M.! "birdFlap") + | otherwise = image flapperDims (assets M.! "bird") + where V2 _ dy = flapperVel backdrop = filled (rgb 0.13 0.13 0.13) $ rect dims lava = move (V2 0 (h / 2 - lavaHeight / 2)) $ filled (rgb 0.72 0.11 0.11) $ rect $ V2 w lavaHeight structure NoObstacle = blank @@ -395,9 +406,21 @@ main = do , SDL.windowDimensions = windowDims } - run engine defaultConfig GameLifecycle - { initialFn = initial - , updateFn = update - , subscriptionsFn = subscriptions - , viewFn = view - } + imageDir <- ( "images") <$> Paths.getDataDir + let assetList = [("bird.png", "bird"), + ("bird-flap.png", "birdFlap"), + ("bird-dead.png", "birdDead") + ] + loadAssets' [] game loaded = game loaded + loadAssets' ((file, id):files) game loaded = do + SDL.withImage engine (imageDir file) $ \image -> + loadAssets' files game (M.insert id image loaded) + loadAssets files game = loadAssets' files game M.empty + + loadAssets assetList $ \allAssets -> + run engine defaultConfig GameLifecycle + { initialFn = initial allAssets + , updateFn = update + , subscriptionsFn = subscriptions + , viewFn = view + } diff --git a/helm.cabal b/helm.cabal index 22adb27..fcc6801 100644 --- a/helm.cabal +++ b/helm.cabal @@ -9,6 +9,7 @@ license: MIT license-file: LICENSE tested-with: GHC == 8.0.2 extra-source-files: LICENSE, README.md +data-files: images/bird.png images/bird-dead.png images/bird-flap.png author: Zack Corr maintainer: Zack Corr copyright: (c) 2013-2017, Zack Corr @@ -67,10 +68,15 @@ executable helm-example-flappy main-is: Main.hs hs-source-dirs: examples/flappy + other-modules: + Paths_helm + build-depends: base >= 4 && < 5, linear >= 1 && < 2, random == 1.*, + containers >= 0.5, + filepath >= 1, helm executable helm-example-hello diff --git a/images/bird-dead.png b/images/bird-dead.png new file mode 100644 index 0000000000000000000000000000000000000000..bd275dafd0f5e85e6cc55102478e099bd99480b2 GIT binary patch literal 3418 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 CC(S=1L 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 literal 0 HcmV?d00001