请考虑以下代码:
module Main where
import Control.Event.Handler
import Reactive.Banana
import Reactive.Banana.Frameworks
main :: IO ()
main = do
(addHandler, fire) <- newAddHandler
compile (network addHandler) >>= actuate
fire "fire one"
fire "fire two"
network :: AddHandler String -> MomentIO ()
network addHandler = do
fireEvent <- fromAddHandler addHandler
behavior <- stepper "initial stepper value" fireEvent
behaviorValue <- valueB behavior
reactimate $ putStrLn . (\v -> "fire input: " ++ show v) <$> fireEvent
reactimate $ print behaviorValue <$ fireEvent
该程序的输出是:
fire input: "fire one"
"initial stepper value"
fire input: "fire two"
"initial stepper value"
我正确使用valueB
吗?如果没有,我做错了什么? valueB
的目的是什么?我何时应该使用它?
答案 0 :(得分:2)
有助于记住Moment
(和MomentIO
)monad表示在特定时刻发生的计算。组合器valueB
只返回当时行为的值。在你的情况下,这是在一开始。
如果您想在不同时间对行为的值进行抽样,可以使用与<@>
和<@
非常相似的<$>
和<$
运算符。例如,用
reactimate $ print <$> behavior <@ fireEvent
将在事件触发时的每个时刻打印行为的值。
更高级的用途是将valueB
与execute
一起使用。
答案 1 :(得分:1)
根据文档,valueB
获取给定行为的当前值。它适用于某些MonadMoment
。在这种情况下,这个“时刻”是网络创建的时间。因此,您始终可以获得相同的值。您只需要在开始时询问一次该值。
你不能直接对行为的变化做出反应,因为他们并没有真正通知他们的变化(他们是连续的信号)。
如果您想查看valueB
的实际操作。我认为execute
函数就是您所需要的。
execute (valueB <$> stepper "initial stepper value" fireEvent)
这当然是一个非常人为的例子,但它应该做你想要的。
另外,我没有专门针对ReactiveBanana的经验,但大多数FRP框架的工作方式都相似。