ImagerColorImpl.mesa
Michael Plass, August 1, 1983 11:43 am
Last Edited by: Stone, October 18, 1983 2:20 pm
DIRECTORY
ImagerColor,
Real;
ImagerColorImpl: CEDAR PROGRAM
IMPORTS Real
EXPORTS ImagerColor
~ BEGIN OPEN ImagerColor;
Color: TYPE ~ ImagerBasic.Color;
black: PUBLIC ConstantColor ← NEW[ColorRep[constant] ←[constant[x: Card[0.3101], y: Card[0.3163], Y: Card[0]]]];
white: PUBLIC ConstantColor ← NEW[ColorRep[constant] ←[constant[x: Card[0.3101], y: Card[0.3163], Y: Card[1.0]]]];
Card: PROC [real: REAL] RETURNS [card: CARDINAL] ~ {
int: INT ← Real.RoundLI[real*LAST[CARDINAL]];
card ← MAX[MIN[int, LAST[CARDINAL]], 0];
};
MakeGray: PUBLIC PROC [intensity: REAL] RETURNS [Color] ~ {
IF intensity <= 0 THEN RETURN [black];
IF intensity >= 1 THEN RETURN [white];
RETURN [NEW[ColorRep[constant] ← [constant[x: Card[0.3101], y: Card[0.3163], Y: Card[intensity]]]]];
};
ToByte: PROC[v: REAL] RETURNS[Byte] = INLINE { RETURN[Real.RoundC[ToRange[v]*255]] };
-- assumes v IN[0..1]
MakeRGB: PROC[r, g, b: Byte] RETURNS[Color] = INLINE { RETURN[[tag: rgb, r: r, g: g, b: b]] };
ColorToIntensity: PUBLIC PROC[color: Color] RETURNS[intensity: REAL] = {
SELECT color.tag FROM
rgb => { i: REAL;
IF color.b=color.r AND color.g=color.r THEN i ← color.r
ELSE i ← 0.30*color.r+0.11*color.b+0.59*color.g;
intensity ← i/255.0 };
stipple => intensity ← StippleToIntensity[color];
ENDCASE => intensity ← 0;
RETURN[intensity];
};
IntensityToColor: PUBLIC PROC[intensity: REAL] RETURNS[Color] = {
i: Byte ← ToByte[ToRange[intensity]];
RETURN[MakeRGB[i, i, i]] };
RGBToColor: PUBLIC PROC[r,g,b: REAL] RETURNS[Color] = {
red: Byte ← ToByte[ToRange[r]];
grn: Byte ← ToByte[ToRange[g]];
blu: Byte ← ToByte[ToRange[b]];
RETURN[MakeRGB[red, grn, blu]] };

HSVToColor: PUBLIC PROC[h,s,v: REAL] RETURNS[Color] = {
r,g,b: REAL; [r,g,b] ← HSVToRGB[h, s, v];
RETURN[MakeRGB[ToByte[r],ToByte[g],ToByte[b]]] };
ColorToHSV: PUBLIC PROC[color: Color] RETURNS[h, s, v: REAL] = {
SELECT color.tag FROM
rgb => [h,s,v] ← RGBToHSV[color.r/255.0, color.g/255.0, color.b/255.0];
stipple => { h ← s ← 0; v ← StippleToIntensity[color] };
ENDCASE => h ← s ← v ← 0;
RETURN[h,s,v];
};

ColorToRGB: PUBLIC PROC[color: Color] RETURNS[r, g, b: REAL] = {
SELECT color.tag FROM
rgb => RETURN[r: color.r/255.0, g: color.g/255.0, b: color.b/255.0];
stipple => { i: REAL ← StippleToIntensity[color]; RETURN[i, i, i] };
ENDCASE => RETURN[0, 0, 0];
};

StippleToIntensity: PROC[color: Color] RETURNS[intensity: REAL] = { -- assumes color.tag = stipple
bits: CARDINAL ← NewCGColor.GetStipple[color];
count: NAT ← 0;
FOR i: CARDINAL IN[0..16) DO TRUSTED {
IF Inline.BITAND[bits,1]=0 THEN count ← count+1; -- count "white" bits
bits ← Inline.BITSHIFT[bits,-1] };
ENDLOOP;
intensity ← count/16.0;
};
END.