-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdithering.go
86 lines (71 loc) · 1.59 KB
/
dithering.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
package main
import (
"image"
"image/draw"
)
func Dithering(img image.Gray) []byte {
var oldPixel, newPixel int
var error int
width := img.Bounds().Max.X
height := img.Bounds().Max.Y
origin := toByteArray(img)
result := make([]byte, width * height, width * height)
var min, max byte
var half int
min = 255
max = 0
half = 127
for i := 0; i < width*height; i++ {
if origin[i] < min {
min = origin[i]
}
if origin[i] > max {
max = origin[i]
}
}
half = (int(min) + int(max)) / 2
e := make([]int, width*2)
m := []int{0, 1, width-2, width-1, width, 2*width-1}
l := len(origin)
for idx := 0; idx < l; idx++ {
oldPixel = int(origin[idx]) + e[0]
e = append(e[1:], 0)
newPixel = findColor(oldPixel, half)
error=(oldPixel - newPixel)>>3
result[idx] = byte(newPixel / 255)
for _, k := range m {
e[k] += error
}
}
return result
}
func addV(target *[]byte, pos, v int) {
arr := *target
if (pos >= len(arr)) {
return
}
arr[pos] = byte(int(arr[pos]) + v)
}
func toByteArray(img image.Gray) []byte {
width := img.Bounds().Dx()
height := img.Bounds().Dy()
origin := make([]byte, width*height)
for y := 0; y < height; y++ {
for x := 0; x < width; x++ {
origin[y*width+x] = img.GrayAt(x, y).Y
}
}
return origin
}
func toGrayscale(img image.Image) *image.Gray {
result := image.NewGray(img.Bounds())
draw.Draw(result, result.Bounds(), img, img.Bounds().Min, draw.Src)
return result
}
func findColor(c int, half int) int {
if c > half {
return 255
} else {
return 0
}
}