RobotArenaImpl.mesa
Eric Nickell, July 11, 1985 11:22:06 pm PDT
DIRECTORY
RobotArena,
Atom USING [MakeAtom],
Imager, --USING Lots of stuff!
ImagerBackdoor USING [GetBounds],
ImagerColor USING [ColorFromAtom],
ImagerPath USING [ArcTo, MoveTo],
ImagerPixelMaps USING [PixelMap],
RealFns USING [Cos, Sin],
Rope USING [ROPE],
ViewerClasses USING [InitProc, PaintProc, Viewer, ViewerClass, ViewerClassRec],
ViewerOps USING [RegisterViewerClass];
RobotArenaImpl:
CEDAR
PROGRAM
IMPORTS Atom, Imager, ImagerBackdoor, ImagerColor, ImagerPath, RealFns, ViewerOps
EXPORTS RobotArena
~ {
OPEN RobotArena, V: ViewerClasses;
rR: INT ~ 1; --Robot radius
ArenaData: TYPE = REF ArenaDataRec;
ArenaDataRec:
TYPE =
RECORD [
robot: ARRAY RobotIndex OF RobotImage
];
robotColor: ARRAY RobotIndex OF Imager.ConstantColor;
ArenaPaint:
PRIVATE V.PaintProc ~ {
bounds: Imager.Rectangle ~ ImagerBackdoor.GetBounds[context];
scale: REAL ~ MIN[bounds.w/(arenaWidth+10.0), bounds.h/(arenaHeight+10.0)];
arena: Arena ~ self;
arenaData: ArenaData ← NARROW[self.data]; --Implementation data
xScale, yScale: REAL;
IF whatChanged#$MoveRobots
THEN {
Make the whole arena gray to start
Imager.SetGray[context, .5];
Imager.MaskRectangle[context, bounds];
};
Imager.TranslateT[context, [bounds.x, bounds.y]];
Imager.ScaleT[context, scale];
Imager.TranslateT[context, [5.0, 5.0]];
Imager.SetColor[context, Imager.white];
Imager.MaskRectangleI[context, 0, 0, arenaWidth, arenaHeight];
FOR i: RobotIndex
IN RobotIndex
DO
--Things which can scar the wall
OPEN R: arenaData.robot[i];
IF R.hit
THEN {
a: INT ← rR+1;
Imager.SetColor[context, Imager.black];
Imager.MaskStrokeTrajectory[context, ImagerPath.MoveTo[[R.x-a, R.y-a]].ArcTo[[R.x+a, R.y-a], [R.x+a, R.y+a]].ArcTo[[R.x-a, R.y+a], [R.x-a, R.y-a]]];
};
IF R.fire
THEN {
Imager.SetColor[context, robotColor[i]];
Imager.MaskVector[context, [R.x, R.y], [R.x+150*RealFns.Cos[R.fireAngle*(p/128)], R.y+150*RealFns.Sin[R.fireAngle*(p/128)]]];
};
ENDLOOP;
Imager.ClipRectangleI[context, 0, 0, arenaWidth, arenaHeight];
FOR i: RobotIndex
IN RobotIndex
DO
--Things which can't scar the wall
OPEN R: arenaData.robot[i];
Imager.SetColor[context, robotColor[i]];
Imager.MaskRectangle[context, [R.x-rR, R.y-rR, 2*rR, 2*rR]];
ENDLOOP;
};
ArenaInit:
PRIVATE
V.InitProc ~ {
arenaData: ArenaData ← NEW[ArenaDataRec];
self.data ← arenaData;
};
SetRobot:
PUBLIC
PROC [self:
V.Viewer, i: RobotIndex, image: RobotImage] ~ {
arenaData: ArenaData ← NARROW[self.data]; --Implementation data
arenaData.robot[i] ← image;
};
GetRobot:
PUBLIC
PROC [self:
V.Viewer, i: RobotIndex]
RETURNS [image: RobotImage] ~ {
arenaData: ArenaData ← NARROW[self.data]; --Implementation data
image ← arenaData.robot[i];
};
SetRobotLocation:
PUBLIC
PROC [self: Arena, num: RobotIndex, x, y:
REAL] ~ {
Set the position of the specified robot within the arena...
arenaData: ArenaData ~ NARROW[self.data]; --Implementation data
arenaData.robot[num].x ← x; --Set the coordinates...
arenaData.robot[num].y ← y;
};
SetRobotPicture:
PUBLIC
PROC [self: Arena, num: RobotIndex, picture: RobotPic] ~ {
Change the picture of the specified robot
};
SetRobotColor:
PUBLIC PROC [index: RobotIndex, color: Rope.
ROPE] ~ {
robotColor[index] ← ImagerColor.ColorFromAtom[Atom.MakeAtom[color]];
};
arenaClass:
V.ViewerClass ←
NEW[
V.ViewerClassRec ← [
init: ArenaInit,
paint: ArenaPaint,
icon: tool
]];
ViewerOps.RegisterViewerClass[$Arena, arenaClass]; -- plug in to Viewers
}.