[net.micro.atari16] ProGEM part 3 of 6

bammi@cwruecmp.UUCP (Jwahar R. Bammi) (03/22/86)

#!/bin/sh
# This is a shell archive, meaning:
# 1. Remove everything above the #!/bin/sh line.
# 2. Save the resulting text in a file.
# 3. Execute the file with /bin/sh (not csh) to create the files:
#	wind7.prf
#	wind8.prf
#	wind9.prf
# This archive created: Fri Mar 21 22:40:54 1986
# By:	Jwahar R. Bammi ()
export PATH; PATH=/bin:$PATH
echo shar: extracting "'wind7.prf'" '(17805 characters)'
if test -f 'wind7.prf'
then
	echo shar: over-writing existing file "'wind7.prf'"
fi
sed 's/^X//' << \SHAR_EOF > 'wind7.prf'
X.!****************************************************************************
X.! 
X.! ANTIC PUBLISHING INC., COPYRIGHT 1985.  REPRINTED BY PERMISSION.
X.!
X.! ** Professional GEM ** by Tim Oren
X.!
X.! Proff File by ST enthusiasts at
X.! Case Western Reserve University
X.! Cleveland, Ohio
X.! uucp : decvax!cwruecmp!bammi
X.! csnet: bammi@case
X.! arpa : bammi%case@csnet-relay
X.! compuserve: 71515,155
X.!
X.!****************************************************************************
X.!
X.!
X.!****************************************************************************
X.!
X.!			Begin Part 7
X.!
X.!****************************************************************************
X.!
X.PART VII Menu Structures
X.SH HAPPY NEW YEAR
XThis is article number seven in the ST
XPRO GEM series, and the first for 1986.  In this installment,
XI will be discussing GEM menu structures and how to use them
Xin your application.  There is  also a short Feedback
Xresponse section.  You will find the download file containing
Xthe code for this column in the file GEMCL7.C in DL3 of the
XATARI16 SIG (PCS-58).
X.SH MENU BASICS
XIn ST GEM, the menu consists of a bar
Xacross the top of the screen which displays several sub-menu
Xtitles.  Touching one of the titles causes it to highlight,
Xand an associated "drop-down" to be drawn  directly below on
Xthe screen.  This drop-down may be dismissed by moving  to
Xanother title, or by clicking the mouse off of the drop-down.
X.PP
XTo make a selection, the mouse is moved over the
Xdrop-down.  Each  valid selection is highlighted when the
Xmouse touches it.  Clicking the mouse  while over one of
Xthese selections picks that item.  GEM then undraws the
Xdrop-down, and sends a message to your application giving the
Xobject number  of the title bar entry, and the object number
Xof the drop-down item which  were selected by the user.  The
Xselected title entry is left highlighted  while your code
Xprocesses the request.
X.SH  MENU STRUCTURES
XThe data structure which defines a GEM
Xmenu is (surprise!) an object tree, just like the dialogs and
Xpanels which we have discussed before.  However, the
Xoperations of the GEM menu manager are quite different from
Xthose of the form manager, so the internal design of the menu
Xtree has some curious constraints.
X.PP
XThe best way to understand these constraints is to look
Xat an  example.  The first item in the download is the object
Xstructure (only) of the menu tree from the GEM Doodle/Demo
Xsample application.
X.PP
XThe ROOT of a menu tree is sized to fit the entire
Xscreen.  To satisfy the visual hierarchy principle (see
Xarticle #5), the screen is divided into two parts: THE BAR,
Xcontaining the menu titles, and THE SCREEN, while contains
Xthe drop-downs when they are drawn.  Each of these areas is
Xdefined by an object of the same name, which are the only two
Xobjects linked directly below the ROOT of a menu tree.  You
Xwill notice an important implication of this structure:  The
Xmenu titles and their associated drop-downs are stored in
Xentirely different subtrees of the menu!
X.PP
XWhile examining THE BAR in the example listing, you may
Xnotice that its OB_HEIGHT is very large (513).  In
Xhexadecimal this is 0x0201.  This defines a height for THE
XBAR of one character plus two pixels used for spacing.  THE
XBAR and its subtree are the only objects which are drawn on
Xthe screen in the menu's quiescent state.
X.PP
XThe only offspring object of THE BAR is THE ACTIVE.  This
Xobject defines the part of THE BAR which is covered by menu
Xtitles.  The screen rectangle belonging to THE ACTIVE is used
Xby the GEM screen manager when it  waits for the mouse to
Xenter an active menu title.  Notice that THE ACTIVE and its
Xoffspring also have OB_HEIGHTs with pixel residues.
X.PP
XThe actual menu titles are linked left to right in order
Xbelow THE ACTIVE.  Their OB_Xs and OB_WIDTHs are arranged so
Xthat they  completely cover THE ACTIVE.  Normally, the title
Xobjects are typed  G_TITLE, a special type which assures that
Xthe title bar margins are correctly drawn.
X.PP
XTHE SCREEN is the parent object of the drop-down boxes
Xthemselves. They are linked left to right in an order
Xidentical with their titles, so  that the menu manager can
Xmake the correct correspondence at run-time.  The OB_X of
Xeach drop-down is set so that it is positioned below its
Xtitle on the screen.
X.PP
XNotice that it is safe to overlap the drop-downs within a
Xmenu,  since only one of them will be displayed at any time.
XThere is one constraint on the boxes however:  They must be
Xno greater than a quarter screen in total size.  This is the
Xsize of the off-screen blit buffer which is used by GEM to
Xstore the screen contents when the drop-down is drawn.  If
Xyou exceed this size, not all the screen under the drop-down
Xwill be restored, or the ST may crash!
X.PP
XThe entries within a drop-down are usually G_STRINGs,
Xwhich are optimized for drawing speed.  The rectangles of
Xthese entries must  completely cover the drop-down, or the
Xentire drop-down will be inverted  when the mouse touches an
Xuncovered area!  Techniques for using objects  other than
XG_STRINGs are discussed later in this column.
X.PP
XThe first title and its corresponding drop-down are
Xspecial.  The title name, by custom, is set to DESK.  The
Xdrop-down must contain exactly  eight G_STRING objects.  The
Xfirst (again by custom) is the INFO entry,  which usually
Xleads to a dialog displaying author and copyright information
Xfor your application.  The next is a separator string of
Xdashes with the DISABLED flag set.  The following six objects
Xare dummy strings which GEM fills in with the names of desk
Xaccessories when your menu is loaded.
X.PP
XThe purpose of this description of menu trees is to give
Xyou an understanding of what lies "behind the scenes" in the
Xnext section, which describes the run-time menu library
Xcalls.  In practice, the Resource Construction Set provides
X"blank menus" which include all of the required elements, and
Xit also enforces the constraints on internal structure.  You
Xonly need to worry about these if you modify the menu tree
X"on-the-fly".
X.SH USING THE MENU
Xonce you have loaded the application's
Xresource, you can ask the AES to install your menu.  You must
Xfirst get the address of the menu tree within the resource
Xusing:
X.FB rsrc_gaddr()
Xrsrc_gaddr(R_TREE, MENUTREE, &ad_menu);
X.FE
Xassuming that MENUTREE is the name you gave the menu in the
XRCS, and that ad_menu is a LONG which will receive the
Xaddress.  Then you call the AES to establish the menu:
X.FB menu_bar()
Xmenu_bar(ad_menu, TRUE);
X.FE
XAt this point, the AES draws your menu bar on the screen and
Xanimates it when the user moves the mouse into the title
Xarea.
X.PP
XThe AES indicates that the user has made a menu selection
Xby sending your application a message.  The message type is
XMN_SELECTED,  which will be stored in msg[0], the first
Xlocation in the message  returned by evnt_multi().
X.PP
XThe AES also stores the object number of the selected
Xmenu's  title in msg[3], and the object number of the
Xselected menu item in msg[4].  Generally, your application
Xwill process menu messages with nested C switch statements.
XThe outer switch will have one case for each menu title, and
Xthe inner switch statements will have a case for each entry
Xwithin the selected menu.  (This implies that you must give a
Xname to each title and to each menu entry when you create the
Xmenu in the RCS.)
X.PP
XAfter the user has made a menu selection, the AES leaves
Xthe title of the chosen menu in reverse video to indicate
Xthat your application is busy processing the message.  When
Xyou done with whatever action is indicated, you need to
Xreturn the title to a normal state. This is done with
X.FB menu_tnormal()
Xmenu_tnormal(ad_menu, msg[3], TRUE);
X.FE
X.sp 1
X.ce 1
X(Remember that msg[3] is the title's object number.)
X.sp 1
XWhen your application is ready to terminate, it should
Xdelete its menu bar.  Do this with the call:
Xmenu_bar(ad_menu, FALSE);
X.SH GETTING FANCY
XThe techniques above represent the bare
Xminimum to handle menus.  In most cases, however, you will
Xwant your menus to be more "intelligent" in displaying the
Xuser's options.  For instance, you can prevent many user
Xerrors by disabling inappropriate choices, or you can save
Xspace on drop-downs by showing only one line for a toggle and
Xaltering its text or placing and removing a check mark when
Xthe state is changed.  This section discusses these and other
Xadvanced techniques.
X.PP
XIt is a truism of user interface design that the best way
Xto deal with an error is not to let it happen in the first
Xplace.  It  many cases, you can apply this principle to GEM
Xmenus by disabling  choices which should not be used.  If
Xyour application uses a "selection  precedes action" type of
Xinterface, the type of object selected may  give the
Xinformation needed to do this.   Alternately, the state of
Xthe  underlying program may render certain menu choices
Xillegal.
X.PP
XGEM provides a call to disable and re-enable menu
Xoptions. The call is:
X.FB menu_ienable()
Xmenu_ienable(ad_menu, ENTRY, FALSE);
X.FE
Xto disable a selection.  The entry will be grayed out when
Xit is drawn, and will not invert under the mouse and will not
Xbe selected by the user. Substituting TRUE for FALSE
Xre-enables the option.  ENTRY is the name  of the object
Xwhich is being affected, as assigned in the RCS.
X.PP
XNote that menu_ienable() will not normally affect the
Xappearance or operation of menu TITLE entries.  However,
Xthere is an undocumented feature which allows this.  If ENTRY
Xis replaced by the object number of a title bar entry with
Xits top bit set, then the entire associated drop-down will be
Xdisabled or re-enabled as requested, and the title's
Xappearance will be changed.  But, be warned that this feature
Xdid not work reliably in some early versions of GEM.  Test it
Xon your copy of ST GEM, and use it with caution when you
Xcannot control the version under which your application may
Xrun.
X.PP
XIt is also possible to disable menu entries by directly
Xaltering the DISABLED attribute within the OB_STATE word.
XThe routines enab_obj() and disab_obj() in the download show
Xhow this is done.  They are also used in set_menu(), which
Xfollows them immediately.
X.PP
XSet_menu() is a utility which is useful when you wish to
Xsimultaneously enable or disable many entries in the menu
Xwhen the program's state changes or a new object is selected
Xby the user.   It is called with
X.FB set_menu()
Xset_menu(ad_menu, vector);
X.FE
Xwhere vector is a pointer to an array of WORDs.  The first
Xword of the array determines the default state of menu
Xentries.  If it is TRUE, then set_menu() enables all entries
Xin every drop-down of the menu tree, except that the DESK
Xdrop-down is unaffected.  If it is FALSE, then every menu
Xentry is disabled.
X.PP
XThe following entries in the array are the numbers of
Xmenu entries which are to be toggled to the reverse of the
Xdefault state. This list is terminated by a zero entry.
X.PP
XThe advantage of set_menu() is that it allows you to
Xbuild a collection of menu state arrays, and associate one
Xwith each type of user-selected object, program state, and so
Xon.  Changing the status of the menu tree may then be
Xaccomplished with a single call.
X.SH CHECK, PLEASE?
XOne type of state indicator which may
Xappear  within a drop-down is a checkmark next to an entry.
XYou can add the  checkmark with the call:
X.FB menu_icheck()
Xmenu_icheck(ad_menu, ENTRY, TRUE);
X.FE
Xand remove it by replacing the TRUE with FALSE.  As above,
XENTRY is the name of the menu entry of interest.  The
Xcheckmark appears inside the left boundary of the entry
Xobject, so leave some space for it.
X.PP
XThe menu_icheck() call is actually changing the state of
Xthe CHECKED flag within the entry object's OB_STATE word.  If
Xnecessary, you may alter the flag directly using do_obj() and
Xundo_obj() from the download.
X.SH  NOW YOU SEE IT, NOW YOU DON'T
XYou can also alter the
Xtext  which appears in a particular menu entry (assuming that
Xthe entry is  a G_STRING object).  The call
X.FB menu_text()
Xmenu_text(ad_menu, ENTRY, ADDR(text));
X.FE
Xwill substitute the null-terminated string pointed to by
Xtext for whatever is currently in ENTRY.  Remember to make
Xthe drop-down wide enough to handle the largest text string
Xwhich you may substitute.  In the interests of speed,
XG_STRINGs drawn within drop-downs are not clipped, so you may
Xget garbage characters on the desktop if you do not size the
Xdrop-down properly!
X.PP
XThe menu_text() call actually alters the OB_SPEC field of
Xthe menu entry object to point to the string which you
Xspecify.  Since the menu tree is a static data structure
Xwhich may be directly accessed by the AES at any time, be
Xsure that the string is also statically allocated and that it
Xis not modified without first being delinked from the menu
Xtree. Failure to do this may result in random crashes when
Xthe user accesses the drop-down!
X.SH LUNCH AND DINNER MENUS
XSome applications may have such
Xa wide  range of operations that they need more than one menu
Xbar at different  times.  There is no problem with having
Xmore than one menu tree in a  resource, but the AES can only
Xkeep track of one at a time.  Therefore,  to switch menus you
Xneed to use menu_bar(ad_menu1, FALSE); to release  the first
Xmenu, then use menu_bar(ad_menu2, TRUE); to load the second
Xmenu tree.
X.PP
XChanging the entire menu is a drastic action.  Out of
Xconsideration for your user, it should be associated with
Xsome equally obvious change in the application which has just
Xbeen manually requested.  An example  might be changing from
Xspreadsheet to data graphing mode in a multi-function
Xprogram.
X.SH DO IT YOURSELF
XIn a future column, I will discuss how
Xto set up user-defined drawing objects.  If you have already
Xdiscovered them  on your own, you can use them within a
Xdrop-down or as a title entry.
X.PP
XIf the user-defined object is within a drop-down, its
Xassociated drawing code will be called once when the
Xdrop-down is first drawn. It will then be called in
X"state-change" mode when the entry is highlighted (inverted).
XThis allows you to use non-standard methods to show
Xselection, such as outlines.
X.PP
XIf you try to insert a user-defined object within the
Xmenu title area, remember that the G_TITLE object which you
Xare replacing includes part of the dark margin of the bar.
XYou will need to experiment with your object drawing code to
Xreplicate this effect.
X.SH MAKE PRETTY
XThere are a number of menu formatting
Xconventions which have become standard practice.  Using these
Xgives your application a recognizable "look-and-feel" and
Xhelps users learn it.  The following section reviews these
Xconventions, and supplies a few hints and tricks to obtain a
Xbetter appearance for you menus.
X.PP
XThe second drop-down is customarily used as the FILE
Xmenu.  It  contains options related to loading and saving the
Xfiles used by the  application, as well as entries for
Xclearing the workspace and  terminating the program.
X.PP
XYou should avoid crowding the menu bar.  Leave a couple
Xof spaces between each entry, and try not to use more than
X70% of the bar.  Not only does this look better, but you will
Xhave space for longer words if you translate your application
Xto a foreign language.
X.PP
XSimilarly, avoid cluttering menu drop-downs.  Try to keep
Xthe number of options to no more than ten unless they are
Xclearly related, such as colors.  Separate off dissimilar
Xentries with the standard disabled dashes line.  (If you are
Xusing set_menu(), remember to consider the separators when
Xsetting up the state vectors.)
X.PP
XIf the number of options grows beyond this bound, it may
Xbe time to move them to a dialog box.  If so, it is a
Xconvention to put three dots following each menu entry which
Xleads to a dialog. Also, allow a margin on the menu entries.
XTwo leading blanks and a minimum of one trailing blank is
Xstandard, and allows room for checkmarks if they are used.
X.PP
XDangerous menu options should be far away from common
Xused entries, and are best separated with dashed lines.  Such
Xoptions should either lead to a confirming go/no-go alert, or
Xshould have associated "undo" options.
X.PP
XAfter you have finished defining a menu drop-down with
Xthe RCS,  be sure that its entries cover the entire box.
XThen use ctrl-click to  select the drop-down itself, and SORT
Xthe entries top to bottom.  This  way the drop-down draws in
Xsmoothly top to bottom.
X.PP
XFinally, it is possible to put entries other than
XG_STRINGs into drop-downs.  In the RCS, you will need to
Ximport them via the clipboard from the Dialog mode.
X.PP
XSome non-string object, such as icons and images, will
Xlook odd  when they are inverted under the mouse.  There is a
Xstandard trick for  dealing with this problem.  Insert the
Xicon or whatever in the drop-down first.  Then get a G_IBOX
Xobject and position and size it so that it covers the first
Xobject as well as the extra area you would like to be
Xinverted.
X.PP
XEdit the G_IBOX to remove its border, and assign the
Xentry name  to it.  Since the menu manager uses objc_find(),
Xit will detect and invert this second object when the mouse
Xmoves into the drop-down.  (To see why, refer to article #5.)
XFinally, DO NOT SORT a drop-down which has been set  up this
Xway!
X.SH  THAT'S IT FOR NOW!
XThe next column will discuss some of
Xthe principles of designing GEM interfaces for applications.
XThis topic is irreverantly known as GEM mythology or
Xinterface religion.  The subject for the following column is
Xundecided.  I am considering mouse and keyboard messages, VDI
Xdrawing primitives, and the file selector as topics.  Let me
Xknow your preferences in the Feedback!
X.!
X.!
X.!*****************************************************************************
X.!*									      *
X.!*				End Part 7				      *
X.!*									      *
X.!*****************************************************************************
SHAR_EOF
if test 17805 -ne "`wc -c 'wind7.prf'`"
then
	echo shar: error transmitting "'wind7.prf'" '(should have been 17805 characters)'
fi
echo shar: extracting "'wind8.prf'" '(25511 characters)'
if test -f 'wind8.prf'
then
	echo shar: over-writing existing file "'wind8.prf'"
fi
sed 's/^X//' << \SHAR_EOF > 'wind8.prf'
X.!****************************************************************************
X.! 
X.! ANTIC PUBLISHING INC., COPYRIGHT 1985.  REPRINTED BY PERMISSION.
X.!
X.! ** Professional GEM ** by Tim Oren
X.!
X.! Proff File by ST enthusiasts at
X.! Case Western Reserve University
X.! Cleveland, Ohio
X.! uucp : decvax!cwruecmp!bammi
X.! csnet: bammi@case
X.! arpa : bammi%case@csnet-relay
X.! compuserve: 71515,155
X.!
X.!****************************************************************************
X.!
X.!
X.!****************************************************************************
X.!
X.!			Begin Part 8
X.!
X.!****************************************************************************
X.!
X.PART VIII  USER INTERFACES
X.SH AND NOW FOR SOMETHING COMPLETELY DIFFERENT!
XIn response to a
Xnumber of requests, this installment of ST PRO GEM will be devoted
Xto examining a few of the principles of computer/human interface
Xdesign, or "religion" as some would have it.  I'm going to start
Xwith basic ergonomic laws, and try to draw some conclusions which
Xare fairly specific to designing for the ST.  If this article
Xmeets with general approval, further "homilies" may appear at
Xirregular intervals as part of the ST PRO GEM series.
X.PP
XFor those who did NOT ask for this topic, it seems fair to
Xexplain why your diet of hard-core technical information has been
Xinterrupted by a sermon!  As a motivater, we might consider why
Xsome programs are said by reviewers to have a "hot" feel (and
Xhence sell well!) while others are "confusing" or "boring".
X.PP
XAlan Kay has said that "user interface is theatre".  I think
Xwe may be able to take it further, and suggest that a successful
Xprogram works a bit of magic, persuading the user to suspend his
Xdisbelief and enter an imaginary world behind the screen, whether
Xit is the mathematical world of a spreadsheet, or the land of Pacman
Xpursued by ghosts.
X.PP
XA reader of a novel or science fiction story also suspends
Xdisbelief to participate in the work.  Bad grammar and clumsy plotting
Xby the author are jarring, and break down the illusion.  Similarly,
Xa programmer who fails to pay attention to making his interface
Xfast and consistent will annoy the user, and distract him from
Xwhatever care has been lavished on the functional core of the program.
X.SH CREDIT WHERE IT'S DUE
XBefore launching into the discussion
Xof user interface, I should mention that the general treatment and
Xmany of the specific research results are drawn from Card, Newell,
Xand Moran's landmark book on the topic, which is cited at the end
Xof the article.  Any errors in interpretation and application to
XGEM and the ST are entirely my own, however.
X.SH FINGERTIPS
XWe'll start right at the user's fingers with the
Xbasic equation governing positioning of the mouse, Fitt's Law,
Xwhich is given as
X.sp 1
X.ce 1
XT = I * LOG2( D / S + .5)
X.sp 1
Xwhere T is the amount of time to move to a target, D is the distance
Xof the target from the current position, and S is the size of the
Xtarget, stated in equivalent units.  LOG2 is the base 2 (binary)
Xlogarithm function, and I is a proportionality constant, about
X100 milliseconds per bit, which corresponds to the human's "clock
Xrate" for making incremental movements.
X.PP
XWe can squeeze an amazing amount of information out of this
Xformula when attempting to speed up an interface.  Since motion time
Xgoes up with distance, we should arrange the screen with the
Xusual working area near the center, so the mouse will have to move
Xa smaller distance on average from a selected object to a menu or
Xpanel.  Likewise, any items which are usually used together should
Xbe placed together.
X.PP
XThe most common operations will have the greater impact on
Xspeed, so they should be closest to the working area and perhaps
Xlarger than other icons or menu entries.  If you want to have
Xall other operations take about the same time, then the targets
Xfarthest from the working area should be larger, and those closer
Xmay be proportionately smaller.
X.PP
XConsider also the implications for dialogs.  Small check boxes
Xare out.  Large buttons which are easy to hit are in.  There should
Xbe ample space between selectable items to allow for positioning
Xerror.  Dangerous options should be widely separated from common
Xselections.
X.SH MUSCLES
XAnyone who has used the ST Desktop for any period
Xof time has probably noticed that his fingers now know where to find
Xthe File menu.  This phenomenon is sometimes called "muscle memory",
Xand its rate of onset is given by the Power Law of Practice:
X.sp 1
X.ce 1
XT(n) = T(1) * n ** (-a)
X.sp 1
Xwhere T(n) is the time on the nth trial, T(1) is the time on the
Xfirst trial, and a is approximately 0.4.  (I have appropriated
X** from Fortran as an exponentiation operator, since C lacks one.)
X.PP
XThis first thing to note about the Power Law is that it only
Xworks if a target stays in the same place!  This should be a potent
Xargument against rearranging icons, menus, or dialogs without some
Xexplicit request by the user.  The time to hit a target which moves
Xaround arbitrarily will always be T(1)!
X.PP
XIn many cases, the Power Law will also work for sequences of
Xoperations to even greater effect.  If you are a touch typist, you
Xcan observe this effect by comparing how fast you can enter "the"
Xin comparison to three random letters.  We'll come back shortly
Xto consider what we can do to encourage this phenomenon.
X.SH EYES
XJust as fingers are the way the user sends data to the
Xcomputer, so the eyes are his channel from the machine.  The rate
Xat which information may be passed to the user is determined by
Xthe "cycle time" of his visual processor.  Experimental results
Xshow that this time ranges between 50 and 200 milliseconds.
X.PP
XEvents separated by 50 milliseconds or less are always
Xperceived as a single event.  Those separated by more than 200
Xmilliseconds are always seen as separate.  We can use these
Xfacts in optimizing user of the computer's power when driving the
Xinterface.
X.PP
XSuppose your application's interface contains an icon which
Xshould be inverted when the mouse passes over it.  We now know
Xthat flipping it within one twentieth of a second is necessary
Xand sufficient.  Therefore, if a "first cut" at the program achieves
Xthis performance, there is no need for further optimization, unless
Xyou want to interleave other operations.  If it falls short, it will
Xbe necessary to do some assembly coding to achieve a smooth feel.
X.PP
XOn the other hand, two actions which you want to appear distinct
Xor convey two different pieces of information must be separated
Xby an absolute minimum of a fifth of a second, even assuming that
Xthey occur in an identical location on which the user's attention
Xis already focused.
X.PP
XWe are able to influence the visual processing rate within the
X50 to 200 millisecond range by changing the intensity of the stimulus
Xpresented.  This can be done with color, by flashing a target, or
Xby more subtle enhancements such as bold face type.  For instance,
Xmost people using GEM soon become accustomed to the "paper white"
Xbackground of most windows and dialogs.  A dialog which uses a
Xreverse color scheme, white letters on black, is visually shocking
Xin its starkness, and will immediately draw the user's eyes.
X.PP
XIt should be quickly added that stimulus enhancement will only
Xwork when it unambiguously draws attention to the target.  Three or
Xfour blinking objects scattered around the screen are confusing, and
Xworse than no enhancement at all!
X.SH SHORT-TERM MEMORY
XBoth the information gathered by the eyes
Xand movement commands on their way to the hand pass through short-term
Xmemory (also called working memory).  The amount of information which
Xcan be held in short-term memory at any one time is limited.  You can
Xdemonstrate this limit on yourself by attempting to type a sheet of
Xrandom numbers by looking back and forth from the numbers to the
Xscreen.  If you are like most people, you will be able to remember
Xbetween five and nine numbers at a time.  So universal is this
Xfinding that it is sometimes called "the magic number seven, plus
Xor minus two".
X.PP
XThis short-term capacity sets a limit on the number of choices
Xwhich the user can be expected to grasp at once.  It suggests that
Xthe number of independent choices in a menu, for instance, should
Xbe around seven, and never exceed nine.  If this limit is violated,
Xthen the user will have to take several glances, with pauses to
Xthink, in order to make a choice.
X.SH CHUNKING
XThe effective capacity of short-term memory can be
Xincreased when several related items are mentally grouped as a "chunk".
XHumans automatically adopt this strategy to save themselves time.
XFor instance, random numbers had to be used instead of text in the
Xexample above, because people do not type their native language as
Xindividual characters.  Instead, they combine the letters into words
Xand remember these chunks instead.  Put another way, the characters
Xare no longer considered as individual choices.
X.PP
XA well designed interface should promote the use of chunking
Xas a strategy by the user.  One easy way is to gather together
Xrelated options in a single place.  This is one reason that like
Xcommands are grouped into a single menu which is hidden except for
Xits title.  If all of the menu options were "in the open", the user
Xwould be overwhelmed with dozens of alternatives at once.  Instead, a
X"Show Info" command, for instance, becomes two chunks: pick File
Xmenu, then pick Show.
X.PP
XSometimes the interface can accomplish the chunking for the user.
XConsider the difference between a slider bar in a GEM program, and
Xa three digit entry field in a text mode application.  Obviously,
Xthe GEM user has fewer decisions to make in order to set the associated
Xvariable.
X.SH THINK!
XWhile we are puttering around trying to speed up
Xthe keyboard, the mouse, and the screen, the user is actually
Xtrying to get some work done.  We need to back off now, and
Xlook at the ways of thinking, or cognitive processes, that go into
Xaccomplishing the job.
X.PP
XThe user's goal may be to enter and edit a letter, to retrieve
Xinformation from a database, or simply draw a picture, but it
Xprobably has very little to do with programming.  In fact, the
XProblem Space Principle says that the task can be described as
Xa set of states of knowledge, a set of operators and associated
Xconstraints for changing the states, and the knowledge to
Xchoose the appropriate operator, which resides in the user's head.
X.PP
XThose with a background in systems theory can consider this
Xas a somewhat abstract, but straightforward, statement in terms of
Xstate variables and operators.  A programmer might compare the
Xknowledge states to the values of variables, the operators to
Xarithmetic and logic operations, the constraints to the rules of
Xsyntax, and the user's knowledge to the algorithm embodied by a
Xprogram.
X.SH ARE WE NOT MEN?
XA rational person will try to attain his
Xgoals (get the job done) by changing the state of his problem space
Xfrom its initial state to the goal state.  The initial state,
Xfor instance, might be a blank word processor screen.  The desired
Xfinal state is to have a completed business letter on the screen.
X.PP
XThe Rationality Principle says that the user's behavior in
Xtyping, mousing, and so on, can be explained by considering the
Xtasks required to achieve the goal, the operators available to
Xcarry out the tasks, and the limitations on the user's knowledge,
Xobservations, and processing capacity.  This sounds like the
Xtypical user of a computer program must spend a good deal of time
Xscratching his head and wondering what to do next.  In fact, one
Xof Card and Moran's key results is that this is NOT what takes place.
X.PP
XWhat happens, in fact, is that the trained user strikes a sort
Xof "modus vivendi" with his tool and adopts a set of repetitive,
Xtrained behavior patterns as the best way to get the job done.
XHe may go so far as to ignore some functions of the program in
Xorder to set up a reliable pattern.  What we are looking for is a
Xway of measuring and predicting the "quality" of this trained
Xbehavior.  Since using computers is a human endeavor, we should
Xconsider not only the speed with which the task is completed, but
Xthe degree of annoyance or pleasure associated with the process.
X.PP
XCard and Moran constructed a series of behavioral models which
Xthey called GOMS models, for Goals-Operators-Methods-Selection.
XThese models suggested that in the training process the user
Xlearned to combine the basic operators in sequences (chunks!)
Xwhich then became methods for reaching the goals.  Then these
Xfirst level methods might be combined again into second level
Xmethods, and so forth, as the learning progressed.
X.PP
XThe GOMS models were tested in a lengthy series of trials
Xat Xerox PARC using a variety of word processing software.  (Among
Xthe subjects of these experiments were the inventors of
Xthe windowing methods used in GEM!)  The results were again
Xsurprising: the level of detail in the models was really unimportant!
X.PP
XIt turned out to be sufficient to merely count up the number
Xof keystrokes, mouse movements, and thought intervals required
Xby each task.  After summing up all of the tasks, any extra time
Xfor the computer to respond, or the user to move his hands from
Xkeyboard to mouse, or eyes from screen to printed page is added in.
XThis simplified version is called the Keystroke-Level Model.
X.PP
XAs an example of the Keystroke Model, consider the task of
Xchanging a mistyped letter on the screen of a GEM word processor.
XThis might be broken down as follows: 1) find the letter on the screen;
X2) move hand to mouse; 3) point to letter; 4) click mouse button;
X5) move hand to keyboard; 6) strike "Delete" key; 7) strike key
Xfor new character.
X.PP
XThe sufficiency of the Keystroke Model is great news for our
Xattempt to design faster interfaces.  It says we can concentrate
Xour efforts on minimizing the number of total actions to be taken,
Xand making sure that each action is as fast as possible.  We have
Xalready discussed some ways to speed up the mouse and keyboard
Xactions, so let's now consider how to speed up the thought intervals,
Xand cut the number of actions.
X.PP
XOne way to cut down "think time" is to make sure that the
Xcapacity of short-term memory is not exceeded during the course of
Xa task.  For example, the fix-a-letter task described above required
Xthe user to remember 1) his place in the overall job of typing the
Xdocument; 2) the task he is about to perform; 3) where the bad
Xcharacter appeared, and 4) what the new character was.  When this
Xtotal of items creeps toward seven, the user often loses his place
Xand commits errors.
X.PP
XYou can appreciate the ubiquity of this problem by considering
Xhow many times you have made mistakes nesting parentheses,
Xor had to go back to count them, because too many things happened
Xwhile typing the line to remember the nesting levels. The moral is that
Xoperations with long strings of operands should be avoided when
Xdesigning an interface.
X.PP
XThe single most important factor in making an interface
Xcomfortable to use is increasing its predictability, and
Xdecreasing the amount of indecision present at each step during
Xa task.  There is (inevitably) an Uncertainty Principle which
Xrelates the number of choices at each step to the associated
Xtime for thought:
X.sp 1
X.ce 1
XT = I * LOG2 ( N + 1)
X.sp 1
Xwhere LOG2 is the binary logarithm function, N is the number of
Xequally probable choices, and I is a constant of approximately
X140 msec/bit.  When the alternates are not equally probable, the
Xfunction is more complex:
X.sp 1
X.ce 1
XT = I * SUM-FOR-i-FROM-1-TO-N (P(i) * LOG2( 1 / P(i) + 1) )
X.sp 1
Xwhere the P(i) are the probabilities of each of the choices (which
Xmust sum to one).  (SUM-FOR-i... is the best I can do for a sigma
Xoperator on-line!)  Those of you with some information theory
Xbackground will recognize this formula as the entropy of
Xthe decision; we'll come back to that later.
X.PP
XSo what can we learn from this hash?  It turns out, as we might
Xexpect, that we can decrease the decision time by making some
Xof the user's choices more probable than others.  We do that by
Xmeans of feedback cues from the interface.
X.PP
XThe important of reliable, continuous meaningful feedback
Xcannot be emphasized enough.  It helps the beginner learn the system,
Xand its predictability makes the program comfortable for the expert.
XPrograms with no feedback, or unreliable cues, produce confusion,
Xdissonance, and frustration in the user.
X.PP
XThis principle is so important that I going to give several
Xexamples from common GEM practice.  The Desktop provides several
Xinstances.  When an object is selected and a menu drops down, only
Xthose choices which are legal for the object are in black.  The
Xothers are dimmed to grey, and are therefore removed from the
Xdecision.  When a pick is made from the menu, the bar entry remains
Xblack until the operation is complete, reassuring the user that
Xthe correct choice was made.  In both the Desktop and the RCS,
Xitems which are double-clicked open up with a "zoom box" from
Xthe object, again showing that the right object was picked.
X.PP
XOther techniques are useful when operator icons are exposed on
Xthe screen.  When an object is picked, the legal operations might
Xbe outlined, or the bad choices might be dimmed.  If the screen
Xflashing produced by this is objectionable, the legal icons can
Xbe made mouse sensitive, so they will "light up" when the cursor
Xpasses over - again showing the user which choices are legal.
X.PP
XThe desire for feedback is so strong that it should be provided
Xeven while the computer is doing an operation on its own.  The hour
Xglass mouse form is a primitive example of this.  More sophisticated
Xare "progress indicators" such as animated thermometer bars,
Xclocks, or text displays of the processing steps.  The ST Desktop
Xprovides examples in the Format and Disk Copy functions.  The purpose
Xof all of these is to reassure the user that the operation is
Xprogressing normally.  Their lack can lead to amusing spectacles
Xsuch as secretaries leaning over to hear if their disk drives are
Xworking!
X.PP
XAnother commonly overlooked feature is error prevention and
Xcorrection.  Card and Moran's results showed that in order to go
Xfaster, people will tolerate error rates of up to 30% in their
Xwork.  Any program which does not give a fast way to fix mistakes
Xwill be frustrating indeed!
X.PP
XThe best way to cope with an error is to "make it didn't happen",
Xto quote a common child's phrase.  The same feedback methods
Xdiscussed above are also effective in preventing the user from
Xpicking inappropriate combinations of objects and operations.
XReplacement of numeric type-ins with sliders or other visual
Xcontrols eliminates the common "Range Error".  The use of radio
Xbuttons prevents the user from picking incompatible options.
XWhen such techniques are used consistently, the beginner also
Xgains confidence that he may explore the program without blundering
Xinto errors.
X.PP
XOnce an error has occured, the best solution is to have an
X"inverse operation" immediately available.  For instance, the way
Xto fix a bad character is to hit the backspace key.  If a line is
Xinadvertantly deleted, there should be a way to restore it.
X.PP
XSometimes the mechanics of providing true inverses are
Ximpractical, or end up cluttering the interface themselves.  In
Xthese cases, a global "Undo" command should be provided to
Xreverse the effect of the last operation, no matter what it was.
X.SH OF MODES AND BANDWIDTH
XNow I am going to depart from
Xthe Card, Newell and Moran thread of discussion to consider
Xhow we can minimize the number of operations in a task by
Xaltering the modes of the interface.  Although "no modes" has
Xbeen a watchword of Macintosh developers, the term may need
Xdefinition for Atarians.
X.PP
XSimply stated, a mode exists any time you cannot get to
Xall of the capabilities of the program without taking some
Xintermediate step.  Familiar examples are old-style "menu-driven"
Xprograms, in which user must make selections from a number of
Xnested menus in order to perform any operation.  The options
Xof any one menu are unavailable from the others.
X.PP
XRecall that the user is trying to accomplish work in his
Xown problem space, by altering its states.  A mode in the
Xprogram adds additional states to the problem space, which he is
Xforced to consider in order to get the job done.  We might call
Xan interface which is completely modeless "transparent", because it
Xadds no states between the user and his work.  One of the best
Xexamples of a transparent program is the 15-puzzle in the Macintosh
Xdesk accessory set.  The problem space of rearranging the tiles
Xis identical between the program and a physical puzzle.
X.PP
XUnfortunately, most programmers find themselves forced to
Xput modes of some sort into their programs.  These often arise
Xdue to technological limitations, such as memory space, screen
X"real estate", or performance limitations of peripherals.  The
Xquestion is how the modes can be made least offensive.
X.PP
XI will make the general claim that the frustration which a
Xmode produces is directly proportional to the amount of the user's
Xbandwidth which it consumes.  In other words, we need to consider
Xhow many keystrokes, mouse clicks, eye movements, and so on, are
Xgoing into manipulating the true problem states, and how many
Xare being absorbed by the modes of the program.  If the interface
Xis wasting a large amount of the user's effort, it will be perceived
Xas slow and annoying.
X.PP
XHere we can consider again the hierarchy of goals and methods
Xwhich the user employs.  When the mode is low in the hierarchy,
Xand close to the user's "fingertips", it is encountered the most
Xfrequently.  For instance, consider how frustrating it would be
Xto have to hit a function key before typing in each character!
X.PP
XThe "menu-driven" style of programs mentioned above are
Xalmost as bad, since usually only one piece of information is
Xcollected at each menu.  Such a program becomes a labyrinth of
Xstates better suited to an adventure game!
X.PP
XThe least offensive modes are found at the higher, goal
Xrelated levels of the hierarchy.  The better they align with
Xchanges in the state of the original problem, the more they
Xare tolerated.  For example, a word processing program might
Xhave one screen layout for program editing, another for writing
Xletters, and yet another while printing the documents.  A
Xmulti-function business package might have one set of menus for
Xthe spreadsheet, another for a graphing module, and a third
Xfor a database.
X.PP
XIn some cases the problem solved by the program has convenient
X"fracture lines" which can be used to define the modes.  An
Xexample in my own past is the RCS, where the editing of each
Xtype of resource tree forms its own mode, with each of the modes
Xnested within the overall mode and problem of composing the
Xentire resource tree.
X.SH  TO DO IS TO BE!
XAny narrative description of user interface
Xis bound to be lacking.  There is no way text can convey the vibrancy
Xand tactile pleasure of a good interface, or the sullen boredom
Xof a bad one.  Therefore, I encourage you to experiment.  Get out
Xyour favorite arcade game and see if you can spot some of the
Xelements I have described.  Dig into your slush pile for the most
Xannoying program you have ever seen, run it and see if you can see
Xmistakes.  How would you fix them?  Then... go do it to your own
Xprogram!
X.SH AMEN...
XThis concludes the sermon.  I'd like some Feedback
Xas to whether you found this Boring Beyond Belief or Really Hot
XStuff.  If enough people are interested, homily number two will
Xappear a few episodes from now.   The very next installment of ST
XPRO GEM will go back to basics to explore VDI drawing primitives.
XIn the meantime, you might investigate some of the Good Books on
Xinterface design referenced below.
X.br
X.ne 4
X.bold 1
XREFERENCES
X.sp 1
X.in +4
XStuart K. Card, Thomas P. Moran, and Allen
XNewell, THE PSYCHOLOGY OF HUMAN-COMPUTER INTERACTION, Lawrence
XErlbaum Associates, Hillsdale, New Jersey, 1983.
X.br
X(Fundamental
Xand indispensible.  The volume of experimental results make it
Xweighty.  The Good Parts are at the beginning and end.)
X.sp 1
X"Macintosh User Interface Guidelines", in INSIDE MACINTOSH,
XApple Computer, Inc., 1984.
X.br
X(Yes, Atarians, we have something to
Xlearn here.  Though not everything "translates", this is a fine
Xpiece of principled design work.  Read and appreciate.)
X.sp 1
XJames D. Foley, Victor L. Wallace, and Peggy Chan, "The
XHuman Factors of Computer Graphics Interaction Techniques",
XIEEE Computer Graphics (CG & A), November 1984, pp. 13-48.
X.br
X(A good overview, including higher level topics which I have
Xpostponed to a later article.  Excellent bibliography.)
X.sp 1
XJ. D. Foley and A. Van Dam, FUNDAMENTALS OF INTERACTIVE
XCOMPUTER GRAPHICS, Addison Wesley, 1984, Chapters 5 and 6.
X.br
X(If you can't get the article above, read this.  If you are designing
Xgraphics apps, buy the whole book!  Staggering bibliography.)
X.sp 1
XBen Schneidermann, "Direct Manipulation: A Step Beyond
XProgramming Languages", IEEE Computer, August 1983, pp. 57-69.
X.br
X(What do Pacman and Visicalc have in common?  Schneidermann's
Xanalysis is vital to creating hot interfaces.)
X.in -4
X.!
X.!
X.!*****************************************************************************
X.!*									      *
X.!*				End Part 8				      *
X.!*									      *
X.!*****************************************************************************
SHAR_EOF
if test 25511 -ne "`wc -c 'wind8.prf'`"
then
	echo shar: error transmitting "'wind8.prf'" '(should have been 25511 characters)'
fi
echo shar: extracting "'wind9.prf'" '(21188 characters)'
if test -f 'wind9.prf'
then
	echo shar: over-writing existing file "'wind9.prf'"
fi
sed 's/^X//' << \SHAR_EOF > 'wind9.prf'
X.!****************************************************************************
X.! 
X.! ANTIC PUBLISHING INC., COPYRIGHT 1985.  REPRINTED BY PERMISSION.
X.!
X.! ** Professional GEM ** by Tim Oren
X.!
X.! Proff File by ST enthusiasts at
X.! Case Western Reserve University
X.! Cleveland, Ohio
X.! uucp : decvax!cwruecmp!bammi
X.! csnet: bammi@case
X.! arpa : bammi%case@csnet-relay
X.! compuserve: 71515,155
X.!
X.!****************************************************************************
X.!
X.!
X.!****************************************************************************
X.!
X.!			Begin Part 9
X.!
X.!****************************************************************************
X.!
X.PART IX VDI Graphics: Lines and Solids
X.PP
XThis  issue  of ST PRO GEM is the first in a  series  of  two
Xwhich  will explore the fundamentals of VDI graphics  output.   In
Xthis installment, we will take a look at the commands necessary to
Xoutput simple graphics such as lines,  squares and circles as well
Xas  more complex figures such as polygons.   The following episode
Xwill  take a first look at graphics text output,  with an emphasis
Xon  ways  to  optimize its drawing speed.   It will  also  include
Xanother  installment  of ONLINE Feedback.   As usual,  there is  a
Xdownload  with  this column.   You should find it under  the  name
XGEMCL9.C in DL3 of ATARI16 (PCS-58).
X.SH A  BIT  OF HISTORY
XOne  of  the reasons that the VDI can  be  confusing  is  that
Xdrawing anything at all,  even a simple line,  can involve setting
Xaround four different VDI parameters before making the draw  call!
X(Given  the state of the GEM documents,  just FINDING them can  be
Xfun!)  Looking backwards a bit sheds some light on why the VDI  is
Xstructured this way,  and also gives us a framework for organizing
Xa discussion of graphics output.
X.PP
XThe GEM VDI closely follows the so-called GKS standard, which
Xdefines  capabilities  and calling sequences  for  a  standardized
Xgraphic  input/output system.   GKS is itself an evolution from an
Xearly system called "Core".   Both of these standards were born in
Xthe  days  when  pen plotters,  vectored  graphics  displays,  and
Xminicomputers  were  the  latest items.   So,  if you  wonder  why
Xsetting  the drawing pen color is a separate command,  just  think
Xback  a  few  years when it actually meant  what  it  says!   (The
Xcynical   may   choose   instead  to  ponder   the   benefits   of
Xstandardization.)
X.PP
XWhen  doing  VDI  output,  it helps if you pretend  that  the
Xdisplay screen really is a plotter or some other separate  device,
Xwhich  has  its own internal parameters which you can set  up  and
Xread  back.   The class of VDI commands called Attribute Functions
Xlet  you set the parameters.   Output Functions cause the "device"
Xto  actually  draw  someone once it is  configured.   The  Inquire
XFunctions let you read back the parameters if necessary.
X.PP
XThere  are two parameters which are relevant no  matter  what
Xtype of object you are trying to draw.   They are the writing mode
Xand  the clipping rectangle.   The writing mode is similar to that
Xdiscussed in the column on raster operations.   It determines what
Xeffect the figure you are drawing will have on data already on the
Xscreen.  The writing mode is set with the call:
X.FB vswr_mode()
Xvswr_mode(vdi_handle, mode);
X.FE
XVdi_handle,  here  and  below,  is the  handle  obtained  from
Xgraf_handle at the beginning of the program.  Mode is a word which
Xmay be one of:
X.sp 1
X.in +8
X1 - Replace Mode
X.br
X2 - Transparent Mode
X.br
X3 - XOR mode
X.br
X4 - Reverse Transparent Mode
X.in -8
X.PP
XIn  replace mode,  whatever is on the screen is  overwritten.
XIf  you are writing characters,  this means the background of each
Xcharacter cell will be erased.
X.PP
XIn  transparent  mode,  only  the pixels directly  under  the
X"positive"  part  of the image,  that is,  where 1-bits are  being
Xwritten, will be changed.  When writing characters, the background
Xof the cell will be left intact.
X.PP
XIn XOR mode,  an exclusive or is performed between the screen
Xcontents and what is being written.   The effect is to reverse the
Ximage under areas where a 1-bit occurs.
X.PP
XReverse transparent is like transparent,  but with a "reverse
Xcolor  scheme".   That  is,  only  places where a 0-bit is  to  be
Xput   are  changed  to  the  current  writing  color.    When  you
Xwrite  characters in reverse transparent (over white),  the effect
Xis reverse video.
X.PP
XThe  other  common parameter is the clipping  rectangle.   It
Xdefines the area on the screen where the VDI is permitted to draw.
XAny output which would fall outside of this area is ignored; it is
Xeffectively a null operation.   The clip rectangle is set with the
Xcall:
X.FB vs_clip()
Xvs_clip(vdi_handle, flag, pxy);
X.FE
XPxy is a four-word array.   Pxy[0] and pxy[1] are the X  and  Y
Xscreen coordinates,  respectively,  of one corner of your clipping
Xrectangle.    Pxy[2]  and  pxy[3]  are  the  coordinates  of   the
Xdiagonally opposite corner of the rectangle.   (When working  with
Xthe  AES,  use  of  a  GRECT to define  the  clip  is  often  more
Xconvenient.  The routine set_clip() in the download does this.)
X.PP
XFlag is set to TRUE if clipping is to be used.  If you set it
Xto  FALSE,  the  entire  screen is assumed to be fair  game.
X.PP
XNormally,  you should walk the rectangle list for the current
Xwindow to obtain your clipping rectangles.  (See ST PRO GEM #2 for
Xmore details.)  However, turning off the clip speeds up all output
Xoperations,  particularly text.  You may do this ONLY when you are
Xabsolutely certain that the figure you are drawing will not extend
Xout of the top-most window, or out of a dialog.
X.SH THE LINE FORMS ON THE LEFT
XThe  VDI  line  drawing  operations  include  polyline,  arc,
Xelliptical  arc,  and rounded rectangle.   I'll first look at  the
XAttribute Functions for line drawing,  then go through the drawing
Xprimitives themselves.
X.PP
XThe  most  common used line attributes are color  and  width.
XThe color is set with:
X.FB vsl_color()
Xvsl_color(vdi_handle, color);
X.FE
Xwhere color is one of the standard VDI color  indices,  ranging
Xfrom  zero to 15.   (As discussed in column #6,  the  color  which
Xactually appears will depend on the pallette setting of your ST.)
X.PP
XThe  line width may only be set to ODD positive  values,  for
Xreasons  of  symmetry.   If you try to set an even value,  the VDI
Xwill take the next lower odd value.  The call is:
X.FB vsl_width()
Xvsl_width(vdi_handle, width);
X.FE
XThe  two  less  used line parameters are the  end  style  and
Xpattern.   With  the  end style you can cause the output  line  to
Xhave rounded ends or arrowhead ends.  The call is:
X.FB vsl_ends()
Xvsl_ends(vdi_handle, begin_style, end_style);
X.FE
XBegin_style  and end_style are each words which  may  have  the
Xvalues zero for square ends (the default),  one for arrowed  ends,
Xor  two  for  rounded ends.   They determine the  styles  for  the
Xstarting and finishing ends of the line, respectively.
X.PP
XThe line pattern attribute can select dotted or dashed  lines
Xas  well  as more complicated patterns.   Before  continuing,  you
Xshould  note one warning:  VDI line output DOES NOT compensate for
Xpixel aspect ratio.  That is, the dashes on a line will look twice
Xas long drawn vertically on a medium-res ST screen as they do when
Xdrawn horizontally.  The command for setting the pattern is:
X.FB vsl_type()
Xvsl_type(vdi_handle, style);
X.FE
XStyle  is  a word with a value between 1  and  7.   The  styles
Xselected are:
X.sp 1
X.in +8
X1 - Solid (the default)
X.br
X2 - Long Dash
X.br
X3 - Dot
X.br
X4 - Dash, Dot
X.br
X5 - Dash
X.br
X6 - Dash, Dot, Dot
X.br
X7 - (User defined style)
X.in -8
X.PP
XThe  user  defined  style is determined  by  a  16-bit  pattern
Xsupplied  by the application.   A one bit in the pattern  turns  a
Xpixel on, a zero bit leaves it off.  The pattern is cycled through
Xrepeatedly,  using the high bit first.  To use a custom style, you
Xmust make the call:
X.FB vsl_udsty()
Xvsl_udsty(vdi_handle, pattern);
X.FE
Xbefore doing vsl_type().
X.PP
XAs  I  mentioned  above,   the  line  type  Output  Functions
Xavailable are polyline,  circular and ellliptical arc, and rounded
Xrectangle.   Each  has  its own calling sequence.   The call for a
Xpolyline is:
X.FB v_pline()
Xv_pline(vdi_handle, points, pxy);
X.FE
XPoints tells how many vertices will appear on the polyline.  For
Xinstance,  a  straight  line has two vertices:  the  end  and  the
Xbeginning.   A closed square would have five,  with the first  and
Xlast  identical.    (There  is  no  requirement  that  the  figure
Xdescribed be closed.)
X.PP
XThe pxy array contains the X and Y raster coordinates for the
Xvertices,  with a total of 2 * points entries.   Pxy[0] and pxy[1]
Xare the first X-Y pair, and so on.
X.PP
XIf you happen to be using the XOR drawing mode, remember that
Xdrawing  twice  at  a point is equivalent to no  drawing  at  all.
XTherefore,  for  a figure to appear closed in XOR mode,  the final
Xstroke  should actually stop one pixel short of the origin of  the
Xfigure.
X.PP
XYou  may  notice  that  in the GEM  VDI  manual  the  rounded
Xrectangle  and arc commands are referred to as  GDPs  (Generalized
XDrawing Primitives).  This denotation is historical in nature, and
Xhas  no effect unless you are writing your own VDI bindings.
X.PP
XThe  rounded rectangle is nice to use for customized  buttons
Xin  windows and dialogs.   It gives a "softer" look to the  screen
Xthan the standard square objects.  The drawing command is:
X.FB v_rbox()
Xv_rbox(vdi_handle, pxy);
X.FE
XPxy  is  a  four word array  giving  opposite  corners  of  the
Xrectangle,  just as for the vs_clip() call.   The corner  rounding
Xoccurs  within  the  confines of  this  rectangle.   Nothing  will
Xprotrude  unless  you specify a line thickness greater  than  one.
XThe  corner rounding is approximately circular;  there is no  user
Xcontrol over the degree or shape of rounding.
X.PP
XBoth the arc and elliptical arc commands use a curious method
Xof  specifying  angles.   The units are tenths of degrees,  so  an
Xentire  circle is 3600 units.   The count starts at ninety degrees
Xright of vertical, and proceeds counterclockwise.  This means that
X"3 o'clock" is 0 units,  "noon" is 900 units,  "9 o'clock" is 1800
Xunits, and 2700 units is at "half-past".  3600 units take you back
Xto "3 o'clock".
X.PP
XThe command for drawing a circular arc is:
X.FB v_arc()
Xv_arc(vdi_handle, x, y, radius, begin, end);
X.FE
XX  and y specify the raster coordinates of the  center  of  the
Xcircle.   Radius specifies the distance from center to all  points
Xon the arc.   Begin and end are angles given in units as described
Xabove,  both with values between 0 and 3600.   The drawing of  the
Xarc  ALWAYS  proceeds  counterclockwise,   in  the  direction   of
Xincreasing arc number.   So values of 0 and 900 for begin and  end
Xwould  draw  a  quarter circle from  "three  o'clock"  to  "noon".
XReversing  the values would draw the other three quarters  of  the
Xcircle.
X.PP
XA  v_arc()  command  which specifies a  "full  turn"  is  the
Xfastest  way to draw a complete circle on the screen.   Be warned,
Xhowever,  that  the circle drawing algorithm used in the VDI seems
Xto  have  some  serious  shortcomings at  small  radii!   You  can
Xexperiment  with  the  CIRCLE primitive in  ST  Logo,  which  uses
Xv_arc(), to see what I mean.
X.PP
XNotice  that if you want an arc to strike one or more  given
Xpoints on the screen,  then you are in for some trigonometry.   If
Xyour  math  is  a  bit  rusty,  I highly  recommend  the  book  "A
XProgrammer's  Geometry",  by  Bowyer  and Woodwark,  published  by
XButterworths (London, Boston, Toronto).
X.PP
XFinally, the elliptical arc is generated with:
X.FB v_ellarc()
Xv_ellarc(vdi_handle, x, y, xrad, yrad, begin, end);
X.FE
XX,  y,  begin, and end are just as before.  Xrad and yrad give the
Xhorizontal and vertical radii of the defining ellipse.  This means
Xthat  the distance of the arc from center will be yrad  pixels  at
X"noon"  and  "half-past",  and it will be xrad pixels at "3 and  9
Xo'clock".  Again, the arc is always drawn counterclockwise.
X.PP
XThere  are  a  number  of approaches  to  keeping  the  VDI's
Xattributes "in sync" with the actual output operations.   Probably
Xthe  LEAST efficient is to use the Inquire Functions to  determine
Xthe  current  attributes.   For  this  reason,  I have  omitted  a
Xdiscussion of these calls from this column.
X.PP
XAnother  idea  is  to keep a local copy  of  all  significant
Xattributes, use a test-before-set method to minimize the number of
XAttribute  Functions which need to be called.   This puts a burden
Xon  the programmer to be sure that the local  attribute  variables
Xare correctly maintained.   Failure to do so may result in obscure
Xdrawing  bugs.   If  your  application employs  user  defined  AES
Xobjects, you must be very careful because GEM might call your draw
Xcode  in the middle of a VDI operation (particularly if  the  user
Xdefined objects are in the menu).
X.PP
XAlways  setting  the attributes is a simplistic  method,  but
Xoften   proves  most  effective.    The  routines  pl_perim()  and
Xrr_perim()  in the download exhibit this  approach.   Modification
Xfor  other  primitives  is straightforward.   This style  is  most
Xuseful  when  drawing  operations  are  scattered  throughout  the
Xprogram,  so that keeping track of the current attribute status is
Xdifficult.  Although inherently inefficient, the difference is not
Xvery  noticable if the drawing operation requested is itself  time
Xconsuming.
X.PP
XIn  many  applications,  such  as data graphing  programs  or
X"Draw"  packages,  the output operations are centralized,  forming
Xthe primary functionality of the code.   In this case,  it is both
Xeasy  and  efficient  to keep track of  attribute  status  between
Xsuccessive drawing operations.
X.SH SOLIDS
XThere  are  a wider variety of VDI  calls  for  drawing  solid
Xfigures.   They  include rectangle or  bar,  disk,  pie,  ellipse,
Xelliptical  pie,  filled rounded rectangle,  and filled  polygonal
Xarea.   Of course,  filled figure calls also have their own set of
Xattributes which you will need to set.
X.PP
XThe  fill color index determines what pen color will be  used
Xto draw the solid.  It is set with:
X.FB vsf_color()
Xvsf_color(vdi_handle, color);
X.FE
XColor is just the same as for line drawing.   A solid may  or
Xmay not have a visible border.  This is determined with the call:
X.FB vsf_perimeter()
Xvsf_perimeter(vdi_handle, vis);
X.FE
XVis is a Boolean.   If it is true,  the figure will be given  a
Xsolid one pixel outline in the current fill color index.   This is
Xoften  useful  to improve the appearance of solids  drawn  with  a
Xdithered fill pattern.  If vis is false, then no outline is drawn.
X.PP
XThere are two parameters which together determine the pattern
Xused  to  fill your figure.   They are called interior  style  and
Xinterior  index.   The style determines the general type of  fill,
Xand the index is used to select a particular pattern if necessary.
XThe style is set with the command:
X.FB vsf_interior()
Xvsf_interior(vdi_handle, style);
X.FE
Xwhere style is a value from zero through four.   Zero selects  a
Xhollow  style:  the  fill is performed in  color  zero,  which  is
Xusually  white.   Style one selects a solid fill with the  current
Xfill  color.   A style of two is called "pattern" and a  three  is
Xcalled "hatch", which are terms somewhat suggestive of the options
Xwhich can then be selected using the interior index.   Style  four
Xselects the user defined pattern, which is described below.
X.PP
XThe  interior  index is only significant for styles  two  and
Xthree. To set it, use:
X.FB vsf_style()
Xvsf_style(vdi_handle, index);
X.FE
X(Be careful here: it is very easy to confuse this call with the
Xone  above  due  to the unfortunate choice of  name.)   The  index
Xselects the actual drawing pattern.  The GEM VDI manual shows fill
Xpatterns corresponding to index values from 1 to 24 under style 2,
Xand  from  1 to 12 under style 3.   However,  some  of  these  are
Ximplemented  differently on the ST.   Rather than try to  describe
Xthem all here, I would suggest that you experiment.  You can do so
Xeasily  in  ST Logo by opening the Graphics  Settings  dialog  and
Xplaying with the style and index values there.
X.PP
XThe user defined style gives you some interesting options for
Xmulti-color fills.  It is set with:
X.FB vsf_udpat()
Xvsf_udpat(vdi_handle, pattern, planes);
X.FE
XPlanes  determines the number of color planes in  the  pattern
Xwhich  you  supply.   It  is  set to one  if  you  are  setting  a
Xmonochrome  pattern.   (Remember,  monochrome is  not  necessarily
Xblack).   It may be set to higher values on color systems: two for
XST medium-res mode, or four for low-res mode.  If you use a number
Xlower than four under low-res, the other planes are zero filled.
X.PP
XThe  pattern  parameter  is  an array of  words  which  is  a
Xmultiple  of  16 words long.  The pattern determined is 16  by  16
Xpixels,  with each word forming one row of the pattern.   The rows
Xare  arranged top to bottom,  with the most significant bit to the
Xleft.   If  you  have selected a multi-plane pattern,  the  entire
Xfirst plane is stored, then the second, and so on.
X.PP
XNote that to use a multi-plane pattern, you set the writing
Xmode  to replace using vswr_mode().   Since the each plane can  be
Xdifferent,  you can produce multi-colored patterns.   If you use a
Xwriting   color  other  than  black,   some  of  the  planes   may
X"disappear".
X.PP
XMost  of  the  solids Output Functions  have  analogous  line
Xdrawing commands.   The polyline command corresponds to the filled
Xarea primitive.  The filled area routine is:
X.FB v_fillarea()
Xv_fillarea(vdi_handle, count, pxy);
X.FE
XCount  and pxy are just the same as  for  v_pline().   If  the
Xpolygon  defined  by pxy is not closed,  then the VDI  will  force
Xclosure  with  a straight line from the last to the  first  point.
XThe  polygon may  be concave or self-intersecting.   If  perimeter
Xshow is on, the area will be outlined.
X.PP
XOne  note of caution is necessary for both  v_fillarea()  and
Xv_pline().   There is a limit on the number of points which may be
Xstored in pxy[].   This limit occurs because the contents of pxy[]
Xare copied to the intin[] binding array before the VDI is  called.
XYou  can  determine  the maximum number of  vertices  by  checking
Xintout[14] after using the extended inquire function vq_extnd().
X.PP
XFor  reasons unknown to this writer,  there are TWO different
Xfilled rectangle commands in the VDI.  The first is
X.FB vr_recfl()
Xvr_recfl(vdi_handle, pxy);
X.FE
XPxy is a four word array defining two opposite corners of  the
Xrectangle,  just  as  in  vs_clip().   Vr_recfl()  uses  the  fill
Xattribute settings, except that it NEVER draws a perimeter.
X.PP
XThe other rectangle routine is v_bar(), with exactly the same
Xarguments  as  vr_recfl().    The  only  difference  is  that  the
Xperimeter  setting  IS  respected.   These two  routines  are  the
Xfastest way to produce a solid rectangle using the VDI.   They may
Xbe  used in XOR mode with a BLACK fill color to quickly invert  an
Xarea  of  the screen.   You can improve the speed even further  by
Xturning off the clip (if possible), and byte aligning the left and
Xright edges of the rectangle.
X.PP
XSeparate commands are provided for solid circle and  ellipse.
XThe circle call is:
X.FB v_circle()
Xv_circle(vdi_handle, x, y, radius);
X.FE
Xand the ellipse command is:
X.FB v_ellipse()
Xv_ellipse(vdi_handle, x, y, xrad, yrad);
X.FE
XAll of the parameters are identical to those given  above  for
Xv_arc()  and v_ellarc().   The solid analogue of an arc is a  "pie
Xslice".  The VDI pie commands are:
X.FB v_pieslice()
Xv_pieslice(vdi_handle, x, y, radius, begin, end);
X.FE
Xfor a slice from a circular pie, and
X.FB v_ellpie()
Xv_ellpie(vdi_handle, x, y, xrad, yrad, begin, end);
X.FE
Xfor a slice from a "squashed" pie.   Again,  the parameters are
Xidentical  to  those in v_arc() and  v_ellarc().   The  units  and
Xdrawing  order  of angles are also the  same.   The  final  solids
XOutput Function is:
X.FB v_rfbox()
Xv_rfbox(vdi_handle, pxy);
X.FE
Xwhich draws a filled rounded rectangle.   The pxy array  defines
Xtwo  two  opposite  corners of the  bounding  box,  as  shown  for
Xvs_clip().
X.PP
XThe  issues involved in correctly setting the VDI  attributes
Xfor a fill operation are identical to those in drawing lines.  For
Xthose  who  want to employ the "always set" method,  I have  again
Xincluded  two  skeleton  routines in the download,  which  can  be
Xmodified as desired.
X.SH TO  BE  CONTINUED
XThis concludes the first part of our expedition  through  basic
XVDI  operations.   The  next  issue will tackle  the  problems  of
Xdrawing  bit mapped text at a reasonable speed.   This first  pass
Xwill  not attempt to tackle alternate or  proportional  fonts,  or
Xalternate font sizes.   Instead,  I will concentrate on techniques
Xfor  squeezing greater performance out of the standard  monospaced
Xsystem fonts.
X.!
X.!
X.!*****************************************************************************
X.!*									      *
X.!*				End Part 9				      *
X.!*									      *
X.!*****************************************************************************
SHAR_EOF
if test 21188 -ne "`wc -c 'wind9.prf'`"
then
	echo shar: error transmitting "'wind9.prf'" '(should have been 21188 characters)'
fi
#	End of shell archive
exit 0

-- 
					Jwahar R. Bammi
			       Usenet:  .....!decvax!cwruecmp!bammi
			        CSnet:  bammi@case
				 Arpa:  bammi%case@csnet-relay
			   CompuServe:  71515,155