[GUI] State, Attributes and Some basic widgets
Axel Simon
A.Simon@ukc.ac.uk
Tue, 15 Apr 2003 21:54:47 +0100
On Tue, Apr 15, 2003 at 09:34:29PM +0100, Alastair Reid wrote:
> Since Haskell has a different type system from OO languages, we simply
> cannot do things the 'typical GUI toolkit' way. Instead, we have to
> find a way to encode as much as possible of the foreign type system in
> Haskell's type system.
>
> One way to do this is the one Wolfgang advocates: we provide a bunch
> of separate datatypes for each leaf node in the OO class hierarchy, we
> provide a class for each non-leaf node (or 'abstract class' if you
> prefer) in the OO class hierarchy and we use inheritance between the
> Haskell classes and instance declarations to encode the inheritance
> relations in the OO class hierarchy. This approach suffers a bit from
> being tedious to specify all the instances you need for each datatype
> but otherwise works pretty well.
Manuel uses type classes to enforce the inheritance relationship. I
construct these classes automatically for gtk2hs. I think this matches
very closely what Glynn and you propose. One question which I asked
earlier is: a) Shall the classes containt the widget's functionality as
well? (Or, alternatively: b) Shall we have a class for each attribute
(like "onActivate") and create instances for all widgets that implement
it.)
The type definition for a Button in gtk2hs looks like this (and as you
might guess, it is generated automatically):
Cheers,
Axel.
-- ********************************************************* Button
newtype Button = Button (ForeignPtr (Button))
mkButton = Button
unButton (Button o) = o
class BinClass o => ButtonClass o where
toButton :: o -> Button
fromButton :: Button -> o
instance ButtonClass Button where
toButton = id
fromButton = id
instance BinClass Button where
toBin = mkBin.castForeignPtr.unButton
fromBin = mkButton.castForeignPtr.unBin
instance ContainerClass Button where
toContainer = mkContainer.castForeignPtr.unButton
fromContainer = mkButton.castForeignPtr.unContainer
instance WidgetClass Button where
toWidget = mkWidget.castForeignPtr.unButton
fromWidget = mkButton.castForeignPtr.unWidget
instance ObjectClass Button where
toObject = mkObject.castForeignPtr.unButton
fromObject = mkButton.castForeignPtr.unObject
instance GObjectClass Button where
toGObject = mkGObject.castForeignPtr.unButton
fromGObject = mkButton.castForeignPtr.unGObject