We closed this forum 18 June 2010. It has served us well since 2005 as the ALPHA forum did before it from 2002 to 2005. New discussions are ongoing at the new URL http://forum.processing.org. You'll need to sign up and get a new user account. We're sorry about that inconvenience, but we think it's better in the long run. The content on this forum will remain online.
IndexProgramming Questions & HelpPrograms › image dithering: 8bit -> monochrome
Page Index Toggle Pages: 1
image dithering: 8bit -> monochrome (Read 655 times)
image dithering: 8bit -> monochrome
Feb 20th, 2008, 2:08pm
 
hi guys,

I have a monochrome (b/w) graphics lcd here and i'd like to generate "nice" b/w images for it. at the moment i'm using a threshold (if brightness>127: pixel=white). This results in quite ugly images, as one might expect.

so i figured i need some "dithering". there's information about it out there, but i really don't know where to start to implement a realtime dither algorithm in java. I found some solutions using JAI, but actually i want to stick with "normal" processing java. I don't care that much about what dithering algorithm to use (http://en.wikipedia.org/wiki/Dither#Dithering_algorithms), all of them are probably better than thresholding.

thanks for thoughts and hints!
Re: image dithering: 8bit -> monochrome
Reply #1 - Feb 20th, 2008, 2:38pm
 
Floyd-Steinberg looks promisingly simple, yet sufficiently effective.
Re: image dithering: 8bit -> monochrome
Reply #2 - Feb 20th, 2008, 2:51pm
 
There's a link describing a simple dithering algorithm, "not as good as Floyd-Steinberg", as it says, but I gave it a try, and it's quite efficient :
http://wwwhome.cs.utwente.nl/~schooten/graphics/
Re: image dithering: 8bit -> monochrome
Reply #3 - Feb 21st, 2008, 2:48am
 
thanks! antiplastik, your link is great. i tried to implement it... it kind of works. i'm getting 3 "shades of grey" only, but i guess it could be 5. For example i can't get a white-white area. Maybe this is a good oportunity for me to finaly learn how to use bitwise operations and rewrite this thing more elegantly...

http://www.extrapixel.ch/processing/dithering.zip

Quote:
// image dithering
// http://wwwhome.cs.utwente.nl/~schooten/graphics/
PImage ditherImage(PImage img) {
 PImage ditheredImg = img.get(0,0,img.width, img.height);

 // tile = 2*2 pixels
 int[] tilePixelColors = new int[4];
 float[] bias = new float[] {
   0.25, .75, 0.5, 0.0              };
 int pixelPosition;
 float valScale = 1.0 / 255.0;

 // rows
 for (int i=0; i<img.height/2.0; i++) {
   // coloumns
   for (int j=0; j<img.width/2.0; j++) {
     pixelPosition = i*2*img.width + j*2;

     tilePixelColors[0] = (int) (bias[0] + valScale*greyValue(img.pixels[pixelPosition]));
     tilePixelColors[1] = (int) (bias[1] + valScale*greyValue(img.pixels[pixelPosition+1]));
     tilePixelColors[2] = (int) (bias[2] + valScale*greyValue(img.pixels[pixelPosition+img.width]));
     tilePixelColors[2] = (int) (bias[3] + valScale*greyValue(img.pixels[pixelPosition+img.width+1]));

     ditheredImg.pixels[pixelPosition] = color(255*tilePixelColors[0]);
     ditheredImg.pixels[pixelPosition+1] = color(255*tilePixelColors[1]);
     ditheredImg.pixels[pixelPosition+img.width] = color(255*tilePixelColors[2]);
     ditheredImg.pixels[pixelPosition+img.width+1] = color(255*tilePixelColors[3]);
   }
 }
 return ditheredImg;
}

int greyValue(int _color) {
 return (int)((red(_color) + green(_color) + blue(_color)) / 3.0) ;
}
Re: image dithering: 8bit -> monochrome
Reply #4 - Feb 21st, 2008, 12:07pm
 
Yep, I had the same "can't get a white area" problem. I think it is due to the bias values (more exactly the last one which is 0.0). After playing a while, I had a pretty good result with those : {0.25, .75, 0.5, 0.25}.

I'm not sure, but maybe using a larger grid (i.e. 4x4 pixels with different bias values) would result in more shades of grey?

Quote:
Maybe this is a good oportunity for me to finaly learn how to use bitwise operations

/ 256 equals to >> 8
* 256 equals to << 8
Re: image dithering: 8bit -> monochrome
Reply #5 - Feb 21st, 2008, 1:24pm
 
my sketch is here
http://www.geocities.jp/classiclll_newweb/DitherTest/applet/index.html
hope it is for your information
Re: image dithering: 8bit -> monochrome
Reply #6 - Feb 21st, 2008, 2:01pm
 
Classiclll, thank you! your code seems to produce much better results than my attempts. what kind of dithering algorithm does it implement? i'm having having a hard time finding out what your code does exactly Wink
Re: image dithering: 8bit -> monochrome
Reply #7 - Feb 21st, 2008, 4:28pm
 
hi extrapixel

my idea is


- dither pattern 2*2
 0, 2
 3, 1
so
 P1(i,j) := ( i%2!=j%2 ? 2: 0 ) + j%2

- dither psttern 4*4
 00,08,02,10
 12,04,14,06
 03,11,01,09
 15,07,13,05
so
 P2(i,j) := 4*P1(i%2,j%2) + P1(i/2,j/2)

- dither pattern 8*8
 [-omitted-]
so
 P3(i,j) := 4*P2(i%2,j%2) + P2(i/2,j/2)
           := 4*{ 4*P1(i%2%2,j%2%2) + P1(i%2/2,j%2/2) }
                        + 4*P1(i/2%2,j/2%2) + P1(i/2/2,j/2/2)

- so generally
- color depth is 2^(2n)
and
- Pn(i,j) := (i%2<>j%2 ? 1 : 0) + j%2 when n=1
            := 4*Pn-1(i%2,j%2)          when n>1
                    + Pn-1(i/2,j/2)

- dither conversion
- let k(x,y) be color value at (x,y)
- following gives dither bit at (x,y)
    ( Pn(x, y) <= k(x,y) ? black : white )
Re: image dithering: 8bit -> monochrome
Reply #8 - Feb 21st, 2008, 10:30pm
 
ok, i'm slowly getting it Wink thank you!

here's a video that compares your algorithm (at the start and end of the video) with my quick'n'dirty method (middle part):
http://www.extrapixel.ch/processing/compare_dither.mov
it's a 128x64 graphic lcd... looks kinda crappy in the video, but it's so cool in real.

Re: image dithering: 8bit -> monochrome
Reply #9 - Feb 22nd, 2008, 5:09am
 
may be "dither matrix" or "ordered dithering"
http://www.jhlabs.com/ip/filters/DitherFilter.html
my logic is an algorithm creating any sized matrix, i think.
Page Index Toggle Pages: 1