Updater-0.2: Monadic FRP library based on stm

Safe HaskellNone
LanguageHaskell98

Updater

Contents

Synopsis

Signals

data Signal a Source

Signal is the portable Signal they can be exchanged between any parts of your program. Internally, they are just a variable and a list of change hooks.

newSignal :: a -> Updater (Signal a) Source

Creates a new signal. You can use this signal in any context you want and share it freely between any number of different Updater monads.

writeSignal :: Signal a -> a -> Updater () Source

Writes the value to the variable inside the signal and schedules the listeners to run. The listeners will run in the same stm action and with the value you gave. However, they do not run immediately. So you are guaranteed that writeSignal will not have any immediate sideffects other then writing the one single variable.

readSignal :: Signal a -> Updater a Source

Gets the current value.

Updater Monad

data Updater a Source

This monad works very similar to a continuation monad on top of stm. You can do any basic stm computation you want simply using liftSTM. However, if you use getEvent everything after that call will be executed everytime the Signal given to getEvent is changed.

You can also use the Alternative instance to make a union of events.

You can also use the Applicative instance to run two things 'parallel'. Parallel meaning that events on one side will not cause the other side to be reevaluated completely.

runUpdater :: Updater a -> IO a Source

This will evaluate the Updater Monad. It will block until the first run reaches the end. After that, it will return the result and free everything. To prevent signals from reaching the end use stop or getEvent with some exit signal.

getEvent :: Signal a -> Updater a Source

Runs everything below it everytime its input signal is updated.

onCommit :: IO () -> Updater () Source

IO actions given here will be executed once a signal update has been completed. They keep the order in which they are inserted.

onCleanup :: Updater () -> Updater () Source

doesn't really work yet

Helpers

stop :: Updater a Source

Just a synonym for empty from Alternative. It basically prevents signals from ever progressing beyond this point. You can use this to make a filter for instance

when (condition) stop

modifySignal :: Signal a -> (a -> a) -> Updater () Source

simple combination of readSignal and writeSignal

getBehavior :: Signal a -> Updater a Source

Similar to getEvent except that it also fires an event immediately, with the value of the current state.

getBehavior signal = liftSTM (readSignal signal) <|> getEvent signal

local :: Updater a -> Updater () Source

Returns immediately after registering the given computation. However, events from inside will not spread outside, except for the initial one.

It is implemented like this

local computation = return () <|> (computation >> stop)

putLine :: String -> Updater () Source

Just for some quick debugging

putLine = onCommit . putStrLn

runGlobalUpdater :: Updater a -> IO () Source

this is just a convenience for use in ghci and in the test cases. It will just run the updater it is given in it's own thread.