55 "strings"
66
77 "github.com/gookit/color"
8+ "github.com/mattn/go-runewidth"
89 log "github.com/sirupsen/logrus"
910)
1011
@@ -48,10 +49,17 @@ func (g *graph) drawEdge(e *edge) (*drawing, *drawing, *drawing, *drawing, *draw
4849
4950func (d * drawing ) drawText (start drawingCoord , text string ) {
5051 // Increase dimensions if necessary.
51- d .increaseSize (start .x + len (text ), start .y )
52- log .Debug ("Drawing '" , text , "' from " , start , " to " , drawingCoord {x : start .x + len (text ), y : start .y })
53- for x := 0 ; x < len (text ); x ++ {
54- (* d )[x + start .x ][start .y ] = string (text [x ])
52+ textWidth := runewidth .StringWidth (text )
53+ d .increaseSize (start .x + textWidth , start .y )
54+ log .Debug ("Drawing '" , text , "' from " , start , " to " , drawingCoord {x : start .x + textWidth , y : start .y })
55+ pos := 0
56+ for _ , char := range text {
57+ (* d )[start .x + pos ][start .y ] = string (char )
58+ charWidth := runewidth .RuneWidth (char )
59+ for i := 1 ; i < charWidth ; i ++ {
60+ (* d )[start .x + pos + i ][start .y ] = ""
61+ }
62+ pos += charWidth
5563 }
5664}
5765
@@ -228,10 +236,17 @@ func drawBox(n *node, g graph) *drawing {
228236 boxDrawing [to.x ][to.y ] = "+" // Bottom right corner
229237 }
230238 // Draw text
239+ nameWidth := runewidth .StringWidth (n .name )
231240 textY := from .y + h / 2
232- textX := from .x + w / 2 - CeilDiv (len (n .name ), 2 ) + 1
233- for x := 0 ; x < len (n .name ); x ++ {
234- boxDrawing [textX + x ][textY ] = wrapTextInColor (string (n .name [x ]), n .styleClass .styles ["color" ], g .styleType )
241+ textX := from .x + w / 2 - CeilDiv (nameWidth , 2 ) + 1
242+ pos := 0
243+ for _ , char := range n .name {
244+ boxDrawing [textX + pos ][textY ] = wrapTextInColor (string (char ), n .styleClass .styles ["color" ], g .styleType )
245+ charWidth := runewidth .RuneWidth (char )
246+ for i := 1 ; i < charWidth ; i ++ {
247+ boxDrawing [textX + pos + i ][textY ] = ""
248+ }
249+ pos += charWidth
235250 }
236251
237252 return & boxDrawing
@@ -317,15 +332,24 @@ func drawSubgraphLabel(sg *subgraph, g graph) (*drawing, drawingCoord) {
317332 labelDrawing := * (mkDrawing (width , height ))
318333
319334 // Draw label centered at top
335+ nameWidth := runewidth .StringWidth (sg .name )
320336 labelY := from .y + 1
321- labelX := from .x + width / 2 - len ( sg . name ) / 2
337+ labelX := from .x + width / 2 - nameWidth / 2
322338 if labelX < from .x + 1 {
323339 labelX = from .x + 1
324340 }
325- for i , char := range sg .name {
326- if labelX + i < to .x {
327- labelDrawing [labelX + i ][labelY ] = string (char )
341+ pos := 0
342+ for _ , char := range sg .name {
343+ if labelX + pos < to .x {
344+ labelDrawing [labelX + pos ][labelY ] = string (char )
345+ charWidth := runewidth .RuneWidth (char )
346+ for i := 1 ; i < charWidth ; i ++ {
347+ if labelX + pos + i < to .x {
348+ labelDrawing [labelX + pos + i ][labelY ] = ""
349+ }
350+ }
328351 }
352+ pos += runewidth .RuneWidth (char )
329353 }
330354
331355 // Return label drawing and its offset position
@@ -337,12 +361,20 @@ func wrapTextInColor(text, c, styleType string) string {
337361 if c == "" {
338362 return text
339363 }
340- if styleType == "html" {
364+ switch styleType {
365+ case "html" :
341366 return fmt .Sprintf ("<span style='color: %s'>%s</span>" , c , text )
342- } else if styleType == "cli" {
367+ case "xterm" :
368+ var r , g , b int
369+ if _ , err := fmt .Sscanf (c , "#%02x%02x%02x" , & r , & g , & b ); err != nil {
370+ log .Warnf ("Invalid xterm color %s" , c )
371+ return text
372+ }
373+ return fmt .Sprintf ("\x1b [38;2;%d;%d;%dm%s\x1b [39m" , r , g , b , text )
374+ case "cli" :
343375 cliColor := color .HEX (c )
344376 return cliColor .Sprint (text )
345- } else {
377+ default :
346378 log .Warnf ("Unknown style type %s" , styleType )
347379 return text
348380 }
0 commit comments