Graphics Objects
Volume Number: 2
Issue Number: 11
Column Tag: Lisp Listener
Simple Graphics Objects
By Andrew Shalit, Cambridge, MA
Graphics Objects in MacScheme
Welcome back to Lisp Listener! Our current choice of Lisp implementations is
MacScheme by Semantic Micro systems. Scheme is a modern and elegant dialect of Lisp,
and MacScheme is a robust, complete, and elegant implementation. Previously M
MacScheme did not offer pro-grammers much access to the Macintosh toolbox. In
August a new release of a product called MacScheme + Toolsmith, was made which
allows the production of event-driven programs. This will be followed shortly by an
application builder that will make it possible to create stand-alone applications with
MacScheme. The MacScheme editor, which is currently fairly limited, is also in the
process of being upgraded. Look for reviews of all these items in future columns.
The only way to get to the toolbox in the previous incar-nation of MacScheme,
version 1.11, was through an escape into machine language that looks very complicated
(I haven't tried it out). Version 1.11 does, though, have some simple graphics
capabilities which we will be using in this month's column. As it stands now,
MacScheme is a great way to learn Lisp and explore object oriented programming.
Graphics in MacScheme
In early 1986, MacScheme was enhanced to allow the use of simple graphics
operations. MacScheme has one graphics window, which must be opened with a
procedure call before graphics can be used. The graphics window can be two sizes, 'full'
or 'half'. To open up a small graphics window, the code would be:
(start-graphics 'half)
Once a graphics window is open, you can get rid of it by saying:
(end-graphics)
(One thing to be careful of: you aren't allowed to 'start-graphics' if the graphics
window is already there, and you aren't allowed to end them if it isn't there. Moreover,
there is currently no way for a procedure to test whether the graphics window is open.
Hopefully Semantic Micro systems will add this test feature soon, or just allow you to
open the window even if it already open, or close it if it is closed.)
Once the graphics window is open, there are just under 30 commands for
drawing in it. These are all pretty basic: drawing, erasing, and inverting lines,
rectangles, ovals, circles and points. You can also set up a picture that will be
refreshed if the graphics window is obscured, draw a string, and clear the window.
For Macintosh programmers, MacScheme graphics take a little readjusting. This
is because MacScheme uses the coordinate system that you learned in grade school,
instead of the one you learned in Inside Macintosh. That's right, the x coordinate comes
first, followed by the y coordinate. The half size graphics window is 470x130 pixels,
so the procedure call
(paint-oval 20 95 50 125)
would paint a circle in the lower left hand corner of the graphics window.
The general form of graphics procedures that work with two points is
(procedure x1 y1 x2 y2)
Data Abstraction
This brings us to the first programming issue of the column: data abstraction.
As you can imagine, it would be awkward working with rectangles and points if you
always had to think about them in terms of their individual coordinates. One of the
strong points of Lisp is its ability to create complex data objects. So, before I did
anything with graphics, I created a set of procedures for working with points and
rectangles. The simplest way to work with a rectangle is to set it up as a list of four
coordinates. The coordinates can then be passed to a MacScheme graphics procedure by
saying
(apply the-procedure the-list )
In the sample procedures shown here, I use a slightly more complex data
structure because it makes the issue of data abstraction stand out more clearly.
As I have defined them, a point is a simple pair, and a rectangle is a list of points.
But the particular internal structure of a point or a rectangle is unimportant to most of
the procedures I will write. When I want to work with a point or rectangle, I always do