package door

import (
	"testing"
)

func pctUpdate(pct *int64) func() int64 {
	return func() int64 {
		return *pct
	}
}

func TestBarsUnicode(t *testing.T) {
	// verify that the BARS_CP437 matches BARS_UNICODE

	cp437 := BARS_CP437.solid
	convert := CP437_to_Unicode(cp437)
	unicode := BARS_UNICODE.solid
	if convert != unicode {
		t.Errorf("BARS solid: %#v != %#v\n", unicode, convert)
	}

	for half := 0; half < 2; half++ {
		cp437 := BARS_CP437.half[half]
		convert := CP437_to_Unicode(cp437)
		unicode := BARS_UNICODE.half[half]
		if convert != unicode {
			t.Errorf("BARS half[%d]: %#v != %#v\n", half, unicode, convert)
		}
	}

	for grad := 0; grad < 4; grad++ {
		cp437 := BARS_CP437.gradient[grad]
		convert := CP437_to_Unicode(cp437)
		unicode := BARS_UNICODE.gradient[grad]
		if convert != unicode {
			t.Errorf("BARS gradient[%d]: %#v != %#v\n", grad, unicode, convert)
		}
	}
}

func TestBars(t *testing.T) {

	// This is normally done by door init, but we're skipping that right now
	Unicode = true
	BARS = BARS_UNICODE

	BarColor := ColorText("BLUE")

	Bar25 := ColorText("RED")
	Bar50 := ColorText("BROWN")
	Bar75 := ColorText("BOLD YEL")
	Bar95 := ColorText("GREEN")
	Bar100 := ColorText("BRI GREEN")

	bar := BarLine{Line: Line{DefaultColor: BarColor}, Width: 10, Style: SOLID}
	bar.ColorRange = []BarRange{
		{2500, Bar25},
		{5000, Bar50},
		{7500, Bar75},
		{9500, Bar95},
		{10100, Bar100}}

	BarSolid := map[int]string{0: Bar25 + "          ",
		5:   Bar25 + "          ",
		10:  Bar25 + "\u2588         ",
		20:  Bar25 + "\u2588\u2588        ",
		25:  Bar25 + "\u2588\u2588        ",
		30:  Bar50 + "\u2588\u2588\u2588       ",
		50:  Bar50 + "\u2588\u2588\u2588\u2588\u2588     ",
		75:  Bar75 + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588   ",
		90:  Bar95 + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588 ",
		95:  Bar95 + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588 ",
		100: Bar100 + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588",
	}

	for pct, text := range BarSolid {
		bar.Percent = int64(pct * 100)
		got := bar.Output()
		if got != text {
			t.Errorf("BarSolidRange: Expected %#v (%d%%), got %#v", text, pct, got)
		}
	}

	BarColor = ColorText("BLA ON WHI")
	bar = BarLine{Line: Line{DefaultColor: BarColor}, Width: 10, Style: HALF_STEP, PercentStyle: PERCENT_SPACE}
	BarHalf := map[int]string{0: BarColor + "     0%   ",
		5:   BarColor + "\u258c    5%   ",
		6:   BarColor + "\u258c    6%   ",
		10:  BarColor + "\u2588   10%   ",
		20:  BarColor + "\u2588\u2588  20%   ",
		25:  BarColor + "\u2588\u2588\u258c 25%   ",
		26:  BarColor + "\u2588\u2588\u258c 26%   ",
		50:  BarColor + "\u2588\u2588\u2588 50%   ",
		75:  BarColor + "\u2588\u2588\u2588 75%   ",
		90:  BarColor + "\u2588\u2588\u2588 90% \u2588 ",
		100: BarColor + "\u2588\u2588\u2588 100 \u2588\u2588",
	}

	for pct, text := range BarHalf {
		bar.Percent = int64(pct * 100)
		got := bar.Output()
		if got != text {
			t.Errorf("BarHalf: Expected %#v (%d%%), got %#v", text, pct, got)
		}
	}

	BarColor = ColorText("RED")
	bar = BarLine{Line: Line{DefaultColor: BarColor}, Width: 10, Style: GRADIENT}
	BarGrad := map[int]string{0: BarColor + "          ",
		3:   BarColor + "\u2591         ",
		5:   BarColor + "\u2592         ",
		8:   BarColor + "\u2593         ",
		10:  BarColor + "\u2588         ",
		20:  BarColor + "\u2588\u2588        ",
		25:  BarColor + "\u2588\u2588\u2592       ",
		50:  BarColor + "\u2588\u2588\u2588\u2588\u2588     ",
		75:  BarColor + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2592  ",
		100: BarColor + "\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2588",
	}

	var percent int64
	bar.UpdateP = pctUpdate(&percent)

	for pct, text := range BarGrad {
		percent = int64(pct * 100)
		got := bar.Output()
		if got != text {
			t.Errorf("BarGradient: Expected %#v (%d%%), got %#v", text, pct, got)
		}
	}

}