Path: utzoo!attcan!uunet!cs.utexas.edu!usc!elroy.jpl.nasa.gov!mipl3!dfs059 From: dfs059@ipl.jpl.nasa.gov (Dan Stanfill) Newsgroups: comp.sys.mac.programmer Subject: Re: Color QuickDraw, PICT2's and the Clipboard Message-ID: <6577@ipl.jpl.nasa.gov> Date: 10 Aug 89 09:51:27 GMT Organization: Jet Propulsion Laboratory, Image Processing Lab Lines: 86 hpoppe@bierstadt.ucar.edu (Herb Poppe) asks how to get the palette for a PICT before drawing it with DrawPicture. I also struggled with this problem for a while, before I came up with the following (very ugly) solution. I thought my solution was pretty weird, but I was quite happy when I found out that the folks at NCSA use the exact same technique. If anyone knows a better technique, please post it! This technique applies to disk files, but could be extended to the clipboard as well. The secret is to use SetStdCProcs() to intercept calls to CopyBits(). I use the spooling technique described in IM-V as well, so my code looks like the following: SetStdCProcs(&myProcs); dstPort->grafProcs = (QDProcsPtr) &myProcs; myProcs.getPicProc = (Ptr)ReadPictData; if (srcPort == dstPort) myProcs.bitsProc = (Ptr)MyCopyBits; /* only for screen updates */ srcPort and dstPort are a bit of weirdness I use to check whether or not I am printing. Note that if you spool from disk you should use a buffering scheme to read in the pict file in a big chunk in ReadPictData(), otherwise it will be excruciatingly slow. You can then write MyCopyBits() to look something like the following: /************************************************************************/ pascal void MyCopyBits(srcBits, srcRect, dstRect, mode, maskRgn) PixMapPtr srcBits; Rect *srcRect, *dstRect; short mode; RgnHandle maskRgn; { PaletteHandle pal; CGrafPtr dstPort; CTabHandle ctab; GetPort(&dstPort); pal = GetPalette(dstPort); /* check to see if palette already exists */ if (pal == NIL) { ctab = srcBits->pmTable; if (ctab != NIL) { pal = NewPalette(256, ctab, pmTolerant, 0); FreeSomeColors(pal); SetPalette(dstPort, pal, TRUE); ActivatePalette(dstPort); } } StdBits(srcBits, srcRect, dstRect, mode, maskRgn); return; } /************************************************************************/ FreeSomeColors() is my own routine to keep any window from sucking up all 256 colors (this allows color menus, desktops, etc., to still look ok). Finally, after your call to DrawPicture(), be sure to reset the std procs: dstPort->grafProcs = NIL; The code above has a flaw; if a picture has more than one CopyBits call with more than one palette, only the first one is used. I find that most of the time that is ok, though. The only problem I have had is with the output from some scanner software, which, being pre-32-bit-quickdraw, draw 24 bit data as a series of three CopyBits with red, green, and blue ramps, respectively. If your pict file is a 32 bit pict, you won't get a color table, so you ought to handle that as well. The default palette works reasonably when you don't have any knowledge of the color content of an image. Good luck! Dan Stanfill Visualization and Earth Sciences Applications Group Image Processing and Applications and Development Section Jet Propulsion Laboratory dfs@flower.jpl.nasa.gov dan@dial.jpl.nasa.gov dfs059@ipl.jpl.nasa.gov