Computer game in Haskell - a set of tools for the widget

I am writing a small RTS game in Haskell, and it's time to create some graphical interface for it (buttons, menus, etc.). However, I do not have any experience creating GUI tools, so I would be grateful for ideas on how to choose the right data types, event handling procedures, etc.

Desired functionality: menu screens (main, load / save, settings, network game), text inputs, game interface (main screen (C & C-like) with buttons, choices and flags.

My current approach is to present the entire graphical interface as a state machine that has a number of states and transitions between them that fire when an event arrives:

-- Local client state. Actual game state is stored on the server -- and is updated/synced separately. data ClientState = […] -- Keyboard state, mouse state, quadtree of clickables, list of -- widgets. data UIState = […] uiCycle :: UIState -> ClientState -> IO () uiCycle uiState clientState = do event <- waitEvent let widget = findWidget uiState event let (uiState', clientStateAction, ioAction) = uiTransition widget event uiState clientState -- Update game state (execute game logic). let clientState' = clientStateAction clientState -- Redraw appropriate surfaces etc. ioAction uiCycle uiState' clientState' 

A widget is something like

 data Widget = Widget { wtType :: WidgetType , wtParent :: Maybe Widget --, wtRelated :: [Widget] -- Feels hacky. , wtBox :: Rect , wtPosition :: WidgetPosition , wtAnchors :: [WidgetAnchor] , wtEventHandlers :: Map Event EventHandler , wtDisabled :: Bool } 

Where

 type EventHandler = (Event -> (UIState, ClientState) -> (UIState, ClientState, IO ())) 

When an event arrives and the corresponding widget is found, my program looks for the event handler in wtEventHandlers for this widget, and performs an action if such an event handler is found.

When a widget is created, its rectangle is added to the QuadTree , which is requested by findWidget . The tree is updated when widgets are created or deleted.

However, it is very difficult to program this way because the user interface (even for a simple interface with several buttons and without menus).

I thought about introducing each widget as a finite state machine and designing these machines so that the number of states and transitions decreases. It might be nice to wrap it in a monad (for example, this is done in XMonad).

Things I looked at:

My questions:

  • Does widgets describe state machines that “react” to certain events and “ignore” all the others that make sense to the widget tool designer? Is there a better (simpler) way?
  • Describes a description of the interface in Monad good idea?

E. g.

 mkGameScreenButtons = runGuiDef $ do panicExitButton /// MouseDown ==> liftM exitGameNow panicExitButton /// MouseIn ==> do hideGameScreen muteSounds muteMusic panicExitButton /// MouseOut ==> do unhideGameScreen unmuteSounds unmuteMusic gameSpeedSlider /// MouseUp ==> changeSpeed (wtValue gameSpeedSlider) [...] where panicExitButton = mkButton (5, 5) [AnchorTop, AnchorRight] "BOSS BUTTON" [...] 
  • Is there any relevant literature that I could read before moving on? A focus on a functional approach would be nice.
  • Is there a way to avoid writing a widget toolkit? I want my game to work in full screen mode, so Gtk2hs will not work.
+8
user-interface haskell sdl
source share

No one has answered this question yet.

See related questions:

757
Getting started with Haskell
546
Speed ​​comparison with Project Euler: C vs Python vs Erlang vs Haskell
534
Large-scale design in Haskell?
447
What is Haskell used for in the real world?
326
A Good Haskell Source for Reading and Learning
242
What's wrong with a Haskell template?
197
Haskell: lists, arrays, vectors, sequences
4
What are the differences between different GUI tools and language links?
3
Quick update of many widgets in Qt GUI
-one
Board Game and GUI Driven Event: How to Connect?

All Articles