diff options
Diffstat (limited to 'src/util/util.go')
-rw-r--r-- | src/util/util.go | 33 |
1 files changed, 20 insertions, 13 deletions
diff --git a/src/util/util.go b/src/util/util.go index 0aa1d804..59fb5708 100644 --- a/src/util/util.go +++ b/src/util/util.go @@ -7,22 +7,29 @@ import ( "github.com/mattn/go-isatty" "github.com/mattn/go-runewidth" + "github.com/rivo/uniseg" ) -var _runeWidths = make(map[rune]int) - -// RuneWidth returns rune width -func RuneWidth(r rune, prefixWidth int, tabstop int) int { - if r == '\t' { - return tabstop - prefixWidth%tabstop - } else if w, found := _runeWidths[r]; found { - return w - } else if r == '\n' || r == '\r' { - return 1 +// RunesWidth returns runes width +func RunesWidth(runes []rune, prefixWidth int, tabstop int, limit int) (int, int) { + width := 0 + gr := uniseg.NewGraphemes(string(runes)) + idx := 0 + for gr.Next() { + rs := gr.Runes() + var w int + if len(rs) == 1 && rs[0] == '\t' { + w = tabstop - (prefixWidth+width)%tabstop + } else { + w = runewidth.StringWidth(string(rs)) + } + width += w + if limit > 0 && width > limit { + return width, idx + } + idx += len(rs) } - w := runewidth.RuneWidth(r) - _runeWidths[r] = w - return w + return width, -1 } // Max returns the largest integer |