If the GUI is based on the IO monad, then it doesn't seem like there is a lot of advantage to doing it in Haskell. It seems like a better idea to use a more natural language for IO and make RPC/interproc calls to a haskell server to get stuff done.
In other words, if you use the IO monad, you're going to have the same programming experience (only more verbose) as a C/C++/Java programmer? I don't think that's true. My graphics library (http://haskell.org/graphics/) uses the IO monad for manipulating windows and the Draw monad for doing graphics but both feel quite different from similar code I've written in C (and, I believe, from C++ or Java code). In the case of manipulating windows, the different feel comes from using concurrency to "hide the event loop" and from using layers of abstraction to hide the full power (and horror) of the X and Win32 programming models. In the case of the Draw monad (which is identical to the IO monad except that it carries a "device context" around as an implicit parameter), the different feel comes from aggressive use of continuations (actually, they're not quite continuations but I don't have a better word for them). For example, you might normally write code like this: do old_color <- selectColor blue old_font <- selectFont helvetica write_text "Hello World" selectFont old_font selectColor old_color (Reselecting the old color and font at the end is recommended Win32 programming style.) In the HGL, you instead write: setPicture window (withColor blue (withFont helvetica (text "Hello World"))) or, equivalently but allegedly easier to read, setPicture window $ withColor blue $ withFont helvetica $ text "Hello World" where withColor and withFont are defined like this: withColor :: Color -> Draw a -> Draw a withColor c m = do{ old <- selectColor c; a <- m; selectColor old; return a } withFont :: Font -> Draw a -> Draw a withFont f m = do{ old <- selectFont f; a <- m; selectFont old; return a } and setPicture exploits the fact that an object of type "Draw a" is a first class object which can be stored in the window state and executed when appropriate (e.g., when the window is uniconified). What I'm saying is that Haskell's standard abstraction facilities mean that even in the IO monad your programming experience can significantly better than that of a C programmer. (Of course your experience can also be worse if you don't or can't bring Haskell's strengths to bear on your problem.) -- Alastair Reid reid@cs.utah.edu http://www.cs.utah.edu/~reid/