174994d13SStephan Aßmus /* 274994d13SStephan Aßmus * Copyright 2005, Stephan Aßmus <superstippi@gmx.de>. All rights reserved. 374994d13SStephan Aßmus * Distributed under the terms of the MIT License. 474994d13SStephan Aßmus * 574994d13SStephan Aßmus * DrawingMode implementing B_OP_INVERT on B_RGBA32. 674994d13SStephan Aßmus * 774994d13SStephan Aßmus */ 8c0fe8a07SStephan Aßmus 9c0fe8a07SStephan Aßmus #ifndef DRAWING_MODE_INVERT_H 10c0fe8a07SStephan Aßmus #define DRAWING_MODE_INVERT_H 11c0fe8a07SStephan Aßmus 12c0fe8a07SStephan Aßmus #include "DrawingMode.h" 13c0fe8a07SStephan Aßmus 14c0fe8a07SStephan Aßmus // BLEND_INVERT 158d7b8e8cSStephan Aßmus #define BLEND_INVERT(d, a) \ 16c0fe8a07SStephan Aßmus { \ 178d7b8e8cSStephan Aßmus pixel32 _p; \ 188d7b8e8cSStephan Aßmus _p.data32 = *(uint32*)d; \ 198d7b8e8cSStephan Aßmus BLEND(d, 255 - _p.data8[2], 255 - _p.data8[1], 255 - _p.data8[0], a); \ 20c0fe8a07SStephan Aßmus } 21c0fe8a07SStephan Aßmus 22c0fe8a07SStephan Aßmus // ASSIGN_INVERT 238d7b8e8cSStephan Aßmus #define ASSIGN_INVERT(d) \ 24c0fe8a07SStephan Aßmus { \ 258d7b8e8cSStephan Aßmus pixel32 _p; \ 268d7b8e8cSStephan Aßmus _p.data32 = *(uint32*)d; \ 278d7b8e8cSStephan Aßmus d[0] = 255 - _p.data8[0]; \ 288d7b8e8cSStephan Aßmus d[1] = 255 - _p.data8[1]; \ 298d7b8e8cSStephan Aßmus d[2] = 255 - _p.data8[2]; \ 30*9d909e25SStephan Aßmus d[3] = 255; \ 31c0fe8a07SStephan Aßmus } 32c0fe8a07SStephan Aßmus 338d7b8e8cSStephan Aßmus // blend_pixel_invert 348d7b8e8cSStephan Aßmus void 358d7b8e8cSStephan Aßmus blend_pixel_invert(int x, int y, const color_type& c, uint8 cover, 368d7b8e8cSStephan Aßmus agg_buffer* buffer, const PatternHandler* pattern) 37c0fe8a07SStephan Aßmus { 388d7b8e8cSStephan Aßmus if (pattern->IsHighColor(x, y)) { 398d7b8e8cSStephan Aßmus uint8* p = buffer->row(y) + (x << 2); 40c0fe8a07SStephan Aßmus if (cover == 255) { 418d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 42c0fe8a07SStephan Aßmus } else { 438d7b8e8cSStephan Aßmus BLEND_INVERT(p, cover); 44c0fe8a07SStephan Aßmus } 45c0fe8a07SStephan Aßmus } 46c0fe8a07SStephan Aßmus } 47c0fe8a07SStephan Aßmus 488d7b8e8cSStephan Aßmus // blend_hline_invert 498d7b8e8cSStephan Aßmus void 508d7b8e8cSStephan Aßmus blend_hline_invert(int x, int y, unsigned len, 518d7b8e8cSStephan Aßmus const color_type& c, uint8 cover, 528d7b8e8cSStephan Aßmus agg_buffer* buffer, const PatternHandler* pattern) 53c0fe8a07SStephan Aßmus { 548d7b8e8cSStephan Aßmus uint8* p = buffer->row(y) + (x << 2); 55c0fe8a07SStephan Aßmus if(cover == 255) { 56c0fe8a07SStephan Aßmus do { 578d7b8e8cSStephan Aßmus if (pattern->IsHighColor(x, y)) { 588d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 59c0fe8a07SStephan Aßmus } 60c0fe8a07SStephan Aßmus x++; 61c0fe8a07SStephan Aßmus p += 4; 62c0fe8a07SStephan Aßmus } while(--len); 63c0fe8a07SStephan Aßmus } else { 64c0fe8a07SStephan Aßmus do { 658d7b8e8cSStephan Aßmus if (pattern->IsHighColor(x, y)) { 668d7b8e8cSStephan Aßmus BLEND_INVERT(p, cover); 67c0fe8a07SStephan Aßmus } 68c0fe8a07SStephan Aßmus x++; 69c0fe8a07SStephan Aßmus p += 4; 70c0fe8a07SStephan Aßmus } while(--len); 71c0fe8a07SStephan Aßmus } 72c0fe8a07SStephan Aßmus } 73c0fe8a07SStephan Aßmus 748d7b8e8cSStephan Aßmus // blend_solid_hspan_invert 758d7b8e8cSStephan Aßmus void 768d7b8e8cSStephan Aßmus blend_solid_hspan_invert(int x, int y, unsigned len, 778d7b8e8cSStephan Aßmus const color_type& c, const uint8* covers, 788d7b8e8cSStephan Aßmus agg_buffer* buffer, const PatternHandler* pattern) 79c0fe8a07SStephan Aßmus { 808d7b8e8cSStephan Aßmus uint8* p = buffer->row(y) + (x << 2); 81c0fe8a07SStephan Aßmus do { 828d7b8e8cSStephan Aßmus if (pattern->IsHighColor(x, y)) { 83c0fe8a07SStephan Aßmus if (*covers) { 84c0fe8a07SStephan Aßmus if (*covers == 255) { 858d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 86c0fe8a07SStephan Aßmus } else { 878d7b8e8cSStephan Aßmus BLEND_INVERT(p, *covers); 88c0fe8a07SStephan Aßmus } 89c0fe8a07SStephan Aßmus } 90c0fe8a07SStephan Aßmus } 91c0fe8a07SStephan Aßmus covers++; 92c0fe8a07SStephan Aßmus p += 4; 93c0fe8a07SStephan Aßmus x++; 94c0fe8a07SStephan Aßmus } while(--len); 95c0fe8a07SStephan Aßmus } 96c0fe8a07SStephan Aßmus 97c0fe8a07SStephan Aßmus 98c0fe8a07SStephan Aßmus 998d7b8e8cSStephan Aßmus // blend_solid_vspan_invert 1008d7b8e8cSStephan Aßmus void 1018d7b8e8cSStephan Aßmus blend_solid_vspan_invert(int x, int y, unsigned len, 1028d7b8e8cSStephan Aßmus const color_type& c, const uint8* covers, 1038d7b8e8cSStephan Aßmus agg_buffer* buffer, const PatternHandler* pattern) 104c0fe8a07SStephan Aßmus { 1058d7b8e8cSStephan Aßmus uint8* p = buffer->row(y) + (x << 2); 106c0fe8a07SStephan Aßmus do { 1078d7b8e8cSStephan Aßmus if (pattern->IsHighColor(x, y)) { 108c0fe8a07SStephan Aßmus if (*covers) { 109c0fe8a07SStephan Aßmus if (*covers == 255) { 1108d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 111c0fe8a07SStephan Aßmus } else { 1128d7b8e8cSStephan Aßmus BLEND_INVERT(p, *covers); 113c0fe8a07SStephan Aßmus } 114c0fe8a07SStephan Aßmus } 115c0fe8a07SStephan Aßmus } 116c0fe8a07SStephan Aßmus covers++; 1178d7b8e8cSStephan Aßmus p += buffer->stride(); 118c0fe8a07SStephan Aßmus y++; 119c0fe8a07SStephan Aßmus } while(--len); 120c0fe8a07SStephan Aßmus } 121c0fe8a07SStephan Aßmus 122c0fe8a07SStephan Aßmus 1238d7b8e8cSStephan Aßmus // blend_color_hspan_invert 1248d7b8e8cSStephan Aßmus void 1258d7b8e8cSStephan Aßmus blend_color_hspan_invert(int x, int y, unsigned len, 126c0fe8a07SStephan Aßmus const color_type* colors, 1278d7b8e8cSStephan Aßmus const uint8* covers, uint8 cover, 1288d7b8e8cSStephan Aßmus agg_buffer* buffer, const PatternHandler* pattern) 129c0fe8a07SStephan Aßmus { 130c0fe8a07SStephan Aßmus // TODO: does the R5 app_server check for the 131c0fe8a07SStephan Aßmus // appearance of the high color in the source bitmap? 1328d7b8e8cSStephan Aßmus uint8* p = buffer->row(y) + (x << 2); 133c0fe8a07SStephan Aßmus if (covers) { 134c0fe8a07SStephan Aßmus // non-solid opacity 135c0fe8a07SStephan Aßmus do { 136c0fe8a07SStephan Aßmus if (*covers) { 137c0fe8a07SStephan Aßmus if (*covers == 255) { 1388d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 139c0fe8a07SStephan Aßmus } else { 1408d7b8e8cSStephan Aßmus BLEND_INVERT(p, *covers); 141c0fe8a07SStephan Aßmus } 142c0fe8a07SStephan Aßmus } 143c0fe8a07SStephan Aßmus covers++; 144c0fe8a07SStephan Aßmus p += 4; 145c0fe8a07SStephan Aßmus // ++colors; 146c0fe8a07SStephan Aßmus } while(--len); 147c0fe8a07SStephan Aßmus } else { 148c0fe8a07SStephan Aßmus // solid full opcacity 149c0fe8a07SStephan Aßmus if (cover == 255) { 150c0fe8a07SStephan Aßmus do { 1518d7b8e8cSStephan Aßmus ASSIGN_INVERT(p); 152c0fe8a07SStephan Aßmus p += 4; 153c0fe8a07SStephan Aßmus // ++colors; 154c0fe8a07SStephan Aßmus } while(--len); 155c0fe8a07SStephan Aßmus // solid partial opacity 156c0fe8a07SStephan Aßmus } else if (cover) { 157c0fe8a07SStephan Aßmus do { 1588d7b8e8cSStephan Aßmus BLEND_INVERT(p, cover); 159c0fe8a07SStephan Aßmus p += 4; 160c0fe8a07SStephan Aßmus // ++colors; 161c0fe8a07SStephan Aßmus } while(--len); 162c0fe8a07SStephan Aßmus } 163c0fe8a07SStephan Aßmus } 164c0fe8a07SStephan Aßmus } 165c0fe8a07SStephan Aßmus 166c0fe8a07SStephan Aßmus #endif // DRAWING_MODE_INVERT_H 167c0fe8a07SStephan Aßmus 168