diff --git a/widgets/text/text.go b/widgets/text/text.go index 8a64249..eecb466 100644 --- a/widgets/text/text.go +++ b/widgets/text/text.go @@ -85,7 +85,11 @@ func New(opts ...Option) (*Text, error) { func (t *Text) Reset() { t.mu.Lock() defer t.mu.Unlock() + t.reset() +} +// reset implements Reset, caller must hold t.mu. +func (t *Text) reset() { t.buff.Reset() t.givenWOpts = nil t.wOptsTracker = attrrange.NewTracker() @@ -109,8 +113,13 @@ func (t *Text) Write(text string, wOpts ...WriteOption) error { return err } + opts := newWriteOptions(wOpts...) + if opts.replace { + t.reset() + } + pos := t.buff.Len() - t.givenWOpts = append(t.givenWOpts, newWriteOptions(wOpts...)) + t.givenWOpts = append(t.givenWOpts, opts) wOptsIdx := len(t.givenWOpts) - 1 if err := t.wOptsTracker.Add(pos, pos+len(text), wOptsIdx); err != nil { return err diff --git a/widgets/text/text_test.go b/widgets/text/text_test.go index 29fa4e8..5433d66 100644 --- a/widgets/text/text_test.go +++ b/widgets/text/text_test.go @@ -133,6 +133,24 @@ func TestTextDraws(t *testing.T) { return ft }, }, + { + desc: "multiple writes replace when requested", + canvas: image.Rect(0, 0, 12, 1), + writes: func(widget *Text) error { + if err := widget.Write("hello", WriteReplace()); err != nil { + return err + } + return widget.Write("world", WriteReplace()) + }, + want: func(size image.Point) *faketerm.Terminal { + ft := faketerm.MustNew(size) + c := testcanvas.MustNew(ft.Area()) + + testdraw.MustText(c, "world", image.Point{0, 0}) + testcanvas.MustApply(c, ft) + return ft + }, + }, { desc: "reset clears the content", canvas: image.Rect(0, 0, 12, 1), diff --git a/widgets/text/write_options.go b/widgets/text/write_options.go index 1c94a04..ddb5c40 100644 --- a/widgets/text/write_options.go +++ b/widgets/text/write_options.go @@ -29,6 +29,7 @@ type WriteOption interface { // writeOptions stores the provided options. type writeOptions struct { cellOpts *cell.Options + replace bool } // newWriteOptions returns new writeOptions instance. @@ -56,3 +57,11 @@ func WriteCellOpts(opts ...cell.Option) WriteOption { wOpts.cellOpts = cell.NewOptions(opts...) }) } + +// WriteReplace instructs the text widget to replace the entire text content on +// this write instead of appending. +func WriteReplace() WriteOption { + return writeOption(func(wOpts *writeOptions) { + wOpts.replace = true + }) +}