\chapter{Simple graphics} \label{sec:graphics} In \chapref{starting} we introduced the principal predicates of \product{}. For the examples we used controllers, because these are relatively easy to use. In this section we present the basic graphical components. These are more general and therefore can be applied in many more situations, but they are also more difficult to use. This section only introduces the basics of graphics in \product{}. \ifpw{}{See also \cite{XPCE:draw}.} The online manual and the demo programs provide more information on using \product{}'s graphics. \section{Graphical building blocks} \index{graphical,window}\index{window,coordinates}% A \class{window} is the most generic window class of \product{}. Drawings are often displayed on a \class{picture}, which is a window with scrollbars. The drawing area of a window is two-dimensional and infinitely large (both positive and negative). The query below creates a picture and opens it on the screen. \begin{code} 1 ?- new(@p, picture('Demo Picture')), send(@p, open). \end{code} The following queries draw various primitive graphicals on this picture. \begin{code} 2 ?- send(@p, display, new(@bo, box(100,100))). 3 ?- send(@p, display, new(@ci, circle(50)), point(25,25)). 4 ?- send(@p, display, new(@bm, bitmap('32x32/books.xpm')), point(100,100)). 5 ?- send(@p, display, new(@tx, text('Hello')), point(120, 50)). 6 ?- send(@p, display, new(@bz, bezier_curve(point(50,100), point(120,132), point(50, 160), point(120, 200)))). \end{code} \product{}'s graphics infrastructure automatically takes care of the necessary repaint operations when graphical objects are manipulated. Try the queries below to appreciate this. The result is shown in \figref{graphics}. \begin{code} 7 ?- send(@bo, radius, 10). 8 ?- send(@ci, fill_pattern, colour(orange)). 9 ?- send(@tx, font, font(times, bold, 18)). 10 ?- send(@bz, arrows, both). \end{code} \postscriptfig[width=4in]{graphics}{Example graphics} \product{} avoids unnecessary repaint operations and expensive computations involved in updating the screen. The screen is only updated {\em after} all available input has been processed or on an explicit request to update it. The following code illustrates this. Running \mbox{\tt ?- square_to_circle(@bo).} will show the box immediately as a circle without showing any of the intermediate results. \begin{code} :- require([between/3, forall/2]). square_to_circle(Box) :- get(Box, height, H), MaxRadius is H // 2, forall(between(0, MaxRadius, Radius), send(Box, radius, Radius)). \end{code} To get the intended animating behaviour, use `graphical ->flush' to explicitly force redraw right now: \begin{code} :- require([between/3, forall/2]). square_to_circle(Box) :- get(Box, height, H), MaxRadius is H // 2, forall(between(0, MaxRadius, Radius), ( send(Box, radius, Radius), send(Box, flush) )). \end{code} \subsection{Available primitive graphical objects} An overview of the available primitive graphical classes is most easily obtained using the Class Hierarchy tool described in \secref{classhierarchy}. Table \tabref{primgraphics} provides an overview of the primitive graphicals. \begin{table} \begin{center} \begin{tabularlp}{\class{ellipse}} \hline \class{arrow} & Arrow-head. Normally used implicitly by class \class{line}. \\ \hline \class{bezier} & Bezier curve. Both quadratic and cubic Biezer curves are supported. \\ \hline \class{bitmap} & Visualisation of an image. Both monochrome and full-colour images are supported. Images can have shape. See \secref{images}. \\ \hline \class{pixmap} & Subclass of bitmap only for coloured images. \\ \hline \class{box} & Rectangle. Can be rounded and filled. \\ \hline \class{circle} & Special case of ellipse. \\ \hline \class{ellipse} & Elliptical shape. May be filled. \\ \hline \class{arc} & Part of an ellipse. Can have arrows. Can show as \idx{pie-slice}. \\ \hline \class{line} & Straight line segment. Can have arrows. \\ \hline \class{path} & Poly-line through multiple points. Can have arrows. Can be \idx{smooth}. \\ \hline \class{text} & Visualisation of a string in some font. Can have various attributes, can be clipped, formatted, etc. \\ \hline \end{tabularlp} \end{center} \caption{Primitive graphical objects} \label{tab:primgraphics} \end{table} \section{Compound graphicals} Often one would like to combine two or more primitive graphical objects into a single unit. This is achieved using class \class{device}. Below we create an icon, consisting of a bitmap and a textual label displayed below it. \begin{code} 9 ?- new(@ic, device), send(@ic, display, bitmap('happy.bm')), send(@ic, display, text('Happy'), point(0, 64)), send(@p, display, @ic, point(250, 20)). \end{code} A compound graphical may be treated as a unit. It may be moved, erased, coloured, etc.\ by sending a single message to the compound. Compound graphicals are normal graphicals and thus may de displayed on other compound graphicals, resulting in a consists-of hierarchy of nested graphicals. See also \secref{vishierarchy}. The classes related to compound graphical objects are shown in \tabref{compoundgraphics}. \begin{table} \begin{center} \begin{tabularlp}{\class{figure}} \hline \class{device} & Most generic compound graphical object. The \class{window} is a subclass of \class{device} and all graphical operations are defined on class \class{device}. \\ \hline \class{figure} & Subclass of \class{device}, provides clipping, background, containing rectangle, border and the possibility to show a subset of the displayed graphical objects. \\ \hline \class{format} & A format object specifies a two-dimensional table layout. Formats may be associated to graphical devices using `device ->format'. \\ \class{table} & The successor of \class{format} realises tabular layout compatible to the HTML-3 model for tables. See \secref{tabular}. \\ \hline \end{tabularlp} \end{center} \caption{Compound graphical classes} \label{tab:compoundgraphics} \end{table} \section{Connecting graphical objects} \label{sec:connection} \index{graph}% The primary application domain of \product{} is handling graphical modelling languages. Drawing in such languages often entails connecting graphical objects using lines. Instead of adding an instance of \class{line} to the graphical device at the proper place, it is much better to declare two graphical objects to be connected. Class \class{connection} provides for this. To prepare an object for making connections, the object should first define \classs{handle}. Below is a simple example. The link is a {\em reusable} object and therefore defined as a global reference. See \secref{namedref}. The screendump is shown in \figref{connect}. \begin{pcecode} :- pce_global(@in_out_link, make_in_out_link). make_in_out_link(L) :- new(L, link(in, out, line(arrows := second))). linked_box_demo :- new(P, picture('Linked Box demo')), send(P, open), send(P, display, new(B1, box(50,50)), point(20,20)), send(P, display, new(B2, box(25,25)), point(100,100)), send(B1, handle, handle(w, h/2, in)), send(B2, handle, handle(w/2, 0, out)), send_list([B1, B2], recogniser, new(move_gesture)), send(B1, connect, B2, @in_out_link). \end{pcecode} \postscriptfig{connect}{A connection between two boxes} If there are multiple handles of the same `kind' on a graphical, a connection will automatically try to connect to the `best' handle. The classes related to making connections are summarised in \tabref{connectclasses}. \begin{table} \begin{center} \begin{tabularlp}{\class{connect_gesture}} \hline \class{connection} & Subclass of class \class{line}. A connection can connect two graphicals on the same window that have handles. The line is automatically updated if either of the graphicals is moved, resized, changed from device, (un)displayed, hidden/exposed or destroyed. \\ \hline \class{handle} & Defines the location, nature and name of a connection point for a connection. Handles can be attached to individual graphicals as well as to their class. \\ \hline \class{link} & Defines the generic properties of a connection: the nature (`kind') of the handle at either side and the line attributes (arrows, pen and colour). \\ \hline \class{connect_gesture} & Event-processing object (see \secref{recogniser}) used to connect two graphical objects. \\ \hline \end{tabularlp} \end{center} \caption{Classes used to define connections} \label{tab:connectclasses} \end{table} Note that, as class \class{connection} is a subclass of \class{graphical}, connections can be created between connections. Class \class{graphical} defines various methods to help reading the relations expressed with connections and/or refine the generic \class{connect_gesture}. \section{Constraints} \product{} allows the user to specify constraints between pairs of objects. In the example above we would like the text to be centered relative to the bitmap. This may be achieved using: \begin{code} 10 ?- get(@ic, member, bitmap, Bitmap), get(@ic, member, text, Text), new(_, constraint(Bitmap, Text, identity(center_x))). \end{code} Each time either the bitmap or the text changes this constraint will invoke <-center_x on the changed object and ->center_x with the return value on the other object. Class \class{spatial} defines more general geometrical constraints between graphicals. Constraints are high-level, but potentially expensive means to specify graphical relations. An alternative is the redefinition of the ->geometry method of (compound) graphical objects. See \chapref{udc}. \section{Activating graphicals using the mouse} \label{sec:recogniser} \index{event,processing}\index{sensitive}\index{moving graphicals}% \class{Recogniser} objects enable detection of mouse- and keyboard activities. \product{} defines both primitive and complex recognisers. The first (called \class{handler}) processes a single event. The latter processes a \class{gesture}: sequence of events starting with a mouse-button-down up to the corresponding mouse-button-up. The following example allows us to move the icon by dragging with the middle mouse button: \begin{code} 11 ?- send(@ic, recogniser, new(move_gesture)). \end{code} The second example allows us to double-click on the icon. This is a common way to `open'\index{open,icon} an icon. In the example we will just print 'hello' in the Prolog window. \begin{code} 12 ?- send(@ic, recogniser, click_gesture(left, '', double, message(@pce, write_ln, hello))). \end{code} The predefined recogniser classes are summarised in \tabref{recognisers}. Besides the built-in recognisers, the \productpl{} library defines various additional ones. See also \secref{dragdrop}. \begin{table} \begin{center} \begin{tabularlp}{\class{resize_outline_gesture}} \hline \class{handler} & Binds a single event to a \class{message}. \\ \hline \class{handler_group} & Combines multiple recognisers into a single. \\ \hline \class{key_binding} & Maps keyboard sequences to commands. \\ \hline \class{click_gesture} & Maps a mouse-click to a message. Allows to specify modifiers (alt/meta, control, shift), button and multi (single, double, triple). \\ \hline \class{connect_gesture} & Connect two graphicals dragging from the first to the second. \\ \hline \class{move_gesture} & Move graphical by dragging it. \\ \hline \class{move_outline_gesture} & Move graphical by dragging an outline. \\ \hline \class{resize_gesture} & Resize graphical by dragging a side or corner. \\ \hline \class{resize_outline_gesture} & Resize graphical by dragging a side or corner of the outline. \\ \hline \end{tabularlp} \end{center} \caption{Recogniser classes} \label{tab:recognisers} \end{table} \section{Summary} In this section we have introduced some of the graphics capabilities of \product{}. \product{}'s graphics are built from primitive and compound graphicals. A compound graphical has its own coordinate system in which it can display any graphical object including other compound objects. Graphical objects can be connected to each others using a \class{connection}. This facility makes the generation of graphs relatively simple. It also makes it very simple to extract the graph represented by a drawing made by the user. Graphical objects are made sensitive to mouse and keyboard activities by attaching \class{recogniser} objects to them. \product{} defines standard recognisers for various complex operations such as moving, resizing, popup-menu's, linking graphicals and clicking on graphicals.