Implemented RenderSequence for MarkdownTextRenderer.
This commit is contained in:
parent
e7de9eabe6
commit
31f6e9a66d
@ -8,13 +8,7 @@ import (
|
|||||||
// TextRender adds common methods for rendering a text on screeen.
|
// TextRender adds common methods for rendering a text on screeen.
|
||||||
type TextRender interface {
|
type TextRender interface {
|
||||||
NormalizedText(text string) string
|
NormalizedText(text string) string
|
||||||
RenderSequence(text string, lastColor, background Attribute) RenderedSubsequence
|
RenderSequence(text string, lastColor, background Attribute) RenderedSequence
|
||||||
}
|
|
||||||
|
|
||||||
type subSecequence struct {
|
|
||||||
start int
|
|
||||||
end int
|
|
||||||
color Attribute
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// MarkdownRegex is used by MarkdownTextRenderer to determine how to format the
|
// MarkdownRegex is used by MarkdownTextRenderer to determine how to format the
|
||||||
@ -33,50 +27,61 @@ type MarkdownTextRenderer struct{}
|
|||||||
// NormalizedText returns the text the user will see (without colors).
|
// NormalizedText returns the text the user will see (without colors).
|
||||||
// It strips out all formatting option and only preserves plain text.
|
// It strips out all formatting option and only preserves plain text.
|
||||||
func (r MarkdownTextRenderer) NormalizedText(text string) string {
|
func (r MarkdownTextRenderer) NormalizedText(text string) string {
|
||||||
lText := strings.ToLower(text)
|
return r.RenderSequence(text, 0, 0).NormalizedText
|
||||||
indexes := markdownPattern.FindAllStringSubmatchIndex(lText, -1)
|
|
||||||
|
|
||||||
// Interate through indexes in reverse order.
|
|
||||||
for i := len(indexes) - 1; i >= 0; i-- {
|
|
||||||
theIndex := indexes[i]
|
|
||||||
start, end := theIndex[0], theIndex[1]
|
|
||||||
contentStart, contentEnd := theIndex[2], theIndex[3]
|
|
||||||
|
|
||||||
text = text[:start] + text[contentStart:contentEnd] + text[end:]
|
|
||||||
}
|
|
||||||
|
|
||||||
return text
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// RenderedSubsequence is a string sequence that is capable of returning the
|
/*
|
||||||
|
RenderSequence renders the sequence `text` using a markdown-like syntax:
|
||||||
|
`[hello](red) world` will become: `hello world` where hello is red.
|
||||||
|
|
||||||
|
You may also specify other attributes such as bold text:
|
||||||
|
`[foo](YELLOW, BOLD)` will become `foo` in yellow, bold text.
|
||||||
|
|
||||||
|
|
||||||
|
For all available combinations, colors, and attribute, see: `StringToAttribute`.
|
||||||
|
|
||||||
|
This method returns a RenderedSequence
|
||||||
|
*/
|
||||||
|
func (r MarkdownTextRenderer) RenderSequence(text string, lastColor, background Attribute) RenderedSequence {
|
||||||
|
getMatch := func(s string) []int {
|
||||||
|
return markdownPattern.FindStringSubmatchIndex(strings.ToLower(s))
|
||||||
|
}
|
||||||
|
|
||||||
|
var sequences []ColorSubsequence
|
||||||
|
for match := getMatch(text); match != nil; match = getMatch(text) {
|
||||||
|
start, end := match[0], match[1]
|
||||||
|
colorStart, colorEnd := match[4], match[5]
|
||||||
|
contentStart, contentEnd := match[2], match[3]
|
||||||
|
|
||||||
|
color := strings.ToUpper(text[colorStart:colorEnd])
|
||||||
|
content := text[contentStart:contentEnd]
|
||||||
|
theSequence := ColorSubsequence{color, contentStart - 1, contentEnd - 1}
|
||||||
|
|
||||||
|
sequences = append(sequences, theSequence)
|
||||||
|
text = text[:start] + content + text[end:]
|
||||||
|
}
|
||||||
|
|
||||||
|
return RenderedSequence{text, lastColor, background, sequences}
|
||||||
|
}
|
||||||
|
|
||||||
|
// RenderedSequence is a string sequence that is capable of returning the
|
||||||
// Buffer used by termui for displaying the colorful string.
|
// Buffer used by termui for displaying the colorful string.
|
||||||
type RenderedSubsequence struct {
|
type RenderedSequence struct {
|
||||||
RawText string
|
|
||||||
NormalizedText string
|
NormalizedText string
|
||||||
LastColor Attribute
|
LastColor Attribute
|
||||||
BackgroundColor Attribute
|
BackgroundColor Attribute
|
||||||
|
Sequences []ColorSubsequence
|
||||||
|
}
|
||||||
|
|
||||||
sequences subSecequence
|
// A ColorSubsequence represents a color for the given text span.
|
||||||
|
type ColorSubsequence struct {
|
||||||
|
Color string // TODO: use attribute
|
||||||
|
Start int
|
||||||
|
End int
|
||||||
}
|
}
|
||||||
|
|
||||||
// Buffer returns the colorful formatted buffer and the last color that was
|
// Buffer returns the colorful formatted buffer and the last color that was
|
||||||
// used.
|
// used.
|
||||||
func (s *RenderedSubsequence) Buffer(x, y int) ([]Point, Attribute) {
|
func (s *RenderedSequence) Buffer(x, y int) ([]Point, Attribute) {
|
||||||
// var buffer []Point
|
|
||||||
// dx := 0
|
|
||||||
// for _, r := range []rune(s.NormalizedText) {
|
|
||||||
// p := Point{
|
|
||||||
// Ch: r,
|
|
||||||
// X: x + dx,
|
|
||||||
// Y: y,
|
|
||||||
// Fg: Attribute(rand.Intn(8)),
|
|
||||||
// Bg: background,
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// buffer = append(buffer, p)
|
|
||||||
// dx += charWidth(r)
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// return buffer
|
|
||||||
return nil, s.LastColor
|
return nil, s.LastColor
|
||||||
}
|
}
|
||||||
|
@ -6,15 +6,47 @@ import (
|
|||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func getMDRenderer() MarkdownTextRenderer {
|
||||||
|
return MarkdownTextRenderer{}
|
||||||
|
}
|
||||||
|
|
||||||
func TestMarkdownTextRenderer_NormalizedText(t *testing.T) {
|
func TestMarkdownTextRenderer_NormalizedText(t *testing.T) {
|
||||||
renderer := MarkdownTextRenderer{}
|
renderer := getMDRenderer()
|
||||||
|
|
||||||
got := renderer.NormalizedText("[ERROR](red,bold) Something went wrong")
|
got := renderer.NormalizedText("[ERROR](red,bold) Something went wrong")
|
||||||
assert.Equal(t, got, "ERROR Something went wrong")
|
assert.Equal(t, got, "ERROR Something went wrong")
|
||||||
|
|
||||||
got = renderer.NormalizedText("[foo](g) hello [bar](green) world")
|
got = renderer.NormalizedText("[foo](red) hello [bar](green) world")
|
||||||
assert.Equal(t, got, "foo hello bar world")
|
assert.Equal(t, got, "foo hello bar world")
|
||||||
|
|
||||||
got = renderer.NormalizedText("[foo](g) hello [bar]green (world)")
|
got = renderer.NormalizedText("[foo](g) hello [bar]green (world)")
|
||||||
assert.Equal(t, got, "foo hello [bar]green (world)")
|
assert.Equal(t, got, "foo hello [bar]green (world)")
|
||||||
|
|
||||||
|
// FIXME: [[ERROR]](red,bold) test should normalize to:
|
||||||
|
// [ERROR] test
|
||||||
|
}
|
||||||
|
|
||||||
|
func assertRenderSequence(t *testing.T, sequence RenderedSequence, last, background Attribute, text string, lenSequences int) {
|
||||||
|
assert.Equal(t, last, sequence.LastColor)
|
||||||
|
assert.Equal(t, background, sequence.BackgroundColor)
|
||||||
|
assert.Equal(t, text, sequence.NormalizedText)
|
||||||
|
assert.Equal(t, lenSequences, len(sequence.Sequences))
|
||||||
|
}
|
||||||
|
|
||||||
|
func assertColorSubsequence(t *testing.T, s ColorSubsequence, color string, start, end int) {
|
||||||
|
assert.Equal(t, ColorSubsequence{color, start, end}, s)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestMarkdownTextRenderer_RenderSequence(t *testing.T) {
|
||||||
|
renderer := getMDRenderer()
|
||||||
|
|
||||||
|
got := renderer.RenderSequence("[ERROR](red,bold) something went wrong", 3, 5)
|
||||||
|
assertRenderSequence(t, got, 3, 5, "ERROR something went wrong", 1)
|
||||||
|
assertColorSubsequence(t, got.Sequences[0], "RED,BOLD", 0, 5)
|
||||||
|
|
||||||
|
got = renderer.RenderSequence("[foo](red) hello [bar](green) world", 7, 2)
|
||||||
|
assertRenderSequence(t, got, 3, 2, "foo hello bar world", 2)
|
||||||
|
|
||||||
|
assertColorSubsequence(t, got.Sequences[0], "RED", 0, 3)
|
||||||
|
assertColorSubsequence(t, got.Sequences[1], "GREEN", 10, 13)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user