Files
MujicaUI/count_up_test.go
T

131 lines
3.5 KiB
Go

package mujica
import (
"fmt"
"math"
"strings"
"testing"
"time"
"github.com/egoist/mygo/ui"
)
func TestCountUpCountsAndSettles(t *testing.T) {
value := 100.0
tt, n := motionFrames(func(c *ui.Context) {
CountUp(c, value, CountUpOptions{Duration: 300 * time.Millisecond})
}, 200, 60)
if !tt.HasText("100") || motionBusy(tt, n) {
t.Fatalf("first value shown at once: %q", tt.Texts())
}
value = 200
tt.Frame()
time.Sleep(100 * time.Millisecond)
tt.Frame()
mid := ""
for _, s := range tt.Texts() {
if s != "200" {
mid = s
}
}
if mid == "" || mid == "100" {
t.Fatalf("no value between: %q", tt.Texts())
}
time.Sleep(300 * time.Millisecond)
tt.Frame()
if motionCount(tt, "200") != 2 || motionBusy(tt, n) {
t.Fatalf("did not settle: %q", tt.Texts())
}
tt.SetPreferences(ui.Preferences{ReduceMotion: true, TextScale: 1})
value = 5
tt.Frame()
if motionCount(tt, "5") != 2 {
t.Fatalf("reduced motion did not jump: %q", tt.Texts())
}
}
func TestCountUpFormatAndInvalid(t *testing.T) {
tt := ui.NewTester(func(c *ui.Context) {
Use(c, Settings{})
CountUp(c, 12.345, CountUpOptions{Decimals: 1})
CountUp(c, 3, CountUpOptions{Format: func(v float64) string { return fmt.Sprintf("%.0f items", v) }})
}, 300, 80)
if !tt.HasText("12.3") || !tt.HasText("3 items") {
t.Fatalf("format: %q", tt.Texts())
}
for _, o := range []CountUpOptions{{Duration: -1}, {Decimals: -1}} {
func() {
defer func() {
if recover() == nil {
t.Errorf("%+v did not panic", o)
}
}()
ui.Render(func(c *ui.Context) { Use(c, Settings{}); CountUp(c, 1, o) }, 100, 50, 1)
}()
}
defer func() {
if r := recover(); r == nil || !strings.Contains(fmt.Sprint(r), "finite") {
t.Fatal("NaN did not panic")
}
}()
ui.Render(func(c *ui.Context) { Use(c, Settings{}); CountUp(c, nanValue(), CountUpOptions{}) }, 100, 50, 1)
}
func nanValue() float64 {
zero := 0.0
return zero / zero
}
func TestCountUpSnapshot(t *testing.T) {
snapshot(t, "count_up", 300, 100, func(c *ui.Context) {
ui.Column(c).Padding(16).Gap(8).Children(func() {
CountUp(c, 12840, CountUpOptions{}).FontSize(FontSize(c, 28)).Font("Georgia, serif")
CountUp(c, 0.875, CountUpOptions{Format: func(v float64) string { return fmt.Sprintf("%.1f%%", v*100) }})
})
})
}
func TestCountUpFiniteExtremeInterpolation(t *testing.T) {
value := -math.MaxFloat64
tt, _ := motionFrames(func(c *ui.Context) {
CountUp(c, value, CountUpOptions{Duration: time.Second, Format: func(v float64) string {
if math.IsNaN(v) || math.IsInf(v, 0) {
t.Fatal("finite endpoints produced non-finite text")
}
return fmt.Sprintf("%g", v)
}})
}, 300, 80)
value = math.MaxFloat64
tt.Frame()
}
func TestCountUpOffscreenStopsFrames(t *testing.T) {
value := 1.0
tt, n := motionFrames(func(c *ui.Context) {
ui.Column(c).Height(80).Clip().Children(func() {
ui.Box(c).Size(10, 200).Shrink(0)
CountUp(c, value, CountUpOptions{Duration: time.Second})
})
}, 300, 80)
value = 2
tt.Frame()
if motionBusy(tt, n) {
t.Fatal("offscreen CountUp requested continuous rebuilds")
}
}
func TestCountUpRestoredMotionKeepsFinalValue(t *testing.T) {
value := 0.0
shown := 0.0
tt, n := motionFrames(func(c *ui.Context) {
CountUp(c, value, CountUpOptions{Duration: 5 * time.Second, Format: func(v float64) string { shown = v; return fmt.Sprintf("%g", v) }})
}, 300, 100)
value = 100
tt.Frame()
tt.SetPreferences(ui.Preferences{ReduceMotion: true, TextScale: 1})
tt.SetPreferences(ui.Preferences{TextScale: 1})
if shown != 100 || motionBusy(tt, n) {
t.Fatalf("restored value %v", shown)
}
}