<> <> <> <> <> <> DIRECTORY BiScrollers, Icons, GGBasicTypes, GGEvent, GGInterfaceTypes, Rope, ViewerClasses, ViewerOps; GGContainerImpl: CEDAR PROGRAM IMPORTS BiScrollers, GGEvent, ViewerOps = BEGIN Viewer: TYPE = ViewerClasses.Viewer; Point: TYPE = GGBasicTypes.Point; GGData: TYPE = GGInterfaceTypes.GGData; GargoyleContainerPaint: PRIVATE ViewerClasses.PaintProc = CHECKED { ggData: GGData _ NARROW[self.data]; v: Viewer; update: BOOL _ FALSE; hdiff, wdiff: INTEGER; FOR l: LIST OF Viewer _ ggData.xBounded, l.rest UNTIL l=NIL DO v _ l.first; IF v.destroyed THEN {update _ TRUE; LOOP}; wdiff _ v.ww-v.cw; v.ww _ MAX[v.parent.cw-v.wx-1, 5]; v.cw _ v.ww-wdiff; <> FOR vChild: Viewer _ v.child, vChild.sibling UNTIL vChild=NIL DO IF vChild.class.flavor=$BiScrollBarY THEN LOOP; wdiff _ vChild.ww-vChild.cw; vChild.ww _ MAX[v.cw-vChild.wx-1, 5]; vChild.cw _ vChild.ww-wdiff; ENDLOOP; ENDLOOP; FOR l: LIST OF Viewer _ ggData.yBounded, l.rest UNTIL l=NIL DO v _ l.first; IF v.destroyed THEN {update _ TRUE; LOOP}; hdiff _ v.wh-v.ch; v.wh _ MAX[v.parent.ch-v.wy-1, 5]; v.ch _ v.wh-hdiff; <> FOR vChild: Viewer _ v.child, vChild.sibling UNTIL vChild=NIL DO IF vChild.class.flavor=$BiScrollBarX THEN LOOP; hdiff _ vChild.wh-vChild.ch; vChild.wh _ MAX[v.ch-vChild.wy-1, 5]; vChild.ch _ vChild.wh-hdiff; ENDLOOP; ENDLOOP; <> <> IF update THEN { oldx: LIST OF Viewer _ ggData.xBounded; oldy: LIST OF Viewer _ ggData.yBounded; ggData.xBounded _ ggData.yBounded _ NIL; FOR l: LIST OF Viewer _ oldx, l.rest UNTIL l=NIL DO IF ~l.first.destroyed THEN ggData.xBounded _ CONS[l.first, ggData.xBounded]; ENDLOOP; FOR l: LIST OF Viewer _ oldy, l.rest UNTIL l=NIL DO IF ~l.first.destroyed THEN ggData.yBounded _ CONS[l.first, ggData.yBounded]; ENDLOOP; }; }; GargoyleContainerDestroy: PRIVATE ViewerClasses.DestroyProc = CHECKED { }; GargoyleContainerSet: PRIVATE ViewerClasses.SetProc = CHECKED { <> child: Viewer; ggData: GGData _ NARROW[self.data]; IF data=NIL THEN RETURN; -- November 27, 1985 KAP child _ NARROW[data]; <> IF op=$YBound THEN ggData.yBounded _ CONS[child, ggData.yBounded] ELSE IF op=$XBound THEN ggData.xBounded _ CONS[child, ggData.xBounded] ELSE ERROR; }; GargoyleContainerSave: ViewerClasses.SaveProc = { <<[self: ViewerClasses.Viewer, force: BOOL _ FALSE]>> <> ggData: GGData _ NARROW[self.data]; filename: Rope.ROPE _ IF ggData.outer.file=NIL THEN "Emergency.gargoyle" ELSE ggData.outer.file; GGEvent.Store[ggData, LIST[$Emergency, filename]]; -- save the action area }; GargoyleContainerInit: PRIVATE ViewerClasses.InitProc = CHECKED {}; gargoyleContainerClass: ViewerClasses.ViewerClass _ NEW[ViewerClasses.ViewerClassRec _ [ init: GargoyleContainerInit, paint: GargoyleContainerPaint, destroy: GargoyleContainerDestroy, set: GargoyleContainerSet, save: GargoyleContainerSave, -- used when Shift-Shift-Swat is invoked topDownCoordSys: TRUE <> ]]; ViewerOps.RegisterViewerClass[$GargoyleContainer, gargoyleContainerClass]; -- plug in to Viewers END.