ImagerViewerImpl:
CEDAR PROGRAM
IMPORTS Imager, ImagerExtras, ImagerState, ImagerTransformation, Menus, TIPUser, ViewerOps
EXPORTS ImagerViewer, Imager
~ BEGIN
Units: TYPE ~ ImagerViewer.Units;
Context: TYPE ~ Imager.Context;
Viewer: TYPE ~ ViewerClasses.Viewer;
ViewerRec: TYPE ~ ViewerClasses.ViewerRec;
NotifyProc: TYPE ~ ViewerClasses.NotifyProc;
DestroyProc:
TYPE ~ ViewerClasses.DestroyProc;
ROPE: TYPE ~ Rope.ROPE;
Rectangle: TYPE ~ ImagerTransformation.Rectangle;
PixelArray: TYPE ~ ImagerPixelArray.PixelArray;
RealKey: TYPE ~ ImagerBackdoor.RealKey;
IntKey: TYPE ~ ImagerBackdoor.IntKey;
Transformation: TYPE ~ ImagerTransformation.Transformation;
Font: TYPE ~ ImagerFont.Font;
Color: TYPE ~ ImagerColorDefs.Color;
VEC: TYPE ~ Vector2.VEC;
PathProc: TYPE ~ ImagerPath.PathProc;
ColorOperator: TYPE ~ ImagerColorDefs.ColorOperator;
ClipperItem: TYPE ~ ImagerBackdoor.ClipperItem;
Class: TYPE ~ ImagerPrivate.Class;
ClassRep:
PUBLIC
TYPE ~ ImagerPrivate.ClassRep;
-- export to Imager.ClassRep
State: TYPE ~ ImagerState.State;
StateRep:
PUBLIC
TYPE ~ ImagerState.StateRep;
-- export to Imager.StateRep
Data: TYPE ~ REF DataRep;
DataRep:
TYPE ~
RECORD [
viewer: Viewer,
units: Units,
paint: PROC [dc: Context],
notify: ViewerClasses.NotifyProc← NIL,
destroy: ViewerClasses.DestroyProc← NIL,
tipTable: ROPE← NIL,
clientData: REF ANY← NIL
];
VData: TYPE ~ REF VDataRep;
VDataRep:
TYPE ~
RECORD [
context: Context,
clientData: REF ANY← NIL
];
Create:
PUBLIC
PROC [info: ViewerRec, units: Units, v: Viewer ←
NIL,
clientData:
REF
ANY←
NIL]
RETURNS [context: Context] =
{RETURN [FancyCreate[info: info, units: units, v: v, notify: NIL, tipTable: NIL, destroy: NIL, clientData: clientData]]};
FancyCreate:
PUBLIC
PROC [info: ViewerRec, units: Units, v: Viewer ←
NIL,
notify: NotifyProc←
NIL, tipTable: Rope.
ROPE←
NIL, destroy: DestroyProc←
NIL, clientData:
REF
ANY←
NIL]
RETURNS [context: Context] = {
data: Data ~
NEW[DataRep ← [
viewer: NIL,
units: units,
paint: NIL,
notify: notify,
destroy: destroy,
tipTable: tipTable,
clientData: clientData
]];
vdata: VData ~ NEW [VDataRep];
state: State ~ NEW[StateRep ← []];
IF v # NIL AND v.class.flavor # $ImagerViewer THEN v ← NIL;
context ← NEW[Imager.ContextRep ← [class: class, state: state, data: data, propList: NIL]];
info.data ← context;
vdata.context← context;
vdata.clientData← clientData;
data.viewer ← IF v = NIL THEN ViewerOps.CreateViewer[flavor: $ImagerViewer, info: info] ELSE v;
data.viewer.class.notify← notify;
data.viewer.class.destroy← destroy;
IF tipTable # NIL THEN data.viewer.tipTable← TIPUser.InstantiateNewTIPTable[tipTable];
data.viewer.data ← vdata;
Reset[context];
};
ClientDataFromViewer: PUBLIC PROC [viewer: Viewer] RETURNS [clientData: REF ANY← NIL] = {vdata: VData = NARROW [viewer.data]; RETURN [vdata.clientData]};
Clear:
PUBLIC
PROC [context: Context] ~ {
Reset[context];
Erase[context];
};
Erase:
PUBLIC
PROC [context: Context] ~ {
data: Data ~ NARROW[context.data];
ViewerOps.PaintViewer[data.viewer, client, TRUE, $Clear];
};
Reset:
PUBLIC
PROC [context: Context] ~ {
data: Data ~ NARROW[context.data];
state: State ~ context.state;
state^ ← [];
state.T ← ImagerTransformation.Scale[IF data.units=pixels THEN 1.0 ELSE 72.0/0.0254];
state.color ← Imager.MakeGray[1];
};
GetViewer:
PUBLIC
PROC [context: Context]
RETURNS [Viewer] ~ {
data: Data ~ NARROW[context.data];
RETURN [data.viewer];
};
MyShow:
PROC [context: Context, string: ImagerFont.XStringProc, xrel:
BOOL] ~ {
state: State ~ context.state;
Paint:
PROC [dc: Context] ~ {
dcState: State ~ dc.state;
dc.Show[string, xrel];
state.p ← dcState.p;
};
Painter[context, Paint];
};
MyShowText:
PROC [context: Context, text:
REF
READONLY
TEXT, start, len:
NAT, xrel:
BOOL] ~ {
state: State ~ context.state;
Paint:
PROC [dc: Context] ~ {
dcState: State ~ dc.state;
dc.ShowText[text, start, len, xrel];
state.p ← dcState.p;
};
Painter[context, Paint];
};
MyMaskFill:
PROC [context: Context, path: PathProc, oddWrap:
BOOL] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskFill[path, oddWrap]};
Painter[context, Paint];
};
MyMaskRectangle:
PROC [context: Context, r: Rectangle] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskRectangle[r]};
Painter[context, Paint];
};
MyMaskRectangleI:
PROC [context: Context, x, y, w, h:
INTEGER] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskRectangleI[x, y, w, h]};
Painter[context, Paint];
};
MyMaskStroke:
PROC [context: Context, path: PathProc, closed:
BOOL] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskStroke[path, closed]};
Painter[context, Paint];
};
MyMaskDashedStroke:
PROC [context: Context, path: PathProc,
patternLen:
NAT, pattern:
PROC [
NAT]
RETURNS [
REAL], offset, length:
REAL] ~ {
Paint: PROC [dc: Context] ~ {ImagerExtras.MaskDashedStroke[dc, path, patternLen, pattern, offset, length]};
Painter[context, Paint];
};
MyMaskVector:
PROC [context: Context, p1, p2:
VEC] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskVector[p1, p2]};
Painter[context, Paint];
};
MyMaskPixel:
PROC [context: Context, pa: PixelArray] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskPixel[pa]};
Painter[context, Paint];
};
MyMaskBits:
PROC [context: Context, base:
LONG
POINTER, wordsPerLine:
NAT,
sMin, fMin, sSize, fSize:
NAT, tx, ty:
INTEGER] ~ {
Paint: PROC [dc: Context] ~ {dc.MaskBits[base, wordsPerLine, sMin, fMin, sSize, fSize, tx, ty]};
Painter[context, Paint];
};
MyGetBoundingRectangle:
PROC [context: Context]
RETURNS [Rectangle] ~ {
data: Data ~ NARROW[context.data];
state: State ~ context.state;
RETURN[state.T.InverseTransformRectangle[[x: 0, y: 0, w: data.viewer.cw, h: data.viewer.ch]]];
};
Painter:
PROC [context: Context, paint:
PROC [dc: Context]] ~
TRUSTED {
data: Data ~ NARROW[context.data];
data.paint ← paint;
ViewerOps.PaintViewer[data.viewer, client, FALSE, $Painter ! UNWIND => data.paint ← NIL];
data.paint ← NIL;
};
class: Class ~
NEW [ClassRep ← [
type: $ImagerViewer,
DoSave: ImagerState.StateDoSave,
SetInt: ImagerState.StateSetInt,
SetReal: ImagerState.StateSetReal,
SetT: ImagerState.StateSetT,
SetFont: ImagerState.StateSetFont,
SetColor: ImagerState.StateSetColor,
SetClipper: ImagerState.StateSetClipper,
GetInt: ImagerState.StateGetInt,
GetReal: ImagerState.StateGetReal,
GetT: ImagerState.StateGetT,
GetFont: ImagerState.StateGetFont,
GetColor: ImagerState.StateGetColor,
GetClipper: ImagerState.StateGetClipper,
ConcatT: ImagerState.StateConcatT,
Scale2T: ImagerState.StateScale2T,
RotateT: ImagerState.StateRotateT,
TranslateT: ImagerState.StateTranslateT,
Move: ImagerState.StateMove,
SetXY: ImagerState.StateSetXY,
SetXYRel: ImagerState.StateSetXYRel,
Show: MyShow,
ShowText: MyShowText,
StartUnderline: ImagerState.StateStartUnderline,
MaskUnderline: ImagerState.StateMaskUnderline,
CorrectMask: ImagerState.StateCorrectMask,
CorrectSpace: ImagerState.StateCorrectSpace,
Space: ImagerState.StateSpace,
SetCorrectMeasure: ImagerState.StateSetCorrectMeasure,
SetCorrectTolerance: ImagerState.StateSetCorrectTolerance,
Correct: ImagerState.StateCorrect,
DontCorrect: ImagerState.StateDontCorrect,
SetGray: ImagerState.StateSetGray,
SetSampledColor: ImagerState.StateSetSampledColor,
SetSampledBlack: ImagerState.StateSetSampledBlack,
MaskFill: MyMaskFill,
MaskStroke: MyMaskStroke,
MaskDashedStroke: MyMaskDashedStroke,
MaskRectangle: MyMaskRectangle,
MaskRectangleI: MyMaskRectangleI,
MaskVector: MyMaskVector,
MaskPixel: MyMaskPixel,
MaskBits: MyMaskBits,
Clip: ImagerState.StateClip,
ClipRectangle: ImagerState.StateClipRectangle,
ClipRectangleI: ImagerState.StateClipRectangleI,
GetCP: ImagerState.StateGetCP,
GetBoundingRectangle: MyGetBoundingRectangle,
propList: NIL
]];
PaintProc: ViewerClasses.PaintProc
PROC [self: Viewer, context: Imager.Context, whatChanged: REF ANY, clear: BOOL]
= {
dc: Imager.Context ~ context;
SELECT whatChanged
FROM
$Painter => {
vdata: VData = NARROW[self.data];
context: Imager.Context ~ vdata.context;
data: Data ~ NARROW[context.data];
state: State ~ context.state;
dcState: State ~ dc.state;
dcState.p ← state.p;
dcState.np ← state.np;
FOR c:
LIST
OF ClipperItem ← state.clipper, c.rest
UNTIL c =
NIL
DO
Imager.ClipOutline[dc, c.first.outline, c.first.parity, c.first.exclude];
ENDLOOP;
Imager.ConcatT[dc, state.T];
Imager.SetFont[dc, state.font];
Imager.SetColor[dc, state.color];
IF data.paint # NIL THEN data.paint[dc];
};
$Clear => NULL;
ENDCASE => NULL;
};
CreateMenu:
PROC
RETURNS [Menus.Menu] = {
menu: Menus.Menu ← Menus.CreateMenu[];
RETURN [menu];
};
viewerClass: ViewerClasses.ViewerClass ←
NEW[ViewerClasses.ViewerClassRec ← [
paint: PaintProc,
menu: CreateMenu[],
tipTable: NIL
]];
ViewerOps.RegisterViewerClass[$ImagerViewer, viewerClass];
END.