forked from stathissideris/ditaa
-
Notifications
You must be signed in to change notification settings - Fork 5
/
images_test.go
132 lines (121 loc) · 2.99 KB
/
images_test.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
package main
import (
"bytes"
"flag"
"fmt"
"image"
"image/color"
"image/png"
"io/ioutil"
"os"
"path/filepath"
"testing"
)
var reset = flag.Bool("reset", false, "rebuild reference images")
func init() {
flag.Parse()
}
func TestImageResults(test *testing.T) {
test.Skip("FIXME(akavel): shows stupid diffs in corners of rectangles :/")
err := filepath.Walk("orig-java/tests/text", func(path string, info os.FileInfo, err error) error {
switch {
case err != nil:
return err
case info.IsDir():
return nil
case filepath.Ext(info.Name()) != ".txt":
return nil
}
r, err := os.Open(path)
if err != nil {
test.Error(err)
return nil
}
defer r.Close()
w := bytes.NewBuffer(nil)
err = RenderPNG(r, w)
if err != nil {
test.Errorf("%s: %s", path, err)
return nil
}
fname, ext := info.Name(), filepath.Ext(info.Name())
fname = fname[:len(fname)-len(ext)]
fname = filepath.Join("testdata", fname+".png")
if *reset {
os.MkdirAll("testdata", 0755)
ioutil.WriteFile(fname, w.Bytes(), 0644)
}
err = diffimg(fname, w)
if err != nil {
test.Errorf("%s: %s", path, err)
return nil
}
return nil
})
if err != nil {
test.Error(err)
}
}
func diffimg(path string, buf *bytes.Buffer) error {
r, err := os.Open(path)
if err != nil {
return err
}
defer r.Close()
oldImg, err := png.Decode(r)
if err != nil {
return fmt.Errorf("decoding %s: %s", path, err)
}
newBytes := buf.Bytes()
newImg, err := png.Decode(buf)
if err != nil {
return fmt.Errorf("decoding rendered PNG: %s", err)
}
// Compare the images.
bounds := oldImg.Bounds()
if newImg.Bounds() != bounds {
return fmt.Errorf("bounds differ, expected %v, got %v", bounds, newImg.Bounds())
}
var diff *image.RGBA
for y := bounds.Min.Y; y < bounds.Max.Y; y++ {
for x := bounds.Min.X; x < bounds.Max.X; x++ {
oldpx := oldImg.At(x, y)
newpx := newImg.At(x, y)
if !colorsEqual(oldpx, newpx) {
// Difference - draw it in "pink" color.
if diff == nil {
diff = image.NewRGBA(bounds)
}
diff.Set(x, y, color.RGBA{255, 0, 255, 255})
}
}
}
// If images are different, write "difference mask" to testdata/*-diff.png, and
// "bad image" to testdata/*-testfail.png
if diff != nil {
fname, ext := filepath.Base(path), filepath.Ext(path)
fname = fname[:len(fname)-len(ext)]
diffname, outname := "testdata/"+fname+"-diff.png", "testdata/"+fname+"-testfail.png"
diffbuf := bytes.NewBuffer(nil)
err := png.Encode(diffbuf, diff)
if err != nil {
return fmt.Errorf("cannot encode %s: %s", diffname, err)
}
err = ioutil.WriteFile(diffname, diffbuf.Bytes(), 0644)
if err != nil {
return err
}
err = ioutil.WriteFile(outname, newBytes, 0644)
if err != nil {
return err
}
return fmt.Errorf("rendered image differs from %s, mask written to %s, image to %s",
path, diffname, outname)
}
return nil
}
func colorsEqual(c1, c2 color.Color) bool {
r1, g1, b1, a1 := c1.RGBA()
r2, g2, b2, a2 := c2.RGBA()
return r1 == r2 && g1 == g2 && b1 == b2 && a1 == a2
}