74 lines
1.6 KiB
Haskell
74 lines
1.6 KiB
Haskell
{-
|
|
|
|
here i show how to use lenses to handle states (didnt found any example on states in internet)
|
|
|
|
-}
|
|
|
|
|
|
{-# LANGUAGE TemplateHaskell #-}
|
|
import Lens.Micro.TH (makeLenses)
|
|
import Lens.Micro ((%~), (.~), (&), _2)
|
|
import Lens.Micro.Platform (at) -- Correct import for Map operations
|
|
import Data.IORef (IORef, newIORef, modifyIORef', readIORef)
|
|
import Data.Map (Map)
|
|
import qualified Data.Map as Map
|
|
|
|
|
|
data AppState = AppState
|
|
{ _ui :: UIState
|
|
, _user :: User
|
|
} deriving (Show)
|
|
|
|
data UIState = UIState
|
|
{ _theme :: String
|
|
, _windowSize :: (Int, Int)
|
|
, _keyBindings :: Map String String
|
|
} deriving (Show)
|
|
|
|
data User = User
|
|
{ _name :: String
|
|
, _prefs :: UserPrefs
|
|
} deriving (Show)
|
|
|
|
data UserPrefs = UserPrefs
|
|
{ _fontSize :: Int
|
|
, _darkMode :: Bool
|
|
} deriving (Show)
|
|
|
|
|
|
makeLenses ''AppState
|
|
makeLenses ''UIState
|
|
makeLenses ''User
|
|
makeLenses ''UserPrefs
|
|
|
|
main :: IO ()
|
|
main = do
|
|
let initialState = AppState
|
|
{ _ui = UIState
|
|
{ _theme = "light"
|
|
, _windowSize = (800, 600)
|
|
, _keyBindings = Map.fromList [("Ctrl+S", "save")]
|
|
}
|
|
, _user = User
|
|
{ _name = "Alice"
|
|
, _prefs = UserPrefs
|
|
{ _fontSize = 12
|
|
, _darkMode = False
|
|
}
|
|
}
|
|
}
|
|
|
|
stateRef <- newIORef initialState
|
|
|
|
-- Corrected lens chain with &
|
|
{-
|
|
& is just backwards function application;
|
|
x f , in which f will be applied to the value x
|
|
-}
|
|
modifyIORef' stateRef $ \s ->
|
|
s & ui . keyBindings . at "Ctrl+X" .~ Just "cut"
|
|
& user . prefs . darkMode .~ True
|
|
& ui . windowSize . _2 %~ (+100)
|
|
|
|
finalState <- readIORef stateRef
|
|
print finalState
|