BufferedRefresh.mesa
Copyright Ó 1986, 1987, 1988, 1992 by Xerox Corporation. All rights reserved.
Contents: Builds up an abstraction of transparent layers onto which shapes can be drawn. Each layer may have a backing pixel map, in which case it need not be redrawn when other layers change. This scheme is used by Gargoyle and Solidviews.
Doug Wyatt, June 28, 1988 12:01:34 pm PDT
Bier, July 13, 1993 12:01 pm PDT
Michael Plass, March 25, 1992 11:50 am PST
Kenneth A. Pier, August 18, 1992 1:56 pm PDT
DIRECTORY
Imager, BufferedRefreshTypes, Real;
BufferedRefresh: CEDAR DEFINITIONS = BEGIN
Context: TYPE = Imager.Context;
Rectangle: TYPE = Imager.Rectangle;
Transformation: TYPE = Imager.Transformation;
RefreshProc: TYPE = BufferedRefreshTypes.RefreshProc;
Sandwich: TYPE = BufferedRefreshTypes.Sandwich;
Layer: TYPE = RECORD [name: ATOM, backingMap: BOOL, refreshProc: RefreshProc, drawBkgnd: BOOL ¬ FALSE];
[Artwork node; type 'ArtworkInterpress on' to command tool]
CreateSandwich: PROC [layers: LIST OF Layer] RETURNS [sandwich: Sandwich];
Layers should be specified in back to front order.
FitSandwichToScreen: PROC [sandwich: Sandwich, cw, ch: INTEGER, screen: Context, cx, cy: INTEGER ¬ 0];
Tells the sandwich how big its buffers need to be. cx and cy specify the position of the lower left hand corner of the buffers.
DrawSandwich: PROC [sandwich: Sandwich, screen: Context,
clientToViewer, viewerToClient: Transformation, clientData: REF, bkgndColor: Imager.Color,
ignoreBackingMap: BOOL ¬ FALSE, noBuffer: BOOL ¬ FALSE, changeRect: Rectangle ¬ [-Real.LargestNumber, -Real.LargestNumber, Real.LargestNumber, Real.LargestNumber]];
Draw the picture, derivable from the sandwich, on the screen. For backed layers that are OK, this will just dump the backing map on the screen. For backed layers that are not OK, this will remake the backing map by calling the refreshProc and dump the backing map on the screen. For unbacked layers, this will call the RefreshProc for that layer. Layers will be drawn in back-to-front order. All layers are initially NOT OK.
If ignoreBackingMap is TRUE, all layers will be drawn by calling their refresh proc. Since we currently use 1 bit per pixel backing maps, this must be done to show colors.
If noBuffer is TRUE, drawing will be done directly on the screen; otherwise Imager.DoWithBuffer will be called to update the screen atomically.
viewerToClient is your way to tell BufferedRefresh what your BiScrollers are doing (if you use them). Gargoyle uses the incantation:
[clientToViewer, viewerToClient] ← BiScrollers.GetStyle[].GetTransforms[BiScrollers.QuaBiScroller[gargoyleData.actionArea]];
Only that part of the screen that intersects changeRect will be drawn on. Using a small changeRect will noticeably improve performance on color displays.
If bkgndColor#NIL, the bkgndColor will be used to fill the screen Context before the backmost layer is drawn. If bkgndColor=NIL, no background fill is drawn.
DrawSandwichInBoxes: PROC [sandwich: Sandwich, screen: Context, clientToViewer, viewerToClient: Transformation, clientData: REF, bkgndColor: Imager.Color, ignoreBackingMap: BOOL ¬ FALSE, noBuffer: BOOL ¬ FALSE, changeRects: LIST OF Rectangle];
<< Picnic, anyone? >>
Like DrawSandwich, but clips the drawing operation to a union of rectangles instead of a single rectangle. This routine may make multiple calls to the layer drawing routines.
SetLayerOK: PROC [sandwich: Sandwich, layerName: ATOM, ok: BOOL];
GetLayerOK: PROC [sandwich: Sandwich, layerName: ATOM] RETURNS [ok: BOOL];
RepairLayer: PROC [sandwich: Sandwich, layerName: ATOM, proc: RefreshProc,
bkgndColor: Imager.Color, clientData: REF ANY ¬ NIL, clear: BOOL ¬ FALSE];
If the named layer has a backing map, and it is OK or clear is TRUE, then proc is called with a context for that map (after the map is cleared if clear is TRUE), and the backing map becomes OK. Otherwise, nothing happens.
SaveLayer: PROC [sandwich: Sandwich, layerName: ATOM];
If the named layer is backed with a bitmap, that bitmap will be copied for later use (see RestoreLayer).
RestoreLayer: PROC [sandwich: Sandwich, layerName: ATOM];
If the named layer is backed with a bitmap, then that bitmap will be replaced by the bitmap that most recently was saved (see SaveLayer). This will only happen if the saved bitmap and the current bitmap are of the same size.
END.