Files
ZacharyZhang-NY 51af14709d Add code components 366-385; ScrollArea Follow, editor sync
A terminal with history, a Go-colored code block, a log viewer that
follows, a hex viewer, a memory map, a JSON tree, a line diff, a GAME
OVER crash screen, an FPS meter, profiler bars, breakpoints,
variables, command history, a shortcut list, a debug grid, a pixel
editor that exports string art, a palette editor, a sprite sheet, a
glyph map and a 6502 register view.

layout.ScrollArea takes Follow, and ChatLog now uses it. data.TreeNode
takes a Value drawn in its Slot. pixel gains Has, and Sprite.Art
writes MustSprite art. pixel.Editor takes the caller's value at each
input event, so a value changed between frames is never typed onto.
2026-10-12 07:18:30 -04:00

53 lines
1.2 KiB
Go

package layout_test
import (
"testing"
"github.com/egoist/mygo/ui"
"git.zacharyzhang.com/ZacharyZhang-NY/8bitMyGoUI/layout"
"git.zacharyzhang.com/ZacharyZhang-NY/8bitMyGoUI/pixel"
)
func TestScrollAreaFollowsItsEndWhileThere(t *testing.T) {
s, n, follow := ui.ScrollState{}, 10, true
tt := ui.NewTester(func(c *ui.Context) {
pixel.Use(c, pixel.Settings{Palette: pixel.SpringDay})
layout.ScrollArea(c, &s, layout.ScrollAreaOptions{Label: "Log", Follow: follow}, func() {
for range n {
ui.Box(c).Height(32)
}
}).Element.Size(200, 100)
}, 300, 200)
tt.Frame()
if s.MaxY == 0 || s.Y != s.MaxY {
t.Fatalf("a following view opened at %v of %v", s.Y, s.MaxY)
}
n++
tt.Frame()
if s.Y != s.MaxY {
t.Fatalf("at the end, a new row left the view at %v of %v", s.Y, s.MaxY)
}
// Scrolled up it stays; back at the end, it follows.
s.Y = 0
n++
tt.Frame()
if s.Y != 0 {
t.Fatalf("scrolled up, the view jumped to %v", s.Y)
}
s.Y = s.MaxY
tt.Frame()
n++
tt.Frame()
if s.Y != s.MaxY {
t.Fatalf("back at the end, the view stopped following at %v of %v", s.Y, s.MaxY)
}
// Without Follow, growth leaves the view alone.
follow, s = false, ui.ScrollState{}
n++
tt.Frame()
if s.Y != 0 {
t.Fatalf("a plain view followed to %v", s.Y)
}
}