Haskell Gloss 和 STM 并发集成
Haskell Gloss and STM concurrency integration
我想从多个线程(4 个线程)更新 Haskell Gloss GUI。
我正在查看一个应用程序,其中 Haskell Gloss
GUI 上的事件会触发一系列步骤,这些步骤最终会创建线程,每个线程都可以并且应该根据需要更改 GUI。我正在使用光泽 play
函数。
Gloss GUI 函数 play
类型:
play
:: Display
-> Color
-> Int
-> world
-> (world -> Picture)
-> (Event -> world -> world)
-> (Float -> world -> world)
-> IO ()
注意参数(Event -> world -> world)
,它是处理键盘事件的函数。
如果我在键盘上单击 x,然后 handleKeys::Event -> world -> world
会捕获此 event
,并使用 world
(我的模型应用程序,它是一个由 Gloss 显示的数据结构)和 returns 一个 world
有或没有变化。
根据 handleKeys::Event -> world -> world
处理的事件,可能会使用 forkIO :: IO () -> IO ThreadId
产生其他线程。这些生成的线程还应该操纵 world
和 return a world
进行显示。即每个线程运行一个world->world
类型的函数。然后我会使用 STM 原语进行并发。这些基元是:
putTMVar :: TMVar a -> a -> STM ()
takeMVar :: MVar a -> IO a
atomically :: STM a -> IO a
retry :: STM a
orElse :: STM a -> STM a -> STM a
正如您已经猜到的那样,Haskell 类型检查器让我很头疼。是否有可能 运行 Gloss 应用程序依赖 STM 并发来更新 GUI 而不会违反类型?
你应该使用来自 Graphics.Gloss.Interface.IO.Game
的 playIO
我想从多个线程(4 个线程)更新 Haskell Gloss GUI。
我正在查看一个应用程序,其中 Haskell Gloss
GUI 上的事件会触发一系列步骤,这些步骤最终会创建线程,每个线程都可以并且应该根据需要更改 GUI。我正在使用光泽 play
函数。
Gloss GUI 函数 play
类型:
play
:: Display
-> Color
-> Int
-> world
-> (world -> Picture)
-> (Event -> world -> world)
-> (Float -> world -> world)
-> IO ()
注意参数(Event -> world -> world)
,它是处理键盘事件的函数。
如果我在键盘上单击 x,然后 handleKeys::Event -> world -> world
会捕获此 event
,并使用 world
(我的模型应用程序,它是一个由 Gloss 显示的数据结构)和 returns 一个 world
有或没有变化。
根据 handleKeys::Event -> world -> world
处理的事件,可能会使用 forkIO :: IO () -> IO ThreadId
产生其他线程。这些生成的线程还应该操纵 world
和 return a world
进行显示。即每个线程运行一个world->world
类型的函数。然后我会使用 STM 原语进行并发。这些基元是:
putTMVar :: TMVar a -> a -> STM ()
takeMVar :: MVar a -> IO a
atomically :: STM a -> IO a
retry :: STM a
orElse :: STM a -> STM a -> STM a
正如您已经猜到的那样,Haskell 类型检查器让我很头疼。是否有可能 运行 Gloss 应用程序依赖 STM 并发来更新 GUI 而不会违反类型?
你应该使用来自 Graphics.Gloss.Interface.IO.Game
的 playIO