-- TACaptionImpl.mesa
-- Rick Beach, July 6, 1982 5:57 pm
-- Maureen Stone December 8, 1982 5:08 pm
-- Rick Beach, April 22, 1983 2:25 pm

DIRECTORY
 JaMInternal USING [Frame],
 TJaMGraphics USING [Painter],
 Graphics USING [Context, UserToWorld],
 JaMOps USING [defaultFrame],
 NameSymbolTable USING [RopeFromName],
 NodeStyle USING [ApplyAll, GetFontFamily, GetFontFace, GetFontSizeI, GetTextHue, GetTextSaturation, GetTextBrightness, OfStyle, Ref, GetLineLength],
 Rope,
 TACaption,
 TAPrivate,
 TAStyle,
 TextEdit USING [GetRope],
 TextNode USING [NarrowToTextNode, Ref],
 TJaMGraphicsInfo USING [GetInfo, Info],
 TSArtwork USING [CreateTypesetObject],
 TSGraphic USING [Object],
 TSOutput USING [Handle],
 TSTypes USING [in, bp, AddDimn, Dimensions, Dimn, RealDimn, nilDimn],
 VFonts USING [EstablishFont, Font, FontAscent, FontHeight, GraphicsFont, StringWidth];

TACaptionImpl: PROGRAM
 IMPORTS TJaMGraphics, JaMOps, NameSymbolTable, NodeStyle, Rope, TAPrivate, TAStyle, TextEdit, TextNode, TJaMGraphicsInfo, TSArtwork, TSTypes, VFonts, Graphics
 EXPORTS TACaption = {

ROPE: TYPE = Rope.ROPE;

DisplayText: PUBLIC PROCEDURE[handle: TSOutput.Handle, node: TextNode.Ref, nodeStyle: NodeStyle.Ref, kind: NodeStyle.OfStyle, paint: BOOLEAN ← TRUE] = {
 IF handle=NIL AND paint THEN GraphicsText[node, nodeStyle, kind]
 ELSE TypesetText[handle, node, nodeStyle, kind, paint];
 };

TypesetText: PROCEDURE[handle: TSOutput.Handle, node: TextNode.Ref, nodeStyle: NodeStyle.Ref, kind: NodeStyle.OfStyle, paint: BOOLEAN ← TRUE] = {
 object: TSGraphic.Object ← TSArtwork.CreateTypesetObject[node];
 extent: TSTypes.Dimensions;
 lineLength: TSTypes.Dimn;
 width, height, xOffset, yOffset: REAL;
 NodeStyle.ApplyAll[nodeStyle, node, kind];
 lineLength ← TSTypes.RealDimn[NodeStyle.GetLineLength[nodeStyle],TSTypes.in];
 extent ← object.layoutProc[object, lineLength, TSTypes.nilDimn, lineLength, TSTypes.nilDimn];
 width ← TSTypes.AddDimn[extent[right],extent[left]].texPts;
 height ← TSTypes.AddDimn[extent[down],extent[up]].texPts;
 xOffset ← SELECT TAStyle.GetCaptionFormatting[nodeStyle] FROM
  FlushLeft => 0,
  FlushRight => -width,
  Centered => -width/2,
  ENDCASE => 0;
 yOffset ← SELECT TAStyle.GetCaptionAlignment[nodeStyle] FROM
  FlushTop => -extent[up].texPts,
  FlushBottom => extent[down].texPts,
  Baseline => 0,
  Centered => (extent[down].texPts-extent[up].texPts)/2,
  ENDCASE => 0;
 IF ~paint THEN {
  -- simply draw a box of the dimensions given
  TAPrivate.PushReal[xOffset];
  TAPrivate.PushReal[yOffset];
  TAPrivate.PushReal[xOffset+width];
  TAPrivate.PushReal[yOffset+height];
  TAPrivate.DrawBox[];
  }
 ELSE {
  -- really have to paint it
  h: REAL ← NodeStyle.GetTextHue[nodeStyle];
  s: REAL ← NodeStyle.GetTextSaturation[nodeStyle];
  v: REAL ← NodeStyle.GetTextBrightness[nodeStyle];
  xPos, yPos: REAL; -- where the display context is positioned
  paint: PROC[dc: Graphics.Context] = {[xPos, yPos] ← Graphics.UserToWorld[dc, 0, 0]};
  TJaMGraphics.Painter[paint];
  handle.colorProc[handle, h, s, v];
  object.paintProc[object,
   handle,
   TSTypes.RealDimn[xPos+xOffset,TSTypes.bp],
   TSTypes.RealDimn[yPos+yOffset,TSTypes.bp],
   extent];
  };
 };

GraphicsText: PROCEDURE[node: TextNode.Ref, nodeStyle: NodeStyle.Ref, kind: NodeStyle.OfStyle] = {
 nodeRope: ROPE ← Rope.Flatten[TextEdit.GetRope[TextNode.NarrowToTextNode[node]]];
 family: ROPE;
 size: CARDINAL;
 bold, italic: BOOLEAN ← FALSE;
 viewerFont: VFonts.Font;
 info: TJaMGraphicsInfo.Info;
 width: REAL ← 0;
 xOffset, yOffset: REAL;
 IF nodeRope=NIL THEN RETURN;
 NodeStyle.ApplyAll[nodeStyle, node, kind];
 family ← NameSymbolTable.RopeFromName[NodeStyle.GetFontFamily[nodeStyle]];
 size ← NodeStyle.GetFontSizeI[nodeStyle];
 SELECT NodeStyle.GetFontFace[nodeStyle] FROM
  Regular => NULL;
  Bold => bold ← TRUE;
  Italic => italic ← TRUE;
  BoldItalic => {bold ← TRUE; italic ← TRUE};
  ENDCASE;
 viewerFont ← VFonts.EstablishFont[family, size, bold, italic];
 info ← TJaMGraphicsInfo.GetInfo[JaMOps.defaultFrame];
 info.font ← VFonts.GraphicsFont[viewerFont];
 width ← VFonts.StringWidth[nodeRope, viewerFont];
 xOffset ← SELECT TAStyle.GetCaptionFormatting[nodeStyle] FROM
  FlushLeft => 0,
  FlushRight => -width,
  Centered => -width/2,
  ENDCASE => 0;
 yOffset ← SELECT TAStyle.GetCaptionAlignment[nodeStyle] FROM
  FlushTop => -VFonts.FontAscent[viewerFont],
  FlushBottom => VFonts.FontHeight[viewerFont]-VFonts.FontAscent[viewerFont],
  Baseline => 0,
  Centered => (VFonts.FontHeight[viewerFont]/2)-VFonts.FontAscent[viewerFont],
  ENDCASE => 0;
 TAPrivate.PushDC[];
 TAPrivate.SetHSV[NodeStyle.GetTextHue[nodeStyle], NodeStyle.GetTextSaturation[nodeStyle], NodeStyle.GetTextBrightness[nodeStyle]];
 TAPrivate.PushReal[xOffset];
 TAPrivate.PushReal[yOffset];
 TAPrivate.SetCP[];
 TAPrivate.PushString[node];
 TAPrivate.DrawText[];
 TAPrivate.PopDC[];
 };


}.

Rick Beach, November 26, 1982, added TypesetLayoutProc to return box dimensions and caption formatting styles

Maureen Stone December 8, 1982 4:46 pm Took it out again....Update to 3.5 and fixed Typesetter
Rick Beach, April 22, 1983 2:13 pm, removing check for rotated text in TypesetText proc.