SDL  2.0
SDL_draw.h
Go to the documentation of this file.
1 /*
2  Simple DirectMedia Layer
3  Copyright (C) 1997-2018 Sam Lantinga <slouken@libsdl.org>
4 
5  This software is provided 'as-is', without any express or implied
6  warranty. In no event will the authors be held liable for any damages
7  arising from the use of this software.
8 
9  Permission is granted to anyone to use this software for any purpose,
10  including commercial applications, and to alter it and redistribute it
11  freely, subject to the following restrictions:
12 
13  1. The origin of this software must not be misrepresented; you must not
14  claim that you wrote the original software. If you use this software
15  in a product, an acknowledgment in the product documentation would be
16  appreciated but is not required.
17  2. Altered source versions must be plainly marked as such, and must not be
18  misrepresented as being the original software.
19  3. This notice may not be removed or altered from any source distribution.
20 */
21 #include "../../SDL_internal.h"
22 
23 #include "../../video/SDL_blit.h"
24 
25 /* This code assumes that r, g, b, a are the source color,
26  * and in the blend and add case, the RGB values are premultiplied by a.
27  */
28 
29 #define DRAW_MUL(_a, _b) (((unsigned)(_a)*(_b))/255)
30 
31 #define DRAW_FASTSETPIXEL(type) \
32  *pixel = (type) color
33 
34 #define DRAW_FASTSETPIXEL1 DRAW_FASTSETPIXEL(Uint8)
35 #define DRAW_FASTSETPIXEL2 DRAW_FASTSETPIXEL(Uint16)
36 #define DRAW_FASTSETPIXEL4 DRAW_FASTSETPIXEL(Uint32)
37 
38 #define DRAW_FASTSETPIXELXY(x, y, type, bpp, color) \
39  *(type *)((Uint8 *)dst->pixels + (y) * dst->pitch \
40  + (x) * bpp) = (type) color
41 
42 #define DRAW_FASTSETPIXELXY1(x, y) DRAW_FASTSETPIXELXY(x, y, Uint8, 1, color)
43 #define DRAW_FASTSETPIXELXY2(x, y) DRAW_FASTSETPIXELXY(x, y, Uint16, 2, color)
44 #define DRAW_FASTSETPIXELXY4(x, y) DRAW_FASTSETPIXELXY(x, y, Uint32, 4, color)
45 
46 #define DRAW_SETPIXEL(setpixel) \
47 do { \
48  unsigned sr = r, sg = g, sb = b, sa = a; (void) sa; \
49  setpixel; \
50 } while (0)
51 
52 #define DRAW_SETPIXEL_BLEND(getpixel, setpixel) \
53 do { \
54  unsigned sr, sg, sb, sa = 0xFF; \
55  getpixel; \
56  sr = DRAW_MUL(inva, sr) + r; \
57  sg = DRAW_MUL(inva, sg) + g; \
58  sb = DRAW_MUL(inva, sb) + b; \
59  sa = DRAW_MUL(inva, sa) + a; \
60  setpixel; \
61 } while (0)
62 
63 #define DRAW_SETPIXEL_ADD(getpixel, setpixel) \
64 do { \
65  unsigned sr, sg, sb, sa; (void) sa; \
66  getpixel; \
67  sr += r; if (sr > 0xff) sr = 0xff; \
68  sg += g; if (sg > 0xff) sg = 0xff; \
69  sb += b; if (sb > 0xff) sb = 0xff; \
70  setpixel; \
71 } while (0)
72 
73 #define DRAW_SETPIXEL_MOD(getpixel, setpixel) \
74 do { \
75  unsigned sr, sg, sb, sa; (void) sa; \
76  getpixel; \
77  sr = DRAW_MUL(sr, r); \
78  sg = DRAW_MUL(sg, g); \
79  sb = DRAW_MUL(sb, b); \
80  setpixel; \
81 } while (0)
82 
83 #define DRAW_SETPIXELXY(x, y, type, bpp, op) \
84 do { \
85  type *pixel = (type *)((Uint8 *)dst->pixels + (y) * dst->pitch \
86  + (x) * bpp); \
87  op; \
88 } while (0)
89 
90 /*
91  * Define draw operators for RGB555
92  */
93 
94 #define DRAW_SETPIXEL_RGB555 \
95  DRAW_SETPIXEL(RGB555_FROM_RGB(*pixel, sr, sg, sb))
96 
97 #define DRAW_SETPIXEL_BLEND_RGB555 \
98  DRAW_SETPIXEL_BLEND(RGB_FROM_RGB555(*pixel, sr, sg, sb), \
99  RGB555_FROM_RGB(*pixel, sr, sg, sb))
100 
101 #define DRAW_SETPIXEL_ADD_RGB555 \
102  DRAW_SETPIXEL_ADD(RGB_FROM_RGB555(*pixel, sr, sg, sb), \
103  RGB555_FROM_RGB(*pixel, sr, sg, sb))
104 
105 #define DRAW_SETPIXEL_MOD_RGB555 \
106  DRAW_SETPIXEL_MOD(RGB_FROM_RGB555(*pixel, sr, sg, sb), \
107  RGB555_FROM_RGB(*pixel, sr, sg, sb))
108 
109 #define DRAW_SETPIXELXY_RGB555(x, y) \
110  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_RGB555)
111 
112 #define DRAW_SETPIXELXY_BLEND_RGB555(x, y) \
113  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_BLEND_RGB555)
114 
115 #define DRAW_SETPIXELXY_ADD_RGB555(x, y) \
116  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_ADD_RGB555)
117 
118 #define DRAW_SETPIXELXY_MOD_RGB555(x, y) \
119  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_MOD_RGB555)
120 
121 /*
122  * Define draw operators for RGB565
123  */
124 
125 #define DRAW_SETPIXEL_RGB565 \
126  DRAW_SETPIXEL(RGB565_FROM_RGB(*pixel, sr, sg, sb))
127 
128 #define DRAW_SETPIXEL_BLEND_RGB565 \
129  DRAW_SETPIXEL_BLEND(RGB_FROM_RGB565(*pixel, sr, sg, sb), \
130  RGB565_FROM_RGB(*pixel, sr, sg, sb))
131 
132 #define DRAW_SETPIXEL_ADD_RGB565 \
133  DRAW_SETPIXEL_ADD(RGB_FROM_RGB565(*pixel, sr, sg, sb), \
134  RGB565_FROM_RGB(*pixel, sr, sg, sb))
135 
136 #define DRAW_SETPIXEL_MOD_RGB565 \
137  DRAW_SETPIXEL_MOD(RGB_FROM_RGB565(*pixel, sr, sg, sb), \
138  RGB565_FROM_RGB(*pixel, sr, sg, sb))
139 
140 #define DRAW_SETPIXELXY_RGB565(x, y) \
141  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_RGB565)
142 
143 #define DRAW_SETPIXELXY_BLEND_RGB565(x, y) \
144  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_BLEND_RGB565)
145 
146 #define DRAW_SETPIXELXY_ADD_RGB565(x, y) \
147  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_ADD_RGB565)
148 
149 #define DRAW_SETPIXELXY_MOD_RGB565(x, y) \
150  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_MOD_RGB565)
151 
152 /*
153  * Define draw operators for RGB888
154  */
155 
156 #define DRAW_SETPIXEL_RGB888 \
157  DRAW_SETPIXEL(RGB888_FROM_RGB(*pixel, sr, sg, sb))
158 
159 #define DRAW_SETPIXEL_BLEND_RGB888 \
160  DRAW_SETPIXEL_BLEND(RGB_FROM_RGB888(*pixel, sr, sg, sb), \
161  RGB888_FROM_RGB(*pixel, sr, sg, sb))
162 
163 #define DRAW_SETPIXEL_ADD_RGB888 \
164  DRAW_SETPIXEL_ADD(RGB_FROM_RGB888(*pixel, sr, sg, sb), \
165  RGB888_FROM_RGB(*pixel, sr, sg, sb))
166 
167 #define DRAW_SETPIXEL_MOD_RGB888 \
168  DRAW_SETPIXEL_MOD(RGB_FROM_RGB888(*pixel, sr, sg, sb), \
169  RGB888_FROM_RGB(*pixel, sr, sg, sb))
170 
171 #define DRAW_SETPIXELXY_RGB888(x, y) \
172  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_RGB888)
173 
174 #define DRAW_SETPIXELXY_BLEND_RGB888(x, y) \
175  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_BLEND_RGB888)
176 
177 #define DRAW_SETPIXELXY_ADD_RGB888(x, y) \
178  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_ADD_RGB888)
179 
180 #define DRAW_SETPIXELXY_MOD_RGB888(x, y) \
181  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_MOD_RGB888)
182 
183 /*
184  * Define draw operators for ARGB8888
185  */
186 
187 #define DRAW_SETPIXEL_ARGB8888 \
188  DRAW_SETPIXEL(ARGB8888_FROM_RGBA(*pixel, sr, sg, sb, sa))
189 
190 #define DRAW_SETPIXEL_BLEND_ARGB8888 \
191  DRAW_SETPIXEL_BLEND(RGBA_FROM_ARGB8888(*pixel, sr, sg, sb, sa), \
192  ARGB8888_FROM_RGBA(*pixel, sr, sg, sb, sa))
193 
194 #define DRAW_SETPIXEL_ADD_ARGB8888 \
195  DRAW_SETPIXEL_ADD(RGBA_FROM_ARGB8888(*pixel, sr, sg, sb, sa), \
196  ARGB8888_FROM_RGBA(*pixel, sr, sg, sb, sa))
197 
198 #define DRAW_SETPIXEL_MOD_ARGB8888 \
199  DRAW_SETPIXEL_MOD(RGBA_FROM_ARGB8888(*pixel, sr, sg, sb, sa), \
200  ARGB8888_FROM_RGBA(*pixel, sr, sg, sb, sa))
201 
202 #define DRAW_SETPIXELXY_ARGB8888(x, y) \
203  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_ARGB8888)
204 
205 #define DRAW_SETPIXELXY_BLEND_ARGB8888(x, y) \
206  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_BLEND_ARGB8888)
207 
208 #define DRAW_SETPIXELXY_ADD_ARGB8888(x, y) \
209  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_ADD_ARGB8888)
210 
211 #define DRAW_SETPIXELXY_MOD_ARGB8888(x, y) \
212  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_MOD_ARGB8888)
213 
214 /*
215  * Define draw operators for general RGB
216  */
217 
218 #define DRAW_SETPIXEL_RGB \
219  DRAW_SETPIXEL(PIXEL_FROM_RGB(*pixel, fmt, sr, sg, sb))
220 
221 #define DRAW_SETPIXEL_BLEND_RGB \
222  DRAW_SETPIXEL_BLEND(RGB_FROM_PIXEL(*pixel, fmt, sr, sg, sb), \
223  PIXEL_FROM_RGB(*pixel, fmt, sr, sg, sb))
224 
225 #define DRAW_SETPIXEL_ADD_RGB \
226  DRAW_SETPIXEL_ADD(RGB_FROM_PIXEL(*pixel, fmt, sr, sg, sb), \
227  PIXEL_FROM_RGB(*pixel, fmt, sr, sg, sb))
228 
229 #define DRAW_SETPIXEL_MOD_RGB \
230  DRAW_SETPIXEL_MOD(RGB_FROM_PIXEL(*pixel, fmt, sr, sg, sb), \
231  PIXEL_FROM_RGB(*pixel, fmt, sr, sg, sb))
232 
233 #define DRAW_SETPIXELXY2_RGB(x, y) \
234  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_RGB)
235 
236 #define DRAW_SETPIXELXY4_RGB(x, y) \
237  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_RGB)
238 
239 #define DRAW_SETPIXELXY2_BLEND_RGB(x, y) \
240  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_BLEND_RGB)
241 
242 #define DRAW_SETPIXELXY4_BLEND_RGB(x, y) \
243  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_BLEND_RGB)
244 
245 #define DRAW_SETPIXELXY2_ADD_RGB(x, y) \
246  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_ADD_RGB)
247 
248 #define DRAW_SETPIXELXY4_ADD_RGB(x, y) \
249  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_ADD_RGB)
250 
251 #define DRAW_SETPIXELXY2_MOD_RGB(x, y) \
252  DRAW_SETPIXELXY(x, y, Uint16, 2, DRAW_SETPIXEL_MOD_RGB)
253 
254 #define DRAW_SETPIXELXY4_MOD_RGB(x, y) \
255  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_MOD_RGB)
256 
257 
258 /*
259  * Define draw operators for general RGBA
260  */
261 
262 #define DRAW_SETPIXEL_RGBA \
263  DRAW_SETPIXEL(PIXEL_FROM_RGBA(*pixel, fmt, sr, sg, sb, sa))
264 
265 #define DRAW_SETPIXEL_BLEND_RGBA \
266  DRAW_SETPIXEL_BLEND(RGBA_FROM_PIXEL(*pixel, fmt, sr, sg, sb, sa), \
267  PIXEL_FROM_RGBA(*pixel, fmt, sr, sg, sb, sa))
268 
269 #define DRAW_SETPIXEL_ADD_RGBA \
270  DRAW_SETPIXEL_ADD(RGBA_FROM_PIXEL(*pixel, fmt, sr, sg, sb, sa), \
271  PIXEL_FROM_RGBA(*pixel, fmt, sr, sg, sb, sa))
272 
273 #define DRAW_SETPIXEL_MOD_RGBA \
274  DRAW_SETPIXEL_MOD(RGBA_FROM_PIXEL(*pixel, fmt, sr, sg, sb, sa), \
275  PIXEL_FROM_RGBA(*pixel, fmt, sr, sg, sb, sa))
276 
277 #define DRAW_SETPIXELXY4_RGBA(x, y) \
278  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_RGBA)
279 
280 #define DRAW_SETPIXELXY4_BLEND_RGBA(x, y) \
281  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_BLEND_RGBA)
282 
283 #define DRAW_SETPIXELXY4_ADD_RGBA(x, y) \
284  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_ADD_RGBA)
285 
286 #define DRAW_SETPIXELXY4_MOD_RGBA(x, y) \
287  DRAW_SETPIXELXY(x, y, Uint32, 4, DRAW_SETPIXEL_MOD_RGBA)
288 
289 /*
290  * Define line drawing macro
291  */
292 
293 #define ABS(_x) ((_x) < 0 ? -(_x) : (_x))
294 
295 /* Horizontal line */
296 #define HLINE(type, op, draw_end) \
297 { \
298  int length; \
299  int pitch = (dst->pitch / dst->format->BytesPerPixel); \
300  type *pixel; \
301  if (x1 <= x2) { \
302  pixel = (type *)dst->pixels + y1 * pitch + x1; \
303  length = draw_end ? (x2-x1+1) : (x2-x1); \
304  } else { \
305  pixel = (type *)dst->pixels + y1 * pitch + x2; \
306  if (!draw_end) { \
307  ++pixel; \
308  } \
309  length = draw_end ? (x1-x2+1) : (x1-x2); \
310  } \
311  while (length--) { \
312  op; \
313  ++pixel; \
314  } \
315 }
316 
317 /* Vertical line */
318 #define VLINE(type, op, draw_end) \
319 { \
320  int length; \
321  int pitch = (dst->pitch / dst->format->BytesPerPixel); \
322  type *pixel; \
323  if (y1 <= y2) { \
324  pixel = (type *)dst->pixels + y1 * pitch + x1; \
325  length = draw_end ? (y2-y1+1) : (y2-y1); \
326  } else { \
327  pixel = (type *)dst->pixels + y2 * pitch + x1; \
328  if (!draw_end) { \
329  pixel += pitch; \
330  } \
331  length = draw_end ? (y1-y2+1) : (y1-y2); \
332  } \
333  while (length--) { \
334  op; \
335  pixel += pitch; \
336  } \
337 }
338 
339 /* Diagonal line */
340 #define DLINE(type, op, draw_end) \
341 { \
342  int length; \
343  int pitch = (dst->pitch / dst->format->BytesPerPixel); \
344  type *pixel; \
345  if (y1 <= y2) { \
346  pixel = (type *)dst->pixels + y1 * pitch + x1; \
347  if (x1 <= x2) { \
348  ++pitch; \
349  } else { \
350  --pitch; \
351  } \
352  length = (y2-y1); \
353  } else { \
354  pixel = (type *)dst->pixels + y2 * pitch + x2; \
355  if (x2 <= x1) { \
356  ++pitch; \
357  } else { \
358  --pitch; \
359  } \
360  if (!draw_end) { \
361  pixel += pitch; \
362  } \
363  length = (y1-y2); \
364  } \
365  if (draw_end) { \
366  ++length; \
367  } \
368  while (length--) { \
369  op; \
370  pixel += pitch; \
371  } \
372 }
373 
374 /* Bresenham's line algorithm */
375 #define BLINE(x1, y1, x2, y2, op, draw_end) \
376 { \
377  int i, deltax, deltay, numpixels; \
378  int d, dinc1, dinc2; \
379  int x, xinc1, xinc2; \
380  int y, yinc1, yinc2; \
381  \
382  deltax = ABS(x2 - x1); \
383  deltay = ABS(y2 - y1); \
384  \
385  if (deltax >= deltay) { \
386  numpixels = deltax + 1; \
387  d = (2 * deltay) - deltax; \
388  dinc1 = deltay * 2; \
389  dinc2 = (deltay - deltax) * 2; \
390  xinc1 = 1; \
391  xinc2 = 1; \
392  yinc1 = 0; \
393  yinc2 = 1; \
394  } else { \
395  numpixels = deltay + 1; \
396  d = (2 * deltax) - deltay; \
397  dinc1 = deltax * 2; \
398  dinc2 = (deltax - deltay) * 2; \
399  xinc1 = 0; \
400  xinc2 = 1; \
401  yinc1 = 1; \
402  yinc2 = 1; \
403  } \
404  \
405  if (x1 > x2) { \
406  xinc1 = -xinc1; \
407  xinc2 = -xinc2; \
408  } \
409  if (y1 > y2) { \
410  yinc1 = -yinc1; \
411  yinc2 = -yinc2; \
412  } \
413  \
414  x = x1; \
415  y = y1; \
416  \
417  if (!draw_end) { \
418  --numpixels; \
419  } \
420  for (i = 0; i < numpixels; ++i) { \
421  op(x, y); \
422  if (d < 0) { \
423  d += dinc1; \
424  x += xinc1; \
425  y += yinc1; \
426  } else { \
427  d += dinc2; \
428  x += xinc2; \
429  y += yinc2; \
430  } \
431  } \
432 }
433 
434 /* Xiaolin Wu's line algorithm, based on Michael Abrash's implementation */
435 #define WULINE(x1, y1, x2, y2, opaque_op, blend_op, draw_end) \
436 { \
437  Uint16 ErrorAdj, ErrorAcc; \
438  Uint16 ErrorAccTemp, Weighting; \
439  int DeltaX, DeltaY, Temp, XDir; \
440  unsigned r, g, b, a, inva; \
441  \
442  /* Draw the initial pixel, which is always exactly intersected by \
443  the line and so needs no weighting */ \
444  opaque_op(x1, y1); \
445  \
446  /* Draw the final pixel, which is always exactly intersected by the line \
447  and so needs no weighting */ \
448  if (draw_end) { \
449  opaque_op(x2, y2); \
450  } \
451  \
452  /* Make sure the line runs top to bottom */ \
453  if (y1 > y2) { \
454  Temp = y1; y1 = y2; y2 = Temp; \
455  Temp = x1; x1 = x2; x2 = Temp; \
456  } \
457  DeltaY = y2 - y1; \
458  \
459  if ((DeltaX = x2 - x1) >= 0) { \
460  XDir = 1; \
461  } else { \
462  XDir = -1; \
463  DeltaX = -DeltaX; /* make DeltaX positive */ \
464  } \
465  \
466  /* line is not horizontal, diagonal, or vertical */ \
467  ErrorAcc = 0; /* initialize the line error accumulator to 0 */ \
468  \
469  /* Is this an X-major or Y-major line? */ \
470  if (DeltaY > DeltaX) { \
471  /* Y-major line; calculate 16-bit fixed-point fractional part of a \
472  pixel that X advances each time Y advances 1 pixel, truncating the \
473  result so that we won't overrun the endpoint along the X axis */ \
474  ErrorAdj = ((unsigned long) DeltaX << 16) / (unsigned long) DeltaY; \
475  /* Draw all pixels other than the first and last */ \
476  while (--DeltaY) { \
477  ErrorAccTemp = ErrorAcc; /* remember currrent accumulated error */ \
478  ErrorAcc += ErrorAdj; /* calculate error for next pixel */ \
479  if (ErrorAcc <= ErrorAccTemp) { \
480  /* The error accumulator turned over, so advance the X coord */ \
481  x1 += XDir; \
482  } \
483  y1++; /* Y-major, so always advance Y */ \
484  /* The IntensityBits most significant bits of ErrorAcc give us the \
485  intensity weighting for this pixel, and the complement of the \
486  weighting for the paired pixel */ \
487  Weighting = ErrorAcc >> 8; \
488  { \
489  a = DRAW_MUL(_a, (Weighting ^ 255)); \
490  r = DRAW_MUL(_r, a); \
491  g = DRAW_MUL(_g, a); \
492  b = DRAW_MUL(_b, a); \
493  inva = (a ^ 0xFF); \
494  blend_op(x1, y1); \
495  } \
496  { \
497  a = DRAW_MUL(_a, Weighting); \
498  r = DRAW_MUL(_r, a); \
499  g = DRAW_MUL(_g, a); \
500  b = DRAW_MUL(_b, a); \
501  inva = (a ^ 0xFF); \
502  blend_op(x1 + XDir, y1); \
503  } \
504  } \
505  } else { \
506  /* X-major line; calculate 16-bit fixed-point fractional part of a \
507  pixel that Y advances each time X advances 1 pixel, truncating the \
508  result to avoid overrunning the endpoint along the X axis */ \
509  ErrorAdj = ((unsigned long) DeltaY << 16) / (unsigned long) DeltaX; \
510  /* Draw all pixels other than the first and last */ \
511  while (--DeltaX) { \
512  ErrorAccTemp = ErrorAcc; /* remember currrent accumulated error */ \
513  ErrorAcc += ErrorAdj; /* calculate error for next pixel */ \
514  if (ErrorAcc <= ErrorAccTemp) { \
515  /* The error accumulator turned over, so advance the Y coord */ \
516  y1++; \
517  } \
518  x1 += XDir; /* X-major, so always advance X */ \
519  /* The IntensityBits most significant bits of ErrorAcc give us the \
520  intensity weighting for this pixel, and the complement of the \
521  weighting for the paired pixel */ \
522  Weighting = ErrorAcc >> 8; \
523  { \
524  a = DRAW_MUL(_a, (Weighting ^ 255)); \
525  r = DRAW_MUL(_r, a); \
526  g = DRAW_MUL(_g, a); \
527  b = DRAW_MUL(_b, a); \
528  inva = (a ^ 0xFF); \
529  blend_op(x1, y1); \
530  } \
531  { \
532  a = DRAW_MUL(_a, Weighting); \
533  r = DRAW_MUL(_r, a); \
534  g = DRAW_MUL(_g, a); \
535  b = DRAW_MUL(_b, a); \
536  inva = (a ^ 0xFF); \
537  blend_op(x1, y1 + 1); \
538  } \
539  } \
540  } \
541 }
542 
543 #ifdef AA_LINES
544 #define AALINE(x1, y1, x2, y2, opaque_op, blend_op, draw_end) \
545  WULINE(x1, y1, x2, y2, opaque_op, blend_op, draw_end)
546 #else
547 #define AALINE(x1, y1, x2, y2, opaque_op, blend_op, draw_end) \
548  BLINE(x1, y1, x2, y2, opaque_op, draw_end)
549 #endif
550 
551 /*
552  * Define fill rect macro
553  */
554 
555 #define FILLRECT(type, op) \
556 do { \
557  int width = rect->w; \
558  int height = rect->h; \
559  int pitch = (dst->pitch / dst->format->BytesPerPixel); \
560  int skip = pitch - width; \
561  type *pixel = (type *)dst->pixels + rect->y * pitch + rect->x; \
562  while (height--) { \
563  { int n = (width+3)/4; \
564  switch (width & 3) { \
565  case 0: do { op; pixel++; /* fallthrough */ \
566  case 3: op; pixel++; /* fallthrough */ \
567  case 2: op; pixel++; /* fallthrough */ \
568  case 1: op; pixel++; /* fallthrough */ \
569  } while ( --n > 0 ); \
570  } \
571  } \
572  pixel += skip; \
573  } \
574 } while (0)
575 
576 /* vi: set ts=4 sw=4 expandtab: */