sanity check tests.
This commit is contained in:
parent
10950a3bf2
commit
8b34cb3bd7
|
@ -48,7 +48,33 @@ func drawChart(res http.ResponseWriter, req *http.Request) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func unit(res http.ResponseWriter, req *http.Request) {
|
||||||
|
graph := chart.Chart{
|
||||||
|
Height: 50,
|
||||||
|
Width: 50,
|
||||||
|
Canvas: chart.Style{
|
||||||
|
Padding: chart.Box{IsSet: true},
|
||||||
|
},
|
||||||
|
Background: chart.Style{
|
||||||
|
Padding: chart.Box{IsSet: true},
|
||||||
|
},
|
||||||
|
Series: []chart.Series{
|
||||||
|
chart.ContinuousSeries{
|
||||||
|
XValues: chart.Sequence.Float64(0, 4, 1),
|
||||||
|
YValues: chart.Sequence.Float64(0, 4, 1),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
res.Header().Set("Content-Type", "image/png")
|
||||||
|
err := graph.Render(chart.PNG, res)
|
||||||
|
if err != nil {
|
||||||
|
log.Println(err.Error())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
http.HandleFunc("/", drawChart)
|
http.HandleFunc("/", drawChart)
|
||||||
|
http.HandleFunc("/unit", unit)
|
||||||
log.Fatal(http.ListenAndServe(":8080", nil))
|
log.Fatal(http.ListenAndServe(":8080", nil))
|
||||||
}
|
}
|
||||||
|
|
29
box.go
29
box.go
|
@ -5,8 +5,25 @@ import (
|
||||||
"math"
|
"math"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
// BoxZero is a preset box that represents an intentional zero value.
|
||||||
|
BoxZero = Box{IsSet: true}
|
||||||
|
)
|
||||||
|
|
||||||
|
// NewBox returns a new (set) box.
|
||||||
|
func NewBox(top, left, right, bottom int) Box {
|
||||||
|
return Box{
|
||||||
|
IsSet: true,
|
||||||
|
Top: top,
|
||||||
|
Left: left,
|
||||||
|
Right: right,
|
||||||
|
Bottom: bottom,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Box represents the main 4 dimensions of a box.
|
// Box represents the main 4 dimensions of a box.
|
||||||
type Box struct {
|
type Box struct {
|
||||||
|
IsSet bool
|
||||||
Top int
|
Top int
|
||||||
Left int
|
Left int
|
||||||
Right int
|
Right int
|
||||||
|
@ -15,6 +32,9 @@ type Box struct {
|
||||||
|
|
||||||
// IsZero returns if the box is set or not.
|
// IsZero returns if the box is set or not.
|
||||||
func (b Box) IsZero() bool {
|
func (b Box) IsZero() bool {
|
||||||
|
if b.IsSet {
|
||||||
|
return false
|
||||||
|
}
|
||||||
return b.Top == 0 && b.Left == 0 && b.Right == 0 && b.Bottom == 0
|
return b.Top == 0 && b.Left == 0 && b.Right == 0 && b.Bottom == 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -25,7 +45,7 @@ func (b Box) String() string {
|
||||||
|
|
||||||
// GetTop returns a coalesced value with a default.
|
// GetTop returns a coalesced value with a default.
|
||||||
func (b Box) GetTop(defaults ...int) int {
|
func (b Box) GetTop(defaults ...int) int {
|
||||||
if b.Top == 0 {
|
if !b.IsSet && b.Top == 0 {
|
||||||
if len(defaults) > 0 {
|
if len(defaults) > 0 {
|
||||||
return defaults[0]
|
return defaults[0]
|
||||||
}
|
}
|
||||||
|
@ -36,7 +56,7 @@ func (b Box) GetTop(defaults ...int) int {
|
||||||
|
|
||||||
// GetLeft returns a coalesced value with a default.
|
// GetLeft returns a coalesced value with a default.
|
||||||
func (b Box) GetLeft(defaults ...int) int {
|
func (b Box) GetLeft(defaults ...int) int {
|
||||||
if b.Left == 0 {
|
if !b.IsSet && b.Left == 0 {
|
||||||
if len(defaults) > 0 {
|
if len(defaults) > 0 {
|
||||||
return defaults[0]
|
return defaults[0]
|
||||||
}
|
}
|
||||||
|
@ -47,7 +67,7 @@ func (b Box) GetLeft(defaults ...int) int {
|
||||||
|
|
||||||
// GetRight returns a coalesced value with a default.
|
// GetRight returns a coalesced value with a default.
|
||||||
func (b Box) GetRight(defaults ...int) int {
|
func (b Box) GetRight(defaults ...int) int {
|
||||||
if b.Right == 0 {
|
if !b.IsSet && b.Right == 0 {
|
||||||
if len(defaults) > 0 {
|
if len(defaults) > 0 {
|
||||||
return defaults[0]
|
return defaults[0]
|
||||||
}
|
}
|
||||||
|
@ -58,7 +78,7 @@ func (b Box) GetRight(defaults ...int) int {
|
||||||
|
|
||||||
// GetBottom returns a coalesced value with a default.
|
// GetBottom returns a coalesced value with a default.
|
||||||
func (b Box) GetBottom(defaults ...int) int {
|
func (b Box) GetBottom(defaults ...int) int {
|
||||||
if b.Bottom == 0 {
|
if !b.IsSet && b.Bottom == 0 {
|
||||||
if len(defaults) > 0 {
|
if len(defaults) > 0 {
|
||||||
return defaults[0]
|
return defaults[0]
|
||||||
}
|
}
|
||||||
|
@ -91,6 +111,7 @@ func (b Box) Aspect() float64 {
|
||||||
// Clone returns a new copy of the box.
|
// Clone returns a new copy of the box.
|
||||||
func (b Box) Clone() Box {
|
func (b Box) Clone() Box {
|
||||||
return Box{
|
return Box{
|
||||||
|
IsSet: b.IsSet,
|
||||||
Top: b.Top,
|
Top: b.Top,
|
||||||
Left: b.Left,
|
Left: b.Left,
|
||||||
Right: b.Right,
|
Right: b.Right,
|
||||||
|
|
|
@ -109,9 +109,9 @@ func TestBoxConstrain(t *testing.T) {
|
||||||
func TestBoxOuterConstrain(t *testing.T) {
|
func TestBoxOuterConstrain(t *testing.T) {
|
||||||
assert := assert.New(t)
|
assert := assert.New(t)
|
||||||
|
|
||||||
box := Box{0, 0, 100, 100}
|
box := NewBox(0, 0, 100, 100)
|
||||||
canvas := Box{5, 5, 95, 95}
|
canvas := NewBox(5, 5, 95, 95)
|
||||||
taller := Box{-10, 5, 50, 50}
|
taller := NewBox(-10, 5, 50, 50)
|
||||||
|
|
||||||
c := canvas.OuterConstrain(box, taller)
|
c := canvas.OuterConstrain(box, taller)
|
||||||
assert.Equal(15, c.Top, c.String())
|
assert.Equal(15, c.Top, c.String())
|
||||||
|
@ -119,7 +119,7 @@ func TestBoxOuterConstrain(t *testing.T) {
|
||||||
assert.Equal(95, c.Right, c.String())
|
assert.Equal(95, c.Right, c.String())
|
||||||
assert.Equal(95, c.Bottom, c.String())
|
assert.Equal(95, c.Bottom, c.String())
|
||||||
|
|
||||||
wider := Box{5, 5, 110, 50}
|
wider := NewBox(5, 5, 110, 50)
|
||||||
d := canvas.OuterConstrain(box, wider)
|
d := canvas.OuterConstrain(box, wider)
|
||||||
assert.Equal(5, d.Top, d.String())
|
assert.Equal(5, d.Top, d.String())
|
||||||
assert.Equal(5, d.Left, d.String())
|
assert.Equal(5, d.Left, d.String())
|
||||||
|
|
|
@ -2,6 +2,8 @@ package chart
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
|
"image"
|
||||||
|
"image/png"
|
||||||
"math"
|
"math"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
|
@ -484,10 +486,22 @@ func TestChartCheckRangesWithRanges(t *testing.T) {
|
||||||
assert.Nil(c.checkRanges(xr, yr, yra))
|
assert.Nil(c.checkRanges(xr, yr, yra))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func at(i image.Image, x, y int) drawing.Color {
|
||||||
|
return drawing.ColorFromAlphaMixedRGBA(i.At(x, y).RGBA())
|
||||||
|
}
|
||||||
|
|
||||||
func TestChartE2ELine(t *testing.T) {
|
func TestChartE2ELine(t *testing.T) {
|
||||||
assert := assert.New(t)
|
assert := assert.New(t)
|
||||||
|
|
||||||
c := Chart{
|
c := Chart{
|
||||||
|
Height: 50,
|
||||||
|
Width: 50,
|
||||||
|
Canvas: Style{
|
||||||
|
Padding: Box{IsSet: true},
|
||||||
|
},
|
||||||
|
Background: Style{
|
||||||
|
Padding: Box{IsSet: true},
|
||||||
|
},
|
||||||
Series: []Series{
|
Series: []Series{
|
||||||
ContinuousSeries{
|
ContinuousSeries{
|
||||||
XValues: Sequence.Float64(0, 4, 1),
|
XValues: Sequence.Float64(0, 4, 1),
|
||||||
|
@ -502,5 +516,60 @@ func TestChartE2ELine(t *testing.T) {
|
||||||
|
|
||||||
// do color tests ...
|
// do color tests ...
|
||||||
|
|
||||||
|
i, err := png.Decode(buffer)
|
||||||
|
assert.Nil(err)
|
||||||
|
|
||||||
|
// test the bottom and top of the line
|
||||||
|
assert.Equal(drawing.ColorWhite, at(i, 0, 0))
|
||||||
|
assert.Equal(drawing.ColorWhite, at(i, 49, 49))
|
||||||
|
|
||||||
|
// test a line mid point
|
||||||
|
defaultSeriesColor := GetDefaultColor(0)
|
||||||
|
assert.Equal(defaultSeriesColor, at(i, 0, 49))
|
||||||
|
assert.Equal(defaultSeriesColor, at(i, 49, 0))
|
||||||
|
assert.Equal(drawing.ColorFromHex("bddbf6"), at(i, 24, 24))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestChartE2ELineWithFill(t *testing.T) {
|
||||||
|
assert := assert.New(t)
|
||||||
|
|
||||||
|
c := Chart{
|
||||||
|
Height: 50,
|
||||||
|
Width: 50,
|
||||||
|
Canvas: Style{
|
||||||
|
Padding: Box{IsSet: true},
|
||||||
|
},
|
||||||
|
Background: Style{
|
||||||
|
Padding: Box{IsSet: true},
|
||||||
|
},
|
||||||
|
Series: []Series{
|
||||||
|
ContinuousSeries{
|
||||||
|
Style: Style{
|
||||||
|
Show: true,
|
||||||
|
StrokeColor: drawing.ColorBlue,
|
||||||
|
FillColor: drawing.ColorRed,
|
||||||
|
},
|
||||||
|
XValues: Sequence.Float64(0, 4, 1),
|
||||||
|
YValues: Sequence.Float64(0, 4, 1),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
var buffer = &bytes.Buffer{}
|
||||||
|
err := c.Render(PNG, buffer)
|
||||||
|
assert.Nil(err)
|
||||||
|
|
||||||
|
// do color tests ...
|
||||||
|
|
||||||
|
i, err := png.Decode(buffer)
|
||||||
|
assert.Nil(err)
|
||||||
|
|
||||||
|
// test the bottom and top of the line
|
||||||
|
assert.Equal(drawing.ColorWhite, at(i, 0, 0))
|
||||||
|
assert.Equal(drawing.ColorRed, at(i, 49, 49))
|
||||||
|
|
||||||
|
// test a line mid point
|
||||||
|
defaultSeriesColor := drawing.ColorBlue
|
||||||
|
assert.Equal(defaultSeriesColor, at(i, 0, 49))
|
||||||
|
assert.Equal(defaultSeriesColor, at(i, 49, 0))
|
||||||
}
|
}
|
||||||
|
|
|
@ -104,6 +104,16 @@ func (c Color) Equals(other Color) bool {
|
||||||
c.A == other.A
|
c.A == other.A
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AverageWith averages two colors.
|
||||||
|
func (c Color) AverageWith(other Color) Color {
|
||||||
|
return Color{
|
||||||
|
R: (c.R + other.R) >> 1,
|
||||||
|
G: (c.G + other.G) >> 1,
|
||||||
|
B: (c.B + other.B) >> 1,
|
||||||
|
A: c.A,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// String returns a css string representation of the color.
|
// String returns a css string representation of the color.
|
||||||
func (c Color) String() string {
|
func (c Color) String() string {
|
||||||
fa := float64(c.A) / float64(255)
|
fa := float64(c.A) / float64(255)
|
||||||
|
|
|
@ -1,23 +0,0 @@
|
||||||
package drawing
|
|
||||||
|
|
||||||
import "image"
|
|
||||||
|
|
||||||
// Image is a helper wraper that allows (sane) access to pixel info.
|
|
||||||
type Image struct {
|
|
||||||
Inner *image.RGBA
|
|
||||||
}
|
|
||||||
|
|
||||||
// Width returns the image's width in pixels.
|
|
||||||
func (i Image) Width() int {
|
|
||||||
return i.Inner.Rect.Size().X
|
|
||||||
}
|
|
||||||
|
|
||||||
// Height returns the image's height in pixels.
|
|
||||||
func (i Image) Height() int {
|
|
||||||
return i.Inner.Rect.Size().Y
|
|
||||||
}
|
|
||||||
|
|
||||||
// At returns a pixel color at a given x/y.
|
|
||||||
func (i Image) At(x, y int) Color {
|
|
||||||
return ColorFromAlphaMixedRGBA(i.Inner.At(x, y).RGBA())
|
|
||||||
}
|
|
|
@ -61,7 +61,7 @@ func TestXAxisMeasure(t *testing.T) {
|
||||||
assert.Nil(err)
|
assert.Nil(err)
|
||||||
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
||||||
xa := XAxis{}
|
xa := XAxis{}
|
||||||
xab := xa.Measure(r, Box{0, 0, 100, 100}, &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
xab := xa.Measure(r, NewBox(0, 0, 100, 100), &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
||||||
assert.Equal(122, xab.Width())
|
assert.Equal(122, xab.Width())
|
||||||
assert.Equal(21, xab.Height())
|
assert.Equal(21, xab.Height())
|
||||||
}
|
}
|
||||||
|
|
|
@ -61,7 +61,7 @@ func TestYAxisMeasure(t *testing.T) {
|
||||||
assert.Nil(err)
|
assert.Nil(err)
|
||||||
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
||||||
ya := YAxis{}
|
ya := YAxis{}
|
||||||
yab := ya.Measure(r, Box{0, 0, 100, 100}, &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
yab := ya.Measure(r, NewBox(0, 0, 100, 100), &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
||||||
assert.Equal(32, yab.Width())
|
assert.Equal(32, yab.Width())
|
||||||
assert.Equal(110, yab.Height())
|
assert.Equal(110, yab.Height())
|
||||||
}
|
}
|
||||||
|
@ -79,7 +79,7 @@ func TestYAxisSecondaryMeasure(t *testing.T) {
|
||||||
assert.Nil(err)
|
assert.Nil(err)
|
||||||
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
ticks := []Tick{{Value: 1.0, Label: "1.0"}, {Value: 2.0, Label: "2.0"}, {Value: 3.0, Label: "3.0"}}
|
||||||
ya := YAxis{AxisType: YAxisSecondary}
|
ya := YAxis{AxisType: YAxisSecondary}
|
||||||
yab := ya.Measure(r, Box{0, 0, 100, 100}, &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
yab := ya.Measure(r, NewBox(0, 0, 100, 100), &ContinuousRange{Min: 1.0, Max: 3.0, Domain: 100}, style, ticks)
|
||||||
assert.Equal(32, yab.Width())
|
assert.Equal(32, yab.Width())
|
||||||
assert.Equal(110, yab.Height())
|
assert.Equal(110, yab.Height())
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user