2016-10-30 35 views
0

我在使用包含運動的purescript信號構建Purescript遊戲。用戶按下左/右鍵移動左/右。最小的代碼在下面。Purescript信號從開始的時候開始重複

看起來purescript正在評估信號的「從時間的開始」每一步,這讓我感到莫名其妙。例如,如果我繼續在開始處按右鍵,輸出

m: 0 
m: 0 
m: 1 
m: 0 
m: 1 
m: 2 
m: 0 
m: 1 
m: 2 
m: 3 

而不是

m: 0 
m: 1 
m: 2 
m: 3 

爲我所期望的。我該如何解決?

module SimpleMove where 

import Prelude 
import Control.Monad.Eff (Eff) 
import Control.Monad.Eff.Console (CONSOLE, log) 
import Data.Functor 
import Data.Int 
import Signal (Signal, runSignal, foldp, sampleOn, map2) 
import Signal.DOM (keyPressed) 
import Signal.Time (Time, second, every) 
import Partial.Unsafe (unsafePartial) 

--MODEL 
type Model = Int 

step :: forall e. Partial => Int -> Eff (console :: CONSOLE | e) Model -> Eff (console :: CONSOLE| e) Model 
step dir m' = 
    do 
    m <- m' 
    log ("m: " <> (show m)) 
    pure (m + dir) 

--SIGNALS 
inputDir :: Eff _ (Signal Int) 
inputDir = 
    let 
     f = \l r -> if l 
        then -1 
        else if r 
         then 1 
         else 0 
    in 
     map2 f <$> (keyPressed 37) <*> (keyPressed 39) 

input :: Eff _ (Signal Int) 
input = sampleOn (every second) <$> inputDir 

--MAIN 
main :: Eff _ Unit 
main = 
    unsafePartial do 
     dirSignal <- input 
     let game = foldp step (pure 0) dirSignal 
     runSignal (map void game) 

回答

2

如果您改變mainstep這樣你會得到預期的結果:

main :: Eff _ Unit 
main = do 
     dirSignal <- input 
     let game = foldp step 0 dirSignal 
     runSignal (map render game) 

step :: forall e. Int -> Model -> Model 
step dir m = m + dir 

render :: forall e. Model -> Eff (console :: CONSOLE| e) Unit 
render m = logShow m