From 2182fdfdbf010d01dbee8fd5c0508922ff9080e5 Mon Sep 17 00:00:00 2001
From: sam <sam@92316355-f0b4-4df1-b90c-862c8a59935f>
Date: Sun, 3 Aug 2008 03:30:53 +0000
Subject: [PATCH]   * floydsteinberg.c: perform Floyd-Steinberg dithering on a
 serpentine path.

git-svn-id: file:///srv/caca.zoy.org/var/lib/svn/libpipi/trunk@2653 92316355-f0b4-4df1-b90c-862c8a59935f
---
 pipi/dither/floydsteinberg.c | 16 ++++++++++------
 1 file changed, 10 insertions(+), 6 deletions(-)

diff --git a/pipi/dither/floydsteinberg.c b/pipi/dither/floydsteinberg.c
index 8e50d0b..46f692d 100644
--- a/pipi/dither/floydsteinberg.c
+++ b/pipi/dither/floydsteinberg.c
@@ -44,21 +44,25 @@ pipi_image_t *pipi_floydsteinberg(pipi_image_t *src)
         for(x = 0; x < w; x++)
         {
             float p, q, e;
+            int x2 = (y & 1) ? x : w - 1 - x;
+            int s = (y & 1) ? 1 : -1;
 
-            p = srcdata[y * w + x];
+            p = srcdata[y * w + x2];
             q = p < 0.5 ? 0. : 1.;
-            dstdata[y * w + x] = q;
+            dstdata[y * w + x2] = q;
 
+            /* FIXME: according to our 2008 paper, [7 4 5 0] is a better
+             * error diffusion kernel for serpentine scan. */
             e = p - q;
             if(x < w - 1)
-                srcdata[y * w + x + 1] += e * .4375;
+                srcdata[y * w + x2 + s] += e * .4375;
             if(y < h - 1)
             {
                 if(x > 0)
-                    srcdata[(y + 1) * w + x - 1] += e * .1875;
-                srcdata[(y + 1) * w + x] += e * .3125;
+                    srcdata[(y + 1) * w + x2 - s] += e * .1875;
+                srcdata[(y + 1) * w + x2] += e * .3125;
                 if(x < w - 1)
-                    srcdata[(y + 1) * w + x + 1] += e * .0625;
+                    srcdata[(y + 1) * w + x2 + s] += e * .0625;
             }
         }
     }