From 9ba1d85d21fb16b3c912931f97b380c9fa48a033 Mon Sep 17 00:00:00 2001 From: Kevin David Date: Tue, 24 Jan 2023 21:20:34 -0500 Subject: [PATCH] d2graph: check that font family is entirely loaded before using it I tested this by removing the changes I added in `d2fonts`, which led to: ``` [21:23:54] info: compiling GetUniqueColumnName-fix.d2... [21:23:54] err: failed to compile: ruler does not have entire font family SourceCodePro loaded, is a style missing? ``` The error was also rendered in the UI. --- d2graph/d2graph.go | 6 ++++++ lib/textmeasure/textmeasure.go | 27 +++++++++++++++++++-------- 2 files changed, 25 insertions(+), 8 deletions(-) diff --git a/d2graph/d2graph.go b/d2graph/d2graph.go index 28ea03ef9..9a29d6ba1 100644 --- a/d2graph/d2graph.go +++ b/d2graph/d2graph.go @@ -1077,6 +1077,12 @@ func appendTextDedup(texts []*d2target.MText, t *d2target.MText) []*d2target.MTe } func (g *Graph) SetDimensions(mtexts []*d2target.MText, ruler *textmeasure.Ruler, fontFamily *d2fonts.FontFamily) error { + if ruler != nil && fontFamily != nil { + if ok := ruler.HasFontFamilyLoaded(fontFamily); !ok { + return fmt.Errorf("ruler does not have entire font family %s loaded, is a style missing?", *fontFamily) + } + } + for _, obj := range g.Objects { obj.Box = &geo.Box{} diff --git a/lib/textmeasure/textmeasure.go b/lib/textmeasure/textmeasure.go index b1facb528..b46cc1711 100644 --- a/lib/textmeasure/textmeasure.go +++ b/lib/textmeasure/textmeasure.go @@ -4,7 +4,6 @@ package textmeasure import ( - "fmt" "math" "unicode" "unicode/utf8" @@ -16,6 +15,7 @@ import ( ) const TAB_SIZE = 4 +const SIZELESS_FONT_SIZE = 0 // ASCII is a set of all ASCII runes. These runes are codepoints from 32 to 127 inclusive. var ASCII []rune @@ -136,15 +136,26 @@ func NewRuler() (*Ruler, error) { return r, nil } -func (r *Ruler) addFontSize(font d2fonts.Font) { - sizeless := font - sizeless.Size = 0 - ttf := r.ttfs[sizeless] - if ttf == nil { - panic(fmt.Errorf("sizeless font %s not found with style %s", font.Family, font.Style)) +func (r *Ruler) HasFontFamilyLoaded(fontFamily *d2fonts.FontFamily) bool { + for _, fontStyle := range d2fonts.FontStyles { + font := d2fonts.Font{ + Family: *fontFamily, + Style: fontStyle, + Size: SIZELESS_FONT_SIZE, + } + _, ok := r.ttfs[font] + if !ok { + return false + } } - face := truetype.NewFace(ttf, &truetype.Options{ + return true +} + +func (r *Ruler) addFontSize(font d2fonts.Font) { + sizeless := font + sizeless.Size = SIZELESS_FONT_SIZE + face := truetype.NewFace(r.ttfs[sizeless], &truetype.Options{ Size: float64(font.Size), }) atlas := NewAtlas(face, ASCII)