Refactor concurrent side effects
This commit is contained in:
+1
-1
@@ -89,7 +89,7 @@ firstWorldLoad theConfig = do
|
|||||||
, _uvScreenLayers = [splashMenu]
|
, _uvScreenLayers = [splashMenu]
|
||||||
, _uvIOEffects = return
|
, _uvIOEffects = return
|
||||||
, _uvTestString = testStringInit
|
, _uvTestString = testStringInit
|
||||||
, _uvConcEffects = NoConcEffect
|
, _uvSideEffects = mempty
|
||||||
, _uvCanContinue = cancontinue
|
, _uvCanContinue = cancontinue
|
||||||
, _uvMSeed = mseed
|
, _uvMSeed = mseed
|
||||||
}
|
}
|
||||||
|
|||||||
+27
-14
@@ -3,25 +3,38 @@ module Dodge.Concurrent where
|
|||||||
--import qualified Data.Set as S
|
--import qualified Data.Set as S
|
||||||
import Control.Lens
|
import Control.Lens
|
||||||
import Dodge.Data.Universe
|
import Dodge.Data.Universe
|
||||||
|
import Data.Sequence (Seq (..))
|
||||||
|
|
||||||
--import Control.Concurrent
|
--import Control.Concurrent
|
||||||
--import SDL.Input.Keyboard.Codes
|
--import SDL.Input.Keyboard.Codes
|
||||||
|
|
||||||
conEffects :: Universe -> ConcurrentEffect Universe
|
conEffects :: Universe -> ConcurrentEffect Universe
|
||||||
conEffects u = case u ^. uvConcEffects of
|
conEffects u = case u ^? uvSideEffects . _head of
|
||||||
NewConcEffect{_ceFunction = eff} -> eff
|
Just NewSideEffect{_ceSideEffect = eff} -> ConcurrentEffect (u & uvSideEffects . _head %~ g)
|
||||||
|
(dopop eff)
|
||||||
_ -> NoConcurrentEffect
|
_ -> NoConcurrentEffect
|
||||||
|
|
||||||
tryConcEffect :: Bool -> String -> IO (Universe -> Maybe Universe) -> Universe -> Universe
|
|
||||||
tryConcEffect bl str eff u = case u ^. uvConcEffects of
|
|
||||||
NoConcEffect -> u & uvConcEffects .~ NewConcEffect (ConcurrentEffect setstr (clearConcEff eff)) str bl
|
|
||||||
_ -> u
|
|
||||||
where
|
where
|
||||||
setstr
|
g seff = RunningSideEffect (_ceString seff)
|
||||||
| bl = uvConcEffects .~ BlockingConcEffect str
|
dopop :: IO (Universe -> Maybe Universe) -> IO (Universe -> Maybe Universe)
|
||||||
| otherwise = uvConcEffects .~ BackgroundConcEffect str
|
dopop mf = do
|
||||||
|
f <- mf
|
||||||
|
return $ f . (uvSideEffects %~ taker)
|
||||||
|
taker (_ :<| xs) = xs
|
||||||
|
taker _ = mempty
|
||||||
|
|
||||||
clearConcEff :: IO (Universe -> Maybe Universe) -> IO (Universe -> Maybe Universe)
|
addSideEffect :: IO (Universe -> Maybe Universe) -> String -> Universe -> Universe
|
||||||
clearConcEff eff = do
|
addSideEffect f s = uvSideEffects %~ (|> NewSideEffect f s)
|
||||||
f <- eff
|
|
||||||
return (f . (uvConcEffects .~ NoConcEffect))
|
--tryConcEffect :: Bool -> String -> IO (Universe -> Maybe Universe) -> Universe -> Universe
|
||||||
|
--tryConcEffect bl str eff u = case u ^. uvConcEffects of
|
||||||
|
-- NoConcEffect -> u & uvConcEffects .~ NewConcEffect (ConcurrentEffect setstr (clearConcEff eff)) str bl
|
||||||
|
-- _ -> u
|
||||||
|
-- where
|
||||||
|
-- setstr
|
||||||
|
-- | bl = uvConcEffects .~ BlockingConcEffect str
|
||||||
|
-- | otherwise = uvConcEffects .~ BackgroundConcEffect str
|
||||||
|
|
||||||
|
--clearConcEff :: IO (Universe -> Maybe Universe) -> IO (Universe -> Maybe Universe)
|
||||||
|
--clearConcEff eff = do
|
||||||
|
-- f <- eff
|
||||||
|
-- return (f . (uvConcEffects .~ NoConcEffect))
|
||||||
|
|||||||
+17
-13
@@ -1,5 +1,5 @@
|
|||||||
{-# LANGUAGE DeriveGeneric #-}
|
|
||||||
{-# LANGUAGE DeriveAnyClass #-}
|
{-# LANGUAGE DeriveAnyClass #-}
|
||||||
|
{-# LANGUAGE DeriveGeneric #-}
|
||||||
{-# LANGUAGE StrictData #-}
|
{-# LANGUAGE StrictData #-}
|
||||||
{-# LANGUAGE TemplateHaskell #-}
|
{-# LANGUAGE TemplateHaskell #-}
|
||||||
|
|
||||||
@@ -9,16 +9,17 @@ module Dodge.Data.Universe (
|
|||||||
module Dodge.Data.World,
|
module Dodge.Data.World,
|
||||||
module Data.Preload,
|
module Data.Preload,
|
||||||
module Picture.Data,
|
module Picture.Data,
|
||||||
module Loop.Data
|
module Loop.Data,
|
||||||
) where
|
) where
|
||||||
|
|
||||||
import Loop.Data
|
|
||||||
import Control.Lens
|
import Control.Lens
|
||||||
--import qualified Data.Map.Strict as M
|
--import qualified Data.Map.Strict as M
|
||||||
import Data.Preload
|
import Data.Preload
|
||||||
|
import Data.Sequence (Seq (..))
|
||||||
import qualified Data.Text as T
|
import qualified Data.Text as T
|
||||||
import Dodge.Data.Config
|
import Dodge.Data.Config
|
||||||
import Dodge.Data.World
|
import Dodge.Data.World
|
||||||
|
import Loop.Data
|
||||||
import Picture.Data
|
import Picture.Data
|
||||||
import SDL (Scancode)
|
import SDL (Scancode)
|
||||||
|
|
||||||
@@ -27,18 +28,19 @@ data Universe = Universe
|
|||||||
, _preloadData :: PreloadData
|
, _preloadData :: PreloadData
|
||||||
, _uvScreenLayers :: [ScreenLayer]
|
, _uvScreenLayers :: [ScreenLayer]
|
||||||
, _uvIOEffects :: Universe -> IO Universe
|
, _uvIOEffects :: Universe -> IO Universe
|
||||||
, _uvConcEffects :: ConcEffect
|
, _uvSideEffects :: Seq SideEffect
|
||||||
, _uvConfig :: Configuration
|
, _uvConfig :: Configuration
|
||||||
, _uvTestString :: Universe -> [String]
|
, _uvTestString :: Universe -> [String]
|
||||||
, _uvCanContinue :: Bool
|
, _uvCanContinue :: Bool
|
||||||
, _uvMSeed :: Maybe Int
|
, _uvMSeed :: Maybe Int
|
||||||
}
|
}
|
||||||
|
|
||||||
data ConcEffect = NoConcEffect
|
data SideEffect
|
||||||
| NewConcEffect {_ceFunction :: ConcurrentEffect Universe
|
= NewSideEffect
|
||||||
, _ceString :: String, _ceIsBlocking :: Bool}
|
{ _ceSideEffect :: IO (Universe -> Maybe Universe)
|
||||||
| BlockingConcEffect {_ceString :: String}
|
, _ceString :: String
|
||||||
| BackgroundConcEffect {_ceString :: String}
|
}
|
||||||
|
| RunningSideEffect {_ceString :: String}
|
||||||
|
|
||||||
data OptionScreenFlag = NormalOptions | GameOverOptions | SplashOptions
|
data OptionScreenFlag = NormalOptions | GameOverOptions | SplashOptions
|
||||||
deriving (Eq, Ord, Show, Read) --Generic, Flat)
|
deriving (Eq, Ord, Show, Read) --Generic, Flat)
|
||||||
@@ -59,6 +61,7 @@ data ScreenLayer
|
|||||||
{ _scInput :: T.Text
|
{ _scInput :: T.Text
|
||||||
, _scFooter :: String
|
, _scFooter :: String
|
||||||
}
|
}
|
||||||
|
|
||||||
-- | WaitScreen
|
-- | WaitScreen
|
||||||
-- { _scWaitMessage :: Universe -> String
|
-- { _scWaitMessage :: Universe -> String
|
||||||
-- , _scWaitTime :: Int
|
-- , _scWaitTime :: Int
|
||||||
@@ -67,9 +70,10 @@ data ScreenLayer
|
|||||||
-- { _scDisplay :: Universe -> Picture
|
-- { _scDisplay :: Universe -> Picture
|
||||||
-- }
|
-- }
|
||||||
|
|
||||||
data MenuOptionDisplay = MODString {_modString :: String}
|
data MenuOptionDisplay
|
||||||
| MODBlockedString {_modString :: String}
|
= MODString {_modString :: String}
|
||||||
| MODStringOption {_modString :: String,_modOption :: String}
|
| MODBlockedString {_modString :: String}
|
||||||
|
| MODStringOption {_modString :: String, _modOption :: String}
|
||||||
|
|
||||||
data MenuOption
|
data MenuOption
|
||||||
= Toggle
|
= Toggle
|
||||||
@@ -93,5 +97,5 @@ data IntID a = IntID Int a
|
|||||||
|
|
||||||
makeLenses ''Universe
|
makeLenses ''Universe
|
||||||
makeLenses ''ScreenLayer
|
makeLenses ''ScreenLayer
|
||||||
makeLenses ''ConcEffect
|
makeLenses ''SideEffect
|
||||||
makeLenses ''MenuOptionDisplay
|
makeLenses ''MenuOptionDisplay
|
||||||
|
|||||||
+1
-1
@@ -71,7 +71,7 @@ saveQuit :: Universe -> IO (Maybe Universe)
|
|||||||
saveQuit u =
|
saveQuit u =
|
||||||
return $
|
return $
|
||||||
Just $
|
Just $
|
||||||
u & tryConcEffect True "SAVING" (saveQuitConc u)
|
u & addSideEffect (saveQuitConc u) "SAVING"
|
||||||
|
|
||||||
saveQuitConc :: Universe -> IO (Universe -> Maybe Universe)
|
saveQuitConc :: Universe -> IO (Universe -> Maybe Universe)
|
||||||
saveQuitConc u = do
|
saveQuitConc u = do
|
||||||
|
|||||||
@@ -26,14 +26,9 @@ fixedCoordPictures u =
|
|||||||
cfig = _uvConfig u
|
cfig = _uvConfig u
|
||||||
|
|
||||||
drawConcurrentMessage :: Universe -> Picture
|
drawConcurrentMessage :: Universe -> Picture
|
||||||
drawConcurrentMessage u = case u ^. uvConcEffects of
|
drawConcurrentMessage u = case u ^? uvSideEffects . _head of
|
||||||
BlockingConcEffect str -> fillWidthText cfig str
|
--Just (BlockingConcEffect str) -> fillWidthText cfig str
|
||||||
--listPicturesAt
|
Just (RunningSideEffect str) ->
|
||||||
--(halfWidth cfig)
|
|
||||||
--(halfHeight cfig)
|
|
||||||
--cfig
|
|
||||||
--[centerText str]
|
|
||||||
BackgroundConcEffect str ->
|
|
||||||
listPicturesAt
|
listPicturesAt
|
||||||
(halfWidth cfig)
|
(halfWidth cfig)
|
||||||
(_windowY cfig - 50)
|
(_windowY cfig - 50)
|
||||||
|
|||||||
+4
-2
@@ -18,6 +18,7 @@ import qualified Data.ByteString.Lazy as BS
|
|||||||
import Dodge.Data.Universe
|
import Dodge.Data.Universe
|
||||||
--import qualified Data.Set as S
|
--import qualified Data.Set as S
|
||||||
import System.Directory
|
import System.Directory
|
||||||
|
--import Data.Sequence ((|>))
|
||||||
|
|
||||||
|
|
||||||
writeSaveSlot :: SaveSlot -> Universe -> IO (Universe -> Maybe Universe)
|
writeSaveSlot :: SaveSlot -> Universe -> IO (Universe -> Maybe Universe)
|
||||||
@@ -52,13 +53,14 @@ saveSlotPath QuicksaveSlot = "saveSlot/QuickSave"
|
|||||||
saveSlotPath (LevelStartSlot i) = "saveSlot/LevelStart" ++ show i
|
saveSlotPath (LevelStartSlot i) = "saveSlot/LevelStart" ++ show i
|
||||||
|
|
||||||
saveWorldInSlot :: SaveSlot -> Universe -> Universe
|
saveWorldInSlot :: SaveSlot -> Universe -> Universe
|
||||||
saveWorldInSlot slot u = tryConcEffect False "SAVING" (writeSaveSlot slot u) u
|
--saveWorldInSlot slot u = u & uvSideEffects %~ (|> NewSideEffect (writeSaveSlot slot u) "SAVING")
|
||||||
|
saveWorldInSlot slot u = u & addSideEffect (writeSaveSlot slot u) "SAVING"
|
||||||
|
|
||||||
reloadLevelStart :: Universe -> Universe
|
reloadLevelStart :: Universe -> Universe
|
||||||
reloadLevelStart = loadSaveSlot (LevelStartSlot 0)
|
reloadLevelStart = loadSaveSlot (LevelStartSlot 0)
|
||||||
|
|
||||||
loadSaveSlot :: SaveSlot -> Universe -> Universe
|
loadSaveSlot :: SaveSlot -> Universe -> Universe
|
||||||
loadSaveSlot slot = tryConcEffect True "LOADING" (readSaveSlot slot)
|
loadSaveSlot slot = addSideEffect (readSaveSlot slot) "LOADING"
|
||||||
|
|
||||||
doQuicksave :: Universe -> Universe
|
doQuicksave :: Universe -> Universe
|
||||||
doQuicksave = saveWorldInSlot QuicksaveSlot
|
doQuicksave = saveWorldInSlot QuicksaveSlot
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ startNewGameInSlot slot u = startSeedGame slot i u
|
|||||||
i = fst $ randomR (0, maxBound) (_randGen (_uvWorld u))
|
i = fst $ randomR (0, maxBound) (_randGen (_uvWorld u))
|
||||||
|
|
||||||
startSeedGame :: Int -> Int -> Universe -> Universe
|
startSeedGame :: Int -> Int -> Universe -> Universe
|
||||||
startSeedGame _ i = tryConcEffect True "GENERATING" (startSeedGameConc i)
|
startSeedGame _ i = addSideEffect (startSeedGameConc i) "GENERATING"
|
||||||
|
|
||||||
startSeedGameConc :: Int -> IO (Universe -> Maybe Universe)
|
startSeedGameConc :: Int -> IO (Universe -> Maybe Universe)
|
||||||
startSeedGameConc seed = do
|
startSeedGameConc seed = do
|
||||||
|
|||||||
@@ -93,7 +93,6 @@ updateUniverseLast = over uvWorld (input . mouseButtons . each .~ True) -- to de
|
|||||||
{- For most menus the only way to change the world is using event handling. -}
|
{- For most menus the only way to change the world is using event handling. -}
|
||||||
updateUniverseMid :: Universe -> Universe
|
updateUniverseMid :: Universe -> Universe
|
||||||
updateUniverseMid u
|
updateUniverseMid u
|
||||||
| concurrentblocking = u
|
|
||||||
| otherwise = case _uvScreenLayers u of
|
| otherwise = case _uvScreenLayers u of
|
||||||
(OptionScreen{_scOptionFlag = GameOverOptions} : _) ->
|
(OptionScreen{_scOptionFlag = GameOverOptions} : _) ->
|
||||||
u & uvWorld
|
u & uvWorld
|
||||||
@@ -106,10 +105,6 @@ updateUniverseMid u
|
|||||||
)
|
)
|
||||||
(_ : _) -> u
|
(_ : _) -> u
|
||||||
[] -> functionalUpdate'' u
|
[] -> functionalUpdate'' u
|
||||||
where
|
|
||||||
concurrentblocking = case u ^. uvConcEffects of
|
|
||||||
BlockingConcEffect{} -> True
|
|
||||||
_ -> False
|
|
||||||
|
|
||||||
functionalUpdate'' :: Universe -> Universe
|
functionalUpdate'' :: Universe -> Universe
|
||||||
functionalUpdate'' = advanceScrollAmount . functionalUpdate'
|
functionalUpdate'' = advanceScrollAmount . functionalUpdate'
|
||||||
|
|||||||
+1
-1
@@ -161,7 +161,7 @@ doConLoop themvar spf window coneffs worldSideEffects eventFn !startWorld = go s
|
|||||||
return ()
|
return ()
|
||||||
let startWorld'' = case mconeff of
|
let startWorld'' = case mconeff of
|
||||||
NoConcurrentEffect -> sw
|
NoConcurrentEffect -> sw
|
||||||
ConcurrentEffect immediatef _ -> immediatef sw
|
ConcurrentEffect immediatef _ -> immediatef
|
||||||
mconupdate <- tryTakeMVar themvar
|
mconupdate <- tryTakeMVar themvar
|
||||||
let mstartWorld' = case mconupdate of
|
let mstartWorld' = case mconupdate of
|
||||||
Just conupdate -> conupdate startWorld''
|
Just conupdate -> conupdate startWorld''
|
||||||
|
|||||||
+1
-1
@@ -6,6 +6,6 @@ module Loop.Data where
|
|||||||
data ConcurrentEffect world
|
data ConcurrentEffect world
|
||||||
= NoConcurrentEffect
|
= NoConcurrentEffect
|
||||||
| ConcurrentEffect
|
| ConcurrentEffect
|
||||||
{ _immediateEffect :: world -> world
|
{ _immediateUpdate :: world
|
||||||
, _sideEffect :: IO (world -> Maybe world)
|
, _sideEffect :: IO (world -> Maybe world)
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user