main :: TkEnv -> Cmd ()can be executed by typing main to the prompt in the interactive system ohugs or by running rohugs with the file name as command line argument.
struct Tk = window :: [WindowOpt] -> Request Window bitmap :: [BitmapOpt] -> Request ConfBitmap photo :: [PhotoOpt] -> Request Photo delay :: Int -> (String -> Cmd ()) -> Request String periodic :: Int -> Cmd () -> Request Runnable bell :: Action struct TkEnv < Tk, StdEnv struct Runnable = start :: Action stop :: ActionThe TkEnv structure has six methods:
Many of the structures in Tk have methods with a signature of the form
aWidget :: [AWidgetOpt] -> Request AWidgetA call of this method creates an instance of AWidget; as argument to the call the instance can be configured with a list of widget-specific options. The widget creating methods appear in a hierarchy:
struct Widget = ident :: String destroy :: Action exists :: Request Bool focus, raise, lower :: Action bind :: [Event] -> Action struct Configurable a = set :: [a] -> Action struct ConfWidget a < Widget, Configurable a struct Container = pack :: Packable -> Action unpackAll :: Action struct WWidget a < ConfWidget a, PackableA Widget has a unique identity, can be destroyed (and consequently one can check whether it still exists), can take keyboard focus, can be raised and lowered in the stacking order on screen. Finally and most importantly, one can bind callback procedures to a widget as response to user actions, represented as Events.
ConfWidgets are also Configurable, ie one can set their options not only at creation time but at any time. All Widgets in Tk are actually ConfWidgets; the reason for the design is that there are also other Configurable objects, such as ConfBitmap and Photos.
Some Widgets, notably Windows and Frames, are also Containers, ie they can be packed with a Packable object. All widgets created by methods of a Window are Packable; to capture this we introduce the type WWidget. In addition there are layout functions to combine packables horizontally and vertically, allowing several widgets to be flexibly packed in a container.
struct Window < BasicWindow WindowOpt, ManagedWindow data WindowOpt > Background, BorderWidth, Cursor, Relief, Title struct BasicWindow a < ConfWidget a, Container = button :: [ButtonOpt] -> Request Button canvas :: [CanvasOpt] -> Request Canvas checkButton :: [CheckButtonOpt] -> Request CheckButton entry :: [EntryOpt] -> Request Entry frame :: [FrameOpt] -> Request Frame label :: [LabelOpt] -> Request Label listBox :: [ListBoxOpt] -> Request ListBox menuButton :: [MenuButtonOpt] -> Request MenuButton radioButton :: [RadioButtonOpt] -> Request RadioButton scrollBar :: [ScrollBarOpt] -> Request ScrollBar slider :: [SliderOpt] -> Request Slider textEditor :: [TextEditorOpt] -> Request TextEditor struct ManagedWindow = getGeometry :: Request (Pos,Pos) -- size,position setSize :: Pos -> Action setPosition :: Pos -> Action iconify :: Action deiconify :: Action type Pos = (Int,Int)The ManagedWindow methods are hopefully self-explanatory. All the BasicWindow methods produce WWidgets.
struct Image = imageName :: String struct Bitmap < Image struct ConfBitmap < Bitmap, Configurable BitmapOpt struct PredefBitmap < Bitmap struct Photo < Image, Configurable PhotoOpt = blank :: Action putPixel :: Pos -> Color -> Action getPixel :: Pos -> Request Color copyFrom :: Photo -> Action -- to be refined saveAs :: FilePath -> Action data PhotoOpt > Width, Height, File data BitmapOpt > Background, Foreground, File, BitmapData stop, hourglass, info, questhead, question, warning :: PredefBitmapAn Image is either a Bitmap or a Photo. There are a small number of predefined PreDefBitmaps, enumerated above; these are typically used in dialogs. General bitmaps can be created from either a file containing a bitmap in standard X bitmap format (using the File option) or a string, also in X bitmap format (using the BitmapData option). The general bitmaps can also be configured with a foreground and background color.
Photos represent full-color images, which are created from GIF or PPM files, using the File option. There are also methods to get and set the color of individual pixels. It is, however, infeasible to create or process images significantly using these methods. Presently, image processing using this module is thus not possible; the use of images is limited to pure presentation of externally generated images.
struct Button < WWidget ButtonOpt, Invokable = flash :: Action struct Canvas < ScrollWidget CanvasOpt, Scannable Pos = oval :: Pos -> Pos -> [OvalOpt] -> Request Oval arc :: Pos -> Pos -> [ArcOpt] -> Request Arc rectangle :: Pos -> Pos -> [RectangleOpt] -> Request Rectangle line :: [Pos] -> [LineOpt] -> Request Line polygon :: [Pos] -> [PolygonOpt] -> Request Polygon text :: Pos -> [CTextOpt] -> Request CText image :: Pos -> [CImageOpt] -> Request CImage cwindow :: Pos -> [CWindowOpt] -> Request CWindow clear :: Action save :: FilePath -> Action struct CheckButton < Button = toggle :: Action checked :: Request Bool struct Entry < ScrollWidget EntryOpt, Cell String, Scannable Int = cursorPos :: Request Int struct Frame < WWidget FrameOpt, Container struct Label < WWidget LabelOpt struct ListBox < ScrollWidget ListBoxOpt, LineEditable, Cell [Int], Scannable Pos = view :: Int -> Action struct MenuButton < WWidget MenuButtonOpt = menu :: [MenuOpt] -> Request Menu struct RadioButton < Button = select :: Action deselect :: Action struct ScrollBar < WWidget ScrollBarOpt = attach :: ScrollWidget Background -> Dir -> Action struct Slider < WWidget SliderOpt, Cell Int struct TextEditor < ScrollWidget TextEditorOpt, LineEditable, Scannable Pos data BasicOpt > Background, BorderWidth, Cursor, Relief data BasicWOpt > BasicOpt, Width data DimOpt > Height, Width data StdOpt > BasicWOpt, DimOpt data FontOpt > Font, Foreground, Anchor, Justify data PadOpt > Padx, Pady data ButtonOpt > MenuButtonOpt, Command data CanvasOpt > StdOpt, ScrollRegion data CheckButtonOpt > ButtonOpt, Indicatoron, SelectColor data EntryOpt > BasicWOpt, Justify, Font, Foreground, Enabled type FrameOpt = StdOpt data LabelOpt > StdOpt, FontOpt, PadOpt, Img, Btmp, Underline, Text data ListBoxOpt > StdOpt, Font, Foreground, SelectMode data MenuButtonOpt > LabelOpt, Enabled type RadioButtonOpt = CheckButtonOpt type ScrollBarOpt = StdOpt data SliderOpt > BasicWOpt, From, To, Orientation, Length, Font, Foreground, CmdInt, Enabled data TextEditorOpt > StdOpt, Font, Foreground, PadOpt, Wrap, EnabledThe widgets that can be created from a BasicWindow and packed in a Container are
struct Cell a = setValue :: a -> Action getValue :: Request a struct LineEditable = lines :: Request Int getLine :: Int -> Request String deleteLine :: Int -> Action insertLines :: Int -> [String] -> Action struct Invokable = invoke :: Action struct Scannable a = mark :: a -> Action drag :: a -> Action struct ScrollWidget a < WWidget aA Cell a is an objects that maintains an value of type a. This can typically be manipulated by the user in a widget-specific way; the Cell type gives a unified way of program interaction with this value.
A LineEditable widget supports a few operations for setting and accessing content on a line basis.
An Invokable has a widget-specific way to be invoked by the user; the method invoke provides a uniform way for program invokation.
Finally, a Scannable widget provides hook methods to implement rapid scanning over the widget. All the scannable widgets implement this by default using the middle button; moving the mouse with this button pressed over the widget scans over the widget.
Canvas coordinates have their origin in the upper left corner and pixels as unit.
struct CWidget a < ConfWidget a = getCoords :: Request [Pos] setCoords :: [Pos] -> Action move :: Pos -> Action struct Arc < CWidget ArcOpt struct CImage < CWidget CImageOpt struct CText < CWidget CTextOpt struct CWindow < CWidget WindowOpt, BasicWindow WindowOpt struct Line < CWidget LineOpt struct Oval < CWidget OvalOpt struct Polygon < CWidget PolygonOpt struct Rectangle < CWidget RectangleOpt data CBasicOpt > Fill, Width, Stipple data ArcOpt > OvalOpt, ArcStyle, Angles data CImageOpt > Anchor, Img, Btmp data CTextOpt > Font, Justify, Text, Anchor, Fill data CWindowOpt > DimOpt, Anchor data LineOpt > CBasicOpt, Arrow, Smooth, CapStyle, JoinStyle data OvalOpt > CBasicOpt, Outline data PolygonOpt > OvalOpt, Smooth data RectangleOpt > OvalOptThe canvas widgets are
struct Menu < ConfWidget MenuOpt = mButton :: [MButtonOpt] -> Request MButton cascade :: [MButtonOpt] -> Request Menu struct MButton < Configurable MButtonOpt, Invokable data MenuOpt > WindowOpt, Enabled data MButtonOpt > StdOpt, FontOpt, PadOpt, Img, Btmp, Underline, CLabel, Enabled, CommandWith a menu one can create MButton (button-like entries with text or image and an associated Command) option) and cascaded submenus. Simple use of menus in a menubar (without cascades) is captured in the function menubar in TkUtil.
For popup menus and option menus, see Tix.
data ButtonPress = ButtonPress Int (Pos -> Cmd ()) | AnyButtonPress (Int -> Pos -> Cmd ()) data MouseEvent > ButtonPress = ButtonRelease Int (Pos -> Cmd ()) | AnyButtonRelease (Int -> Pos -> Cmd ()) | Motion Int (Pos -> Cmd ()) | AnyMotion (Pos -> Cmd ()) | Double ButtonPress | Triple ButtonPress data WindowEvent = Enter (Cmd ()) | Leave (Cmd ()) | Configure (Pos -> Cmd ()) data SimpleKeyEvent = KeyPress String (Cmd ()) | KeyRelease String (Cmd ()) | AnyKeyPress (String -> Cmd ()) data KeyEvent > SimpleKeyEvent = Mod [Modifier] SimpleKeyEvent data Modifier = Alt | Control | Lock | Meta | Shift deriving Show data DestroyEvent = Destroy (Cmd ()) data Event > MouseEvent, KeyEvent, WindowEvent, DestroyEventThe supported event types are the following:
data None = None data AnchorType = NW | N | NE | W | C | E | SW | S | SE data ReliefType = Raised | Sunken | Flat | Ridge | Solid | Groove data VertSide = Top | Bottom data WrapType = NoWrap | CharWrap | WordWrap data SelectType = Single | Multiple data Align = LeftAlign | CenterAlign | RightAlign data Round = Round data ArcStyleType = Pie | Chord | Perimeter data CapStyleType > Round = Butt | Proj data JoinStyleType > Round = Bevel | Miter data ArrowType > None = First | Last | Both
data Anchor = Anchor AnchorType Specifies positioning detail for text in some text-based widgets and for the widget as a whole in some canvas widgets.
data Angles = Angles Pos Specifies extent of an Arc.
data ArcStyle = ArcStyle ArcStyleType Specifies form of an Arc.
data Arrow = Arrow ArrowType Specifies in which end(s) a Line should have arrowheads.
data Background = Background Color Specifies a background color for the widget.
data BitmapData = BitmapData String Describes a bitmap as a string in X bitmap format.
data BorderWidth = BorderWidth Int Specifies border width in pixels (normally used together with the Relief option to describe the border).
data Btmp = Btmp PredefBitmap Used to describe (only) the predefined bitmaps to display in a label or button (other bitmaps are prescribed using the Img option).
data CapStyle = CapStyle CapStyleType Specifies cap style for Line widgets.
data CLabel = CLabel String Describes the text on an MButton. (This is unfortunate; for technical reasons the Text option cannot be used for MButtons).
data CmdInt = CmdInt (Int -> Cmd ()) Specifies a callback procedure for sliders (and other widgets in Tix).
data Command = Command (Cmd ()) Specifies a callback procedure for buttons.
data Cursor = Cursor String Specifies the cursor to be used in the widget; the string should be a valid name for an X cursor (e.g. "crosshair","arrow"); a listing of valid cursor names is in the X11 header file cursorfont.h.
data Enabled = Enabled Bool Specifies whether user actions should be enabled (for e.g. buttons, mbuttons, entries, texteditors).
data File = File FilePath Specifies a file name from where to read a bitmap or image.
data Fill = Fill Color Specifies a color for fillable canvas widgets.
data Font = Font String Specifies a font. Valid strings are family size styles, where family includes at least courier, helvetica and times, size is a positive integer and the optional styles includesnormal (default), bold, italic, underline and overstrike. Also full X font names such as "-adobe-courier-medium-o-normal--12-120-75-75-m-70-iso8859-1" are accepted.
data Foreground = Foreground Color Specifies a foreground color for the widget.
data From = From Int Specifies the minimum value for sliders.
data Height = Height Int Specifies the widget height; in lines for font-based widgets and in pixels for others.
data Img = Img Image Specifies an image to be displayed in a label, button or CImage.
data Indicatoron = Indicatoron Bool Specifies whether the indicator should be displayed for checkbuttons and radiobuttons.
data JoinStyle = JoinStyle JoinStyleType Specifies join style for LInes.
data Justify = Justify Align Specifies multi-line text justification.
data Length = Length Int Specifies the length (in pixels) of a slider.
data Orientation = Orientation Dir Specifies orientation of a slider.
data Outline = Outline Color Specifies outline color for fillable canvas widgets.
data Padx = Padx Int Specifies requested external padding (i.e. intra-widget space) in the X direction for a widget (in pixels).
data Pady = Pady Int Specifies requested external padding (i.e. intra-widget space) in the Y direction for a widget (in pixels).
data Relief = Relief ReliefType Specifies border type.
data ScrollRegion = ScrollRegion (Int,Int) (Int,Int) Specifies the coordinates of two opposite corners in a Canvas when attaching scrollbars.
data SelectMode = SelectMode SelectType Specifies for a listbox whether multiple selections are accepted.
data SelectColor = SelectColor (Maybe Color) Specifies the color marking selection in the indicator of a check- or radiobutton.
data Smooth = Smooth Bool Indicates spline approximation for lines and polygons.
data Stipple = Stipple String Specifies a file containing a bitmap pattern to be used for stippling when filling a canvas widget.
data Text = Text String Specifies text on a label or button.
data Title = Title String Specifies a window title to be used by the window manager as title.
data To = To Int Specifies maximum value for a slider.
data Underline = Underline Int Specifies the index of a character in the widget text to underlined.
data Width = Width Int Specifies the width of a widget; in characters for font-based widgets and in pixels for others.
data Wrap = Wrap WrapType Specifies wrap mode for TextEditors.
In the event that a widget that was created in a window needs to be packed inside a subframe, one has to be more explicit. Widgets are laid out in a Container by using the container's pack method. In simple use, widgets created in a window win are packed bu call of win.pack. However, one can also pack these widget in a frame created by calls to win.frame, thus producing Packables or WWidgets.
Packing a window also causes the window to be displayed on screen.
The argument to pack is a Packable object. All WWidgets are Packable; in addition one can combine Packables using the functions
row :: [Packable] -> Packable col :: [Packable] -> Packable infix 6 ^^^ infix 7 <<< (^^^), (<<<) :: Packable -> Packable -> Packable p1 <<< p2 = row [p1,p2] p1 ^^^ p2 = col [p1,p2]For simple layout effects these combinators are sufficient. However, for fine-tunig the layout further concepts are needed.
Every window widget has a preferred size (width and height), which is determined either by the size of its content (text, image, etc) or by explicit setting of Width and Height options. It is then easy to determine a preferred size for a row (column) of widgets; just add their widths (heights) and take the maximum of their heights (widths). Packing a container c using the call c.pack p for some packable p causes the container's size to be set to the preferred size of p (thus containersdo not support the Width and Height options); then sizes are assigned top-down to individual packables. This may lead to a packable being assigned a size that is larger than it prefers (since all elements in a row do not have the same preferred height, etc). Layout finetuning is concerned with how this extra size is utilized. By default, all packables adapt to make use of the extra space. This means that e.g. in a window with a button below a canvas, the button will accept to take on the full width of the canvas, even though it likely prefers a much smaller width. This behaviour can be changed by using the functions
data Stretch > None = XFill | YFill | XYFill type Expandable = Bool fill :: Stretch -> Expandable -> Packable -> Packable rigid, fillX, fillY :: Packable -> Packable rigid = fill None False fillX = fill XFill False fillY = fill YFill FalseEach packable has a stretch property, deciding how it will accept to stretch to fill out extra space in no direction (None), only in the x direction (XFill), only in the y direction (YFill), or in both directions (XYFill). The default is XYFill.
A packable may or may not be expandable; an expandable
packable accepts to be
assigned extra width as a member of a row and extra height as a
member of a column. If a row has been assigned extra width (this can
happen!), this is shared equally among its
expandable elements; if no element is expandable, unused space is
left in the right end of the row; similarly for cols. The default
is to be expandable.
A rigid packable is determined to stick to its preferred
size; a rigid (row of) button(s) below a canvas
will not expand, regardless of how the window is resized. A fillX
packable will expand in the x direction, but not in the y direction;
this is likely to be the preferred behaviour for a menubar or
horizontal scrollbar.
Colors
The data type of colors used in Tk is
data Color = RGB Int Int Int
deriving (Eq)
black = RGB 0 0 0
white = RGB 255 255 255
red = RGB 255 0 0
green = RGB 0 255 0
blue = RGB 0 0 255
yellow = RGB 255 255 0
rgb :: Int -> Int -> Int -> Color
rgb r g b = RGB r g b