Hash-based noise dithering - survives downsampling without moiré artifacts Uses integer hash to generate pseudo-random threshold per pixel
| 69 | // Hash-based noise dithering - survives downsampling without moiré artifacts |
| 70 | // Uses integer hash to generate pseudo-random threshold per pixel |
| 71 | static inline uint8_t quantizeNoise(int gray, int x, int y) { |
| 72 | uint32_t hash = static_cast<uint32_t>(x) * 374761393u + static_cast<uint32_t>(y) * 668265263u; |
| 73 | hash = (hash ^ (hash >> 13)) * 1274126177u; |
| 74 | const int threshold = static_cast<int>(hash >> 24); |
| 75 | |
| 76 | const int scaled = gray * 3; |
| 77 | if (scaled < 255) { |
| 78 | return (scaled + threshold >= 255) ? 1 : 0; |
| 79 | } else if (scaled < 510) { |
| 80 | return ((scaled - 255) + threshold >= 255) ? 2 : 1; |
| 81 | } else { |
| 82 | return ((scaled - 510) + threshold >= 255) ? 3 : 2; |
| 83 | } |
| 84 | } |
| 85 | |
| 86 | // Main quantization function - selects between methods based on config |
| 87 | uint8_t quantize(int gray, int x, int y) { |