[comp.sys.mac] Hints from Heloise

dubois@uwmacc.UUCP (Paul DuBois) (12/13/86)

At odd intervals now and again one likes to make sure all windows are
updated properly without waiting for the usual event processing loop
to get around to it.  Example:  the standard PutFile dialog is put
on the screen to obtain an output file name.  One might ascertain that
the name is not legal (e.g., the file already exists but is of a
different type than the application wants to write), in which case
an alert typically is put up.  But if the windows are not updated,
you've got an alert in front of other windows which have this big ugly
white space where the PutFile dialog used to be.

TransSkel applications may avoid this kind of thing.  First the
code, then the explanation.

--- code ---

# include	"EventMgr.h"

/*
    Process any pending updates
*/

CheckUpdates ()
{
EventRecord event;

    if (!EventAvail (updateMask, &event))
        SkelWhoa ();
}


DoUpdates ()
{
int     mask;
ProcPtr bkGnd;

    SkelGetBackground (&bkGnd);     /* get current background proc */
    SkelGetEventMask (&mask);       /* and event mask */

    SkelBackground (CheckUpdates);  /* install new background & mask */
    SkelEventMask (updateMask);

    SkelMain ();                    /* handle updates only */

    SkelBackground (bkGnd);         /* restore old background & mask */
    SkelEventMask (mask);
}

--- explanation ---

A call to DoUpdates forces all updates to be processed.  This
works because of the structure of TransSkel's event processing loop
(SkelMain) and because of the interaction of SkelMain and the loop
terminator (SkelWhoa).

SkelMain processes events and routes them to the proper handler
procedures, but before it asks for an event, it calls any background
procedure the host may have installed.  The loop may be configured
to ask only for certain events.  In addition, SkelWhoa has the property
that it terminates only the most recent invocation of SkelMain.  This
means that SkelMain may be run recursively, or, in other words, that
event processing loops may be "stacked" on top of each other.

DoUpdates exploits this property in order to create a processing loop
that handles only updates.  First the current background procedure
and event mask are saved, so that they may be properly restored after
the updates have been taken care of.  Then the event mask is set to
ask only for updates, and a background procedure to check for the
existence of pending updates is installed.  Then SkelMain is called.

As long as there are update events pending, the background procedure
CheckUpdates does nothing, and SkelMain routes them to the proper
handlers.  When there aren't any more updates, CheckUpdates notices
this and tells SkelMain to quit (by calling SkelWhoa).  When SkelMain
returns to DoUpdates, the original event mask and background procedure
are restored.

The example may be generalized to any other event or combination of
events, of course.  (The code above requires TransSkel 1.02.)

---
Paul DuBois     UUCP: {allegra,ihnp4,seismo}!uwvax!uwmacc!dubois    |
                ARPA: dubois@easter                               --+--
                      dubois@rhesus                                 |
                                                                    |
"What is lacking cannot be counted." - Solomon the cladist
                                       (Ecclesiastes 1:15)