Comment 19 for bug 180693

Revision history for this message
Guillermo Espertino (Gez) (gespertino-gmail) wrote :

Blending in noise won't work as it won't smooth the transition areas between bands.
I suggested using a spread filter as it jitters pixels randomly within a threshold, creating a similar effect than true dithering (i.e.: creating the optical illusion of a continuous tone by mixing dots of two different colors).

The ideal solution would be to render the gradients in higher precision, then dither them down to 8bpc (as you mention, keeping 16bit would be also useful).

After some e-mail exchange at the mailing list with Tavmjong Bah, I could collect the following information. Please feel free to expand or correct it if something isn't right:

- Cairo has a 10 bit pixel format without alpha that could be useful for adding extra steps to a gradient (1024 levels vs. 256 per channel), but even with 10bpc, pixman creates the gradient at 8 bpc precision.
- Cairo does have simple dithering for it's xlib backend, but apparently it's only for indexed color. It would be interesting to evaluate if Cairo can be extended to add dithering to the image backend.
- Saving as PDF should produce a true PDF vector gradient, it's up to the PDF renderer to render it correctly (in my exprience, the libre PDF renderers out there don't).
- The way cairo is used by Inkscape might make it difficult to produce an effect like the aforementioned "spread" filter or applying any other possible solutions easily.

As it was mentioned on the mailing list too, the cause of banding is mainly rendering the gradients at 8bpc precision, which leaves only 256 levels per channel for work, an insuficient amount of levels for gradients that need to be represented in large sizes. The problem is more evident with grayscale gradients and blending gradients together with transparency.
Dithering seems unavoidable for 8bpc, even in the case of the gradients are produced in higher bit depths. If it has to be displayed as 8bpc, some form of dithering is required to avoid banding.