Skip to content

Dither Algorithm

Michael R Sweet edited this page Mar 19, 2025 · 1 revision

This page discusses the dithering algorithm used by LPrint, which is an adaptive algorithm that uses thresholding near 100% black or white areas and shading otherwise to ensure that barcodes and text are printed clearly. The API also handles any page/label margins so that the output code can focus exclusively on lines of bitmap data for the printer in question.

Sources:

  • "lprint-common.c": Dithering code
  • "lprint.h": API/structure definitions

API

The API is provided by one structure type and three functions.

lprint_dither_t

This structure holds the dither state for the current page. Drivers generally only need to look at the output and out_width members.

typedef struct lprint_dither_s          // Dithering state
{
  pappl_dither_t dither;                // Dither matrix to use
  unsigned char *input[4];              // Input lines for dithering (only 3 are needed, 4 makes it easier for ring buffer)
  unsigned      in_width,               // Width in pixels
                in_height,              // Height in lines
                in_left,                // Left (starting) pixel
                in_top,                 // Top-most pixel
                in_bottom;              // Bottom-most pixel
  unsigned char in_bpp,                 // Input bits per pixel (1 or 8)
                in_white;               // Input white pixel value (0 or 255)
  unsigned char *output,                // Output bitmap
                out_white;              // Output white pixel value (0 or 255)
  unsigned      out_width;              // Output width in bytes
} lprint_dither_t;

lprintDitherAlloc

Allocate memory for a dither buffer.

bool                                    // O - `true` on success, `false` on error
lprintDitherAlloc(
    lprint_dither_t    *dither,         // I - Dither buffer
    pappl_job_t        *job,            // I - Job
    pappl_pr_options_t *options,        // I - Print options
    cups_cspace_t      out_cspace,      // I - Output color space
    double             out_gamma)       // I - Output gamma correction

lprintDitherFree

Free memory for a dither buffer.

void
lprintDitherFree(
    lprint_dither_t *dither)            // I - Dither buffer

lprintDitherLine

Copy the current line and dither it as needed. true is returned if the output line needs to be sent to the printer - the output member points to the output bitmap and outwidth specifies the bitmap width in bytes.

Dithering is always 1 line behind the current line, so you need to call this function one last time in the endpage callback with y == cupsHeight to get the last line.

bool                                    // O - `true` if line dithered, `false` to skip
lprintDitherLine(
    lprint_dither_t     *dither,        // I - Dither buffer
    unsigned            y,              // I - Input line number (starting at `0`)
    const unsigned char *line)          // I - Input line
Clone this wiki locally