[comp.graphics] bit masks

mcooper@sunb4.cs.uiuc.edu (08/30/90)

I'm looking for an algorithm (or C code, of you have it) to generate
16 x 16 bit masks.  Ideally, I should be able to specify a percentage and
the program should spit out the pattern filled appropriately.

ie.

100% yeilds

1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111
1111111111111111

This is no problem to write,m but the simple way gives you nasty artifacts such
as:  25 % yeilds

1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000
1000100010001000


Does anyone have code that will properly randomize this stuff to avoid the
inevitable artifacts and moire patterns?


+-------------------------------------+---------------------------------------+
|  "When the going gets weird,        |                                       |
|              the weird turn pro."   |  Marc Cooper	marcc@ncsa.uiuc.edu   |
|		  		      |  National Center for Supercomputing   |
|		 -Hunter S. Thompson  |		    Applications	      |
+-------------------------------------+---------------------------------------+
|            Disclaimer:  "It's mine! It's all mine!!"   -D. Duck	      |
+-----------------------------------------------------------------------------+

mcooper@sunb3.cs.uiuc.edu (08/30/90)

Many siggested using the OrderedDither code from the Graphics Gems code off
of weedeater.

This I did, and I think it will work just fine..

thanks to all who responded.


+-------------------------------------+---------------------------------------+
|  "When the going gets weird,        |                                       |
|              the weird turn pro."   |  Marc Cooper	marcc@ncsa.uiuc.edu   |
|		  		      |  National Center for Supercomputing   |
|		 -Hunter S. Thompson  |		    Applications	      |
+-------------------------------------+---------------------------------------+
|            Disclaimer:  "It's mine! It's all mine!!"   -D. Duck	      |
+-----------------------------------------------------------------------------+

hawley@adobe.COM (Steve Hawley) (08/31/90)

Here's how to do this:

Go ftp to an archive with the Graphics Gems sources and get the source code
that generates dithering matrices.  Get it up and running, and generate an
8x8 matrix.  Include it in a C program that uses it to dither an 8-bit deep
bitmap down to bi-level, iterating over the value for the percentage in your
8-bit deep map.

something like:

int i;

for (i=0; i < 256; i++) {
   fill8bitwith(i);
   dithermy8bitdownto1();
   printmy1bit();
}

where you're using globals for your bitmaps (no point in getting general for a
single case.

It will work.  Trust me.  I wrote the chapter about dithering.  :')

Steve Hawley
hawley@adobe.com
-- 
"I can always telephone, but I can't tell it much."
	-Roy Blount

mpogue@dg-rtp.dg.com (Mike Pogue) (08/31/90)

In article <23900013@sunb4>, mcooper@sunb4.cs.uiuc.edu writes:
|> 
|> I'm looking for an algorithm (or C code, of you have it) to generate
|> 16 x 16 bit masks.  Ideally, I should be able to specify a percentage and
|> the program should spit out the pattern filled appropriately.
|> 

   The algorithm you want (called ordered dither) is described in both
the Graphics Gems book, and the new edition of Foley and VanDam.

Mike Pogue
Data General Corp.

Speaking for myself alone....

falk@peregrine.Sun.COM (Ed Falk) (08/31/90)

In article <23900013@sunb4> mcooper@sunb4.cs.uiuc.edu writes:
>
>I'm looking for an algorithm (or C code, of you have it) to generate
>16 x 16 bit masks.  Ideally, I should be able to specify a percentage and
>the program should spit out the pattern filled appropriately.
>
>ie.
>
>100% yeilds
>
> [all 1's]
>
>This is no problem to write,m but the simple way gives you nasty artifacts such
>as:  25 % yeilds
>
> [25% 1's]
>
>
>Does anyone have code that will properly randomize this stuff to avoid the
>inevitable artifacts and moire patterns?

It seems to me that what you're asking for is a way to generate
dither patterns.  If you don't mind regular patterns, which generally
is the best way to go, use this dither matrix:


static	int	d16[16][16] = {
	{  0,192, 48,240, 12,204, 60,252,  3,195, 51,243, 15,207, 63,255},
	{128, 64,176,112,140, 76,188,124,131, 67,179,115,143, 79,191,127},
	{ 32,224, 16,208, 44,236, 28,220, 35,227, 19,211, 47,239, 31,223},
	{160, 96,144, 80,172,108,156, 92,163, 99,147, 83,175,111,159, 95},
	{  8,200, 56,248,  4,196, 52,244, 11,203, 59,251,  7,199, 55,247},
	{136, 72,184,120,132, 68,180,116,139, 75,187,123,135, 71,183,119},
	{ 40,232, 24,216, 36,228, 20,212, 43,235, 27,219, 39,231, 23,215},
	{168,104,152, 88,164,100,148, 84,171,107,155, 91,167,103,151, 87},
	{  2,194, 50,242, 14,206, 62,254,  1,193, 49,241, 13,205, 61,253},
	{130, 66,178,114,142, 78,190,126,129, 65,177,113,141, 77,189,125},
	{ 34,226, 18,210, 46,238, 30,222, 33,225, 17,209, 45,237, 29,221},
	{162, 98,146, 82,174,110,158, 94,161, 97,145, 81,173,109,157, 93},
	{ 10,202, 58,250,  6,198, 54,246,  9,201, 57,249,  5,197, 53,245},
	{138, 74,186,122,134, 70,182,118,137, 73,185,121,133, 69,181,117},
	{ 42,234, 26,218, 38,230, 22,214, 41,233, 25,217, 37,229, 21,213},
	{170,106,154, 90,166,102,150, 86,169,105,153, 89,165,101,149, 85}} ;

This maps intensities from 0-255 to either 0 or 1 by these rules:
Take the x and y coordinates of the pixel, mod 16, and use them as an
index into this array.  If the intensity is less than or equal to
this value, write a 0, otherwise, write a 1.

If the intensity is 256, always write a 1.

This is called ordered dithering.

So, if you were to write a solid field of value 256 (100%), you would get

	1111
	1111
	1111
	1111

If you were to write a solid field of value 64 (50%), you would get

	1010
	0000
	1010
	0000

and so on.  If you were to take a greyscale image, and map each pixel,
you would get something you could display on a monochrome monitor.


	-ed falk, sun microsystems -- sun!falk, falk@sun.com
	"What are politicians going to tell people when the
	Constitution is gone and we still have a drug problem?"
			-- William Simpson, A.C.L.U.

jgk@osc.COM (Joe Keane) (09/01/90)

The problem seems to be the same as dithering an arbitrary image; in this case
the image is a constant gray value.  At least, i haven't found a simpler way.

A matrix dither works OK, and is clearly easy to do.  The problem is that some
of the patterns aren't so hot.  Also, it quantizes your gray levels, so you
don't get exactly what you asked for.

I think the best way is with some sort of error-propogating algorithm.  My
favorite is bidirectional Floyd-Steinberg, which generally produces nice
patterns but has some occasional annoying artifacts.

If you don't need repeating patterns, you should add some blue noise and then
dither that.  This makes the `nicest' patterns, since they are somewhat
random, and don't have any features that stick out.

peterdun@microsoft.UUCP (Peter DUNIHO) (09/05/90)

In article <23900013@sunb4>, mcooper@sunb4.cs.uiuc.edu writes:
> 
> I'm looking for an algorithm (or C code, of you have it) to generate
> 16 x 16 bit masks.  Ideally, I should be able to specify a percentage and
> the program should spit out the pattern filled appropriately.
> 
> 
> Does anyone have code that will properly randomize this stuff to avoid the
> inevitable artifacts and moire patterns?
> 
> 

Sounds to me like you need some good dithering algorithms.  I don't really
know where to look for references, but I would start with ACM journals and
graphics books...

erich@eye.com ( Eric Haines) (09/05/90)

In article <23900013@sunb4> mcooper@sunb4.cs.uiuc.edu writes:
>
>I'm looking for an algorithm (or C code, of you have it) to generate
>16 x 16 bit masks.  Ideally, I should be able to specify a percentage and
>the program should spit out the pattern filled appropriately.
>
>ie.
>
>100% yeilds
>
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>1111111111111111
>
>This is no problem to write,m but the simple way gives you nasty artifacts such
>as:  25 % yeilds
>
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>1000100010001000
>
>
>Does anyone have code that will properly randomize this stuff to avoid the
>inevitable artifacts and moire patterns?
>
>
>+-------------------------------------+---------------------------------------+
>|  "When the going gets weird,        |                                       |
>|              the weird turn pro."   |  Marc Cooper	marcc@ncsa.uiuc.edu   |
>|		  		      |  National Center for Supercomputing   |
>|		 -Hunter S. Thompson  |		    Applications	      |
>+-------------------------------------+---------------------------------------+
>|            Disclaimer:  "It's mine! It's all mine!!"   -D. Duck	      |
>+-----------------------------------------------------------------------------+