8{0, 0, 1.0, AA_FLOYD_S, 0, 0};
10#define pos(i1,i2,i3,i4) (((int)(i1)<<12)+((int)(i2)<<8)+((int)(i3)<<4)+(int)(i4))
11char *aa_dithernames[] =
15 "floyd-steelberg dithering",
19#define DO_CONTRAST(i,c) (i<c?0:(i>256-c)?255:(i-c)*255/(255-2*c))
25 *p = aa_defrenderparams;
28#define MYLONG_MAX 0xffffffff
29#define myrand() (state = ((state * 1103515245) + 12345) & MYLONG_MAX)
40 int i1, i2, i3, i4, esum;
44 int gamma = p->gamma != 1.0;
46 if (x2 < 0 || y2 < 0 || x1 > aa_scrwidth(c) || y1 > aa_scrheight(c))
48 if (x2 >= aa_scrwidth(c))
50 if (y2 >= aa_scrheight(c))
58 if (p->dither == AA_FLOYD_S) {
59 errors[0] = calloc(1, (x2 + 5) *
sizeof(
int));
60 if (errors[0] == NULL)
61 p->dither = AA_ERRORDISTRIB;
63 errors[1] = calloc(1, (x2 + 5) *
sizeof(
int));
64 if (errors[1] == NULL)
65 free(errors[0]), p->dither = AA_ERRORDISTRIB;
69 for (i = 0; i < 256; i++) {
70 y = palette[i] + p->bright;
76 y = DO_CONTRAST(y, p->contrast);
78 y = pow(y / 255.0, p->gamma) * 255 + 0.5;
90 gamma = p->randomval / 2;
91 mval = (c->parameters[c->filltable[255]].p[4]);
92 for (y = y1; y < y2; y++) {
94 pos1 = y * aa_scrwidth(c);
96 for (x = x1; x < x2; x++) {
97 i1 = table[((((int) c->imagebuffer[pos])))];
98 i2 = table[((((int) c->imagebuffer[pos + 1])))];
99 i3 = table[((((int) c->imagebuffer[pos + wi])))];
100 i4 = table[((((int) c->imagebuffer[pos + 1 + wi])))];
103 i1 += (i) % p->randomval - gamma;
104 i2 += (i >> 8) % p->randomval - gamma;
105 i3 += (i >> 16) % p->randomval - gamma;
106 i4 += (i >> 24) % p->randomval - gamma;
107 if ((i1 | i2 | i3 | i4) & (~255)) {
127 case AA_ERRORDISTRIB:
128 esum = (esum + 2) >> 2;
135 if (i1 | i2 | i3 | i4) {
136 errors[cur][x - 2] += esum >> 4;
137 errors[cur][x - 1] += (5 * esum) >> 4;
138 errors[cur][x] = (3 * esum) >> 4;
139 esum = (7 * esum) >> 4;
140 esum += errors[cur ^ 1][x];
141 i1 += (esum + 1) >> 2;
143 i3 += (esum + 3) >> 2;
144 i4 += (esum + 2) >> 2;
149 esum = i1 + i2 + i3 + i4;
151 if ((abs(i1 - val) < VAL &&
152 abs(i2 - val) < VAL &&
153 abs(i3 - val) < VAL &&
154 abs(i4 - val) < VAL)) {
156 val = 255, esum = 4 * 256 - 1;
159 val = c->filltable[val];
161 if ((i1 | i2 | i3 | i4) & (~255)) {
179 esum = i1 + i2 + i3 + i4;
184 val = c->table[pos(i2, i1, i4, i3)];
186 esum = (esum - (c->parameters[val].p[4]) * 1020 / mval);
188 val = (i1 + i2 + i3 + i4) >> 2;
189 if ((abs(i1 - val) < VAL &&
190 abs(i2 - val) < VAL &&
191 abs(i3 - val) < VAL &&
192 abs(i4 - val) < VAL)) {
193 val = c->filltable[val];
199 val = c->table[pos(i2, i1, i4, i3)];
202 c->attrbuffer[pos1] = val >> 8;
203 c->textbuffer[pos1] = val & 0xff;
207 if (p->dither == AA_FLOYD_S) {
209 errors[cur][x2 - 2] += (esum) >> 4;
211 errors[cur][x2 - 1] += (5 * esum) >> 4;
214 errors[cur ^ 1][-1] = 0;
217 if (p->dither == AA_FLOYD_S) {
225 static aa_palette table;
226 if (table[255] != 255)
227 for (i = 0; i < 256; i++) {
230 aa_renderpalette(c, table, p, x1, y1, x2, y2);