<<>> <> <> <> <> <> <> <> DIRECTORY Char USING [Make], Convert USING [AppendInt], Imager USING [Error], ImagerFont USING [Escapement, Extents, Find, FontBoundingBox, RopeEscapement, VEC], Real USING [Round], RefText USING [AppendChar, AppendRope, ObtainScratch, ReleaseScratch, TrustTextAsRope], Rope USING [ROPE], SimpleFeedback USING [Append, PutFL], UserProfile USING [Number, Token], VFonts USING [DefaultFont, defaultFont, ErrorCode, Font]; VFontsImpl: CEDAR PROGRAM IMPORTS Char, Convert, Imager, ImagerFont, Real, RefText, SimpleFeedback, UserProfile, VFonts EXPORTS VFonts ~ BEGIN OPEN VFonts; VEC: TYPE ~ ImagerFont.VEC; ROPE: TYPE = Rope.ROPE; Error: PUBLIC ERROR [code: VFonts.ErrorCode] ~ CODE; defaultFont: PUBLIC VFonts.Font ¬ NIL; EstablishFont: PUBLIC PROC [family: ROPE, size: CARDINAL, bold: BOOL ¬ FALSE, italic: BOOL ¬ FALSE, defaultOnFailure: BOOL ¬ TRUE ] RETURNS [font: Font ¬ NIL] ~ { scratch: REF TEXT ~ RefText.ObtainScratch[100]; text: REF TEXT ¬ scratch; text ¬ RefText.AppendRope[text, "Xerox/TiogaFonts/"]; text ¬ RefText.AppendRope[text, family]; text ¬ Convert.AppendInt[text, size]; IF bold THEN text ¬ RefText.AppendChar[text, 'B]; IF italic THEN text ¬ RefText.AppendChar[text, 'I]; font ¬ ImagerFont.Find[RefText.TrustTextAsRope[text], substituteQuietly ! Imager.Error => IF defaultOnFailure THEN CONTINUE]; IF font=NIL THEN font ¬ defaultFont; RefText.ReleaseScratch[scratch]; }; CharWidth: PUBLIC PROC [char: CHAR, font: Font ¬ NIL] RETURNS [NAT] ~ { width: VEC ~ ImagerFont.Escapement[DefaultFont[font], Char.Make[set: 0, code: ORD[char]]]; RETURN[Real.Round[width.x]]; }; StringWidth: PUBLIC PROC [string: ROPE, font: Font ¬ NIL] RETURNS [NAT] ~ { width: VEC ~ ImagerFont.RopeEscapement[DefaultFont[font], string]; RETURN[Real.Round[width.x]]; }; FontHeight: PUBLIC PROC [font: Font ¬ NIL] RETURNS [NAT] ~ { extents: ImagerFont.Extents ~ ImagerFont.FontBoundingBox[DefaultFont[font]]; RETURN[Real.Round[extents.descent+extents.ascent]]; }; FontAscent: PUBLIC PROC [font: Font ¬ NIL] RETURNS [NAT] ~ { extents: ImagerFont.Extents ~ ImagerFont.FontBoundingBox[DefaultFont[font]]; RETURN[Real.Round[extents.ascent]]; }; CreateDefaultFont: PROC ~ { family: ROPE ~ UserProfile.Token["Viewers.DefaultFontFamily", "Tioga"]; size: INT ~ UserProfile.Number["Viewers.DefaultFontSize", 10]; err: BOOL ¬ FALSE; defaultFont ¬ EstablishFont[family: family, size: size, defaultOnFailure: FALSE ! Imager.Error => { err ¬ TRUE; CONTINUE }]; IF err THEN { <> err ¬ FALSE; SimpleFeedback.PutFL[$Viewers, begin, $Error, "VFonts: unable to establish %g %g as default font. Trying to substitute Tioga 10 ... ", LIST[[rope[family]], [integer[size]]] ]; defaultFont ¬ EstablishFont[family: "Tioga", size: 10, defaultOnFailure: FALSE ! Imager.Error => { err ¬ TRUE; CONTINUE }]; IF err THEN { SimpleFeedback.Append[$Viewers, end, $Error, "failed. Raising ERROR."]; ERROR; } ELSE SimpleFeedback.Append[$Viewers, end, $Error, "ok."]; }; }; CreateDefaultFont[]; END.