GP2X Making Images Prettier With Dithering


Micket

Member
Joined
Jul 16, 2006
Messages
196
Age
40
Location
Sweden, Gothenburg
Website
www.micket.com
Well. I for one was slightly bothered by the sometimes lacking colors in 16-bit. Well, at least when it came to different gradients (most likely seen in menus and such) so i tried to apply some dithering to them, and i must say i'm quite pleased with the results
First off, a familiar example from squidgesnes;
Original
original.png

As you see it a.t.m on the gp2x;
nodither.png

As you COULD see if when applying a rather precise floyd-steinberg dithering
dither.png

I even tried running a version which gave these results in realtime (at each time the menu was drawn, without any noticeable lag);
simple.png

I also optimized the algorithm for the last version quite a bit, so it has potential at running in realtime in more then just a slow menu i think. (It could probably be improved quite a bit, depending on how you draw your graphics)

Also, since examples are always fun, here is another one;
Original
original2.png

As it's seen on the gp2x
nodither2.png

16bit decimal presision floyd-steinberg dithering
dither2.png

Simplified floyd-steinberg dithering
simple2.png


And for the source of my test program
note! i only bothered with the dithering algorithm, the actual png handling is pretty much hack and slash until it worked, especially writing, The images get really big, so i just resaved them in gimp to get a decent filesize, if anyone wants to improve this to make a decent program for actual use for people doing graphics for the gp2x, feel free to change)

Oh.. i also hope there is no problem using these images as examples? If there are any problems with it pm me and i'll take them down.

edit: DOH forgot to post the source
http://www.micket.com/Code/dither/gp2x_png.c

edit 2: To clear up a few things;
My example program can be used now to process images before put n the gp2x to see the improvements in many programs, it's not meant to be run on the gp2x in any way but improve the graphics for it. It can output any of the versions shown above.
I never planned the high precision dithering to be run in realtime on the gp2x, however the simplier version does have some potential to do that (perhaps in the photo viewer).
 
For an easier solution, you can go to Telegraphics and download some Photoshop plugins. They have one which can dither to 565 (16bit) and 555 (15bit) color space.

If you don't have Photoshop, you can use the plugins with Irfanview.
 
Ah. well i dont use windows at all myself, and anyone else in linux not wanting to bother with wine can actually use my program, It comiles as simply as "gcc gp2x_png.c -lpng" and actually does work very easily, it just makes the files quite big atm as i haven't set any compression to it.

Also, stuff that uses alpha blending at runtime can't get anything out from a preprocessed dither fully (if the alpha channel has some kind of larger gradient)

I was thinking about changing the photo viewer in the gp2x to include dithering, is it's source available anywhere?
 
I'm sure theres some Linux program which takes Photoshop/Filter Factory filters, Filter Factory is open source.
 
Blah posted on Aug 13 2006 at 04:54 AM said:
I'm sure theres some Linux program which takes Photoshop/Filter Factory filters, Filter Factory is open source.

I've seen some hack to make gimp run them, but no binary for debian, and i haven't gone through the bother to compile it yet.
I got a friend to send my two tests (of squidgesnes and gmenu2x images above) and i checked them out.
Just by looking the different results are indistinguishable, however i did notice one thing when looking into the details, it chooses to place the values spread out to 0-255 with the best spread of 5 (or 6 for green i guess) bits.
(I'm not sure of this, but i am sure that either this plugin, or photoshop is making something to produce pixels where the least significent bits aren't 0)
While it gives nice results (although a slight increase in contrast) on a device displaying 24 bit, you'll have to convert those 8 bit values to 5 and 6 bit values.
I can't really see any pratical fast way to convert them on the gp2x when it comes to actually displaying them.
Compare with just shifting 2 or 3 bits (the method i think most programs are using already with none dithering images) by just using the most significent bits that my example program does.

Also.. i can't really say i'm tempted to use any code from that plugin when it comes to making runtime algorithms/ changing the photo viewer.
 
Last edited by a moderator:
the biggest problem with dithering is that it makes the image filesize bigger if you are using PNG, or decreases the image quality if you are using JPEG.
 
Sparr posted on Aug 13 2006 at 10:37 PM said:
the biggest problem with dithering is that it makes the image filesize bigger if you are using PNG, or decreases the image quality if you are using JPEG.

Not if you do it at run-time ;) Of course that introduces the different negative of slower performance, if it's for anything more frequent than a title screen.
 
Last edited by a moderator:
BradN posted on Aug 14 2006 at 07:03 AM said:
Sparr posted on Aug 13 2006 at 10:37 PM said:
the biggest problem with dithering is that it makes the image filesize bigger if you are using PNG, or decreases the image quality if you are using JPEG.

Not if you do it at run-time ;) Of course that introduces the different negative of slower performance, if it's for anything more frequent than a title screen.

If you do it when you actually load the files and not everytime you draw a frame there will pretty much be no negative effect whatsoever.
But i'm having a hard time seeing that filesize would ever be an issue. It's certainly not bothering people alot atm, as for example squidgesnes used bmp's.
When loaded they wont use any more memory than the original
And to finish it all of; My simple dithering actually decreased the filesize for the gmenu2x background, and the squidgesnes image barely got any bigger.

Although, if you really really want to cut down the filesize, you should still do what my example program is doing with no dithering, cutting down colors to the actual 16bits that can be displayed => smaller files.

Still, if you are using jpeg then image quality is appearantly not an issue for you and dithering is pointless :)
 
Last edited by a moderator:
I've done quite a bit of improvement in my testprogram.
It's still on;
http://www.micket.com/Code/dither/gp2x_png.c
and should compile with something as simple as
gcc -lpng -std=c99 gp2x_png.c -o gp2x_png
you'll probably want to run
./gp2x_png -f -c -p=ff00ff imagein.png imageout.png
most of the times (with ff00ff beeing a protected color, if you use it for transparency)
What needs to be done is better error handling, better support at paletted images, support for more than 1 protected colors and probably alot more stuff i haven't even started to notice yet.

However, the program is quite useable. I just updated the graphics for my copy of squidgesnes along with the change to pngfiles for it, and it was rather easy and the results look good.

edit: Just to clear things up a bit here. Im not trying to compete with pngcrush, advpng, pngout or any similiar program.
If so, i'm pretty sure i'd have named the topic "Making png's smaller".
The main use is to apply a 16 bit dither to images to make gradients appear smoother on the gp2x, or simple reduce colors to 16 bit.
You can also just crop down the colors to 565 if size is an issue. If you did for the menu i'd look identical on the gp2x as you are seeing in squidgesnes right now (with the not-so-small 24 bpp BMP you probably got). Combined with a suitable png-crusher you should achive record low filesize.
 
I'm curious how dithering on RGB compares to using the YCbCr layers, particularly for JPEG. Ultimately it probably comes down to the color resolution of the LCD (although there is supposedly hardware dithering for that...), but you get 8 bits of Y per pixel and 8 bits of Cb and Cr per pair of pixels.
 
Back
Top