[fa.info-mac] Macintosh Development Techniques

info-mac@uw-beaver (info-mac) (12/03/84)

From: Larry Rosenstein <lsr@apple.ARPA>
I want to solicit some input from the net community regarding Macintosh
development techniques.

I am working on a project at Apple that involves making Macintosh
development much easier.  The approach we are taking is similar to that
used in the Lisa Toolkit (if anyone is familiar with that).  Briefly, we
are developing an Expandable Application that implements the standard
Macintosh behavior (eg., printing, resizing/moving windows, handling desk
accessories, etc.).  Programmers make extensions to the Expandable
Application to add specific behavior (eg., drawing an image in the window).

What we try to do is figure out the best way to do a particular task (eg.,
scrolling), and implement it once in the Expandable Application where
everyone can take advantage of it.  I would like to hear: (1) any reactions
you have to this idea, and (more importantly) (2) any helpful hints/tricks
you have for implementing certain features or for debugging.

The following techniques will give you an idea of what I mean (and might be
useful in your own applications):

(1) Instead of reading in the menus into a global array (like the FILE
program does) use the GetMHandle trap, which takes in a menuID of a menu in
the menu bar and returns the handle.  (So far the Expandable Application
has not had to access an item of a menu NOT in the menu bar.)

(2) Calling EnableItem, CheckItem, etc. causes the menu to recompute its
size each time, which takes some time.  Before making these calls, replace
the menuProc by a HANDLE to a dummy procedure that does nothing (but has
the right interface).  Afterwards, you restore the original menuProc and
can call CalcMenuSize to compute the new menu size.  (You can skip the call
the CalcMenuSize if you are sure the menu didn't change size, which is
usually the case.)

(3) When moving the scroll bars (because the window changed size), don't
call HideControl/ShowControl.  Instead, set the clipping to a zero-sized
rectangle.  (Remember that you also need to invalidate the old and new
positions of the grow box.)

(4) When printing, send the spool file to the same volume as the document
(since the program disk is likely to be full and/or write-protected).  The
volume used for the spool file is specified in the iFileVol field of the
TPrJob record, which is described in the "Printing From Macintosh
Applications" section of Inside Macintosh.

I am interested in any comments you have.  I hope that my mailbox can stand
the strain! :-)

Larry Rosenstein
Apple Computer, Inc.

CSNET: lsr%Apple@CSNET-RELAY
UUCP: {nsc, dual, idi, voder}!apple!lsr

info-mac@uw-beaver (info-mac) (12/04/84)

From: Gustavo Fernandez <FERNANDEZ@SU-SCORE.ARPA>
In MacView, I found a problem of two subroutines calling a common routine.
The first caller and the callee both need a certain memory block accessed
by a handle, but the second caller doesn't need it. The first caller needs
to lock the handle, and so does the callee. The question is: does the callee
return with the handle locked (for the first caller) or unlocked (for the
second.)
     I solved this problem by defining two new routines: CHLock (Conditional
Handle Lock) and CHUnlock.
     PROCEDURE CHLock(H:Handle;VAR F:BOOLEAN);
     PROCEDURE ChUnLock(H:Handle;F:BOOLEAN);

     ChLock returns in its second parameter a flag which tells whether the\
handle was locked BEFORE the ChLock. It then unconditionally locks the handle.

    If the boolean flag in CHUnLock is FALSE, then this subroutine unlocks the
handle, else it is a no-op.

   Assuming that the flag is saved on the stack. CHLock and CHUnLock can be called
to any deapth as long as subroutines exit normally.
 
If anyone knows of a better solution, please tell me.
 
 
Another problem I had was dealing with the (often complex) issue of whether
meus were highlighted or not, and if so, which items within the menus were
enabled. I solved this problem by defining a resource type with an individual
resource for each possible combination. (which in my case depended solely on
which window was active (on top) at the time) The resource had the same format
as STR# where each "string" corresponded to a menu and has length (number of
items in menu)+1. The first character is the master control and further characters
control individual menu items. Characters ar E for enable, D for disable, and
. for leave alone. A single character line would simply perform the appropriate
action for the entire menu.
 
This data driven approach, while perhaps not time efficient is quite space
efficient when you want to disable lots of functions inappropriate for a
particular window.
 
-----------------------
 
I would like to hear more of these techniques should you receive any.
This would be a very interesting thread for experienced Mac programmers
on INFO-MAC
-------