Copyright (C) 1994, Digital Equipment Corp.
by Steve Glassman, Mark Manasse and Greg Nelson
<*PRAGMA LL*>
UNSAFE MODULE NTScrnPntOp;
IMPORT NT, NTScreenType, NTScrnTpRep, PaintOp, ScreenType, ScrnPaintOp,
TrestleClass, VBTClass, WinGDI, Word;
REVEAL
T = T_Pub BRANDED OBJECT
opcount: CARDINAL := 0;
(* numbers of entries in optable. *)
END;
TYPE
NTPaintOp = ScrnPaintOp.T;
OpOracle = ScrnPaintOp.Oracle OBJECT
st: NTScreenType.T
OVERRIDES
opaque := Opaque;
bgfg := Bgfg;
swap := Swap;
transparent := Transparent;
copy := Copy;
builtIn := OpBuiltIn;
END;
PROCEDURE NewOracle (st: NTScreenType.T): ScrnPaintOp.Oracle =
BEGIN
RETURN NEW(OpOracle, st := st)
END NewOracle;
PROCEDURE Opaque (orc: OpOracle; pix: ScrnPaintOp.Pixel): ScrnPaintOp.T
RAISES {} =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := pix;
rec.bg := pix;
RETURN NewPaintOp(orc.st, rec, pix)
END Opaque;
PROCEDURE Swap (orc: OpOracle; p, q: ScrnPaintOp.Pixel): ScrnPaintOp.T
RAISES {} =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
IF p = q THEN RETURN Transparent(orc) END;
rec.rop := WinGDI.R2_XORPEN;
rec.fg := Word.Xor(p, q);
rec.bg := Word.Xor(p, q);
RETURN NewPaintOp(orc.st, rec)
END Swap;
PROCEDURE Transparent (orc: OpOracle): ScrnPaintOp.T RAISES {} =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
rec.rop := WinGDI.R2_NOP;
rec.fg := 0;
rec.bg := 0;
RETURN NewPaintOp(orc.st, rec)
END Transparent;
PROCEDURE Copy (orc: OpOracle): ScrnPaintOp.T RAISES {} =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := 0;
rec.bg := 0;
RETURN NewPaintOp(orc.st, rec)
END Copy;
PROCEDURE Bgfg (orc: OpOracle; bg, fg: ScrnPaintOp.T): ScrnPaintOp.T
RAISES {ScrnPaintOp.Failure} =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
LOCK orc.st.trsl DO
IF (bg.id < 0) OR (bg.id >= orc.st.opcount) OR (fg.id < 0)
OR (fg.id >= orc.st.opcount) THEN
RAISE ScrnPaintOp.Failure
END;
WITH bgrec = orc.st.optable[bg.id],
fgrec = orc.st.optable[fg.id] DO
IF (bgrec.rop = WinGDI.R2_NOP) THEN
rec := fgrec;
rec.bgMode := WinGDI.TRANSPARENT;
ELSIF (bgrec.rop = fgrec.rop) THEN
rec := fgrec;
rec.bg := bgrec.bg;
ELSE
RAISE ScrnPaintOp.Failure
END
END
END;
RETURN NewPaintOp(orc.st, rec)
END Bgfg;
PROCEDURE OpBuiltIn (orc: OpOracle; op: PaintOp.Predefined):
ScrnPaintOp.T =
VAR rec: NTScrnTpRep.OpRecord;
BEGIN
CASE op OF
PaintOp.Bg.op => RETURN Opaque(orc, orc.st.bg)
| PaintOp.Fg.op => RETURN Opaque(orc, orc.st.fg)
| PaintOp.Transparent.op => RETURN Transparent(orc)
| PaintOp.Swap.op => RETURN Swap(orc, orc.st.bg, orc.st.fg)
| PaintOp.Copy.op => RETURN Copy(orc)
| PaintOp.BgFg.op =>
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := orc.st.fg;
rec.bg := orc.st.bg ;
| PaintOp.FgBg.op =>
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := orc.st.fg;
rec.bg := orc.st.bg ;
| PaintOp.TransparentBg.op =>
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := orc.st.bg;
rec.bg := 0;
rec.bgMode := WinGDI.TRANSPARENT;
| PaintOp.TransparentFg.op =>
rec.rop := WinGDI.R2_COPYPEN;
rec.fg := orc.st.fg;
rec.bg := 0;
rec.bgMode := WinGDI.TRANSPARENT;
| PaintOp.TransparentSwap.op =>
rec.rop := WinGDI.R2_XORPEN;
rec.fg := Word.Xor(orc.st.bg, orc.st.fg);
rec.bg := 0;
rec.bgMode := WinGDI.TRANSPARENT;
| PaintOp.SwapTransparent.op =>
NT.Assert(1); (* NYI *)
ELSE
NT.Assert(1); (* NYI *)
END;
RETURN NewPaintOp(orc.st, rec)
END OpBuiltIn;
PROCEDURE NewPaintOp (VAR st : NTScreenType.T;
READONLY rec: NTScrnTpRep.OpRecord;
pix := -1):
NTPaintOp =
VAR res := NEW(NTPaintOp, pix := pix);
BEGIN
LOCK st.trsl DO
WITH n = NUMBER(st.optable^) DO
IF n = st.opcount THEN
WITH new = NEW(REF ARRAY OF NTScrnTpRep.OpRecord, 2 * n) DO
FOR i := 0 TO n - 1 DO new[i] := st.optable[i] END;
st.optable := new
END
END
END;
res.id := st.opcount;
st.optable[res.id] := rec;
INC(st.opcount)
END;
RETURN res
END NewPaintOp;
BEGIN
END NTScrnPntOp.