Expand description
Buffer-first rust dithering and halftoning library.
Quantizing grayscale/RGB/RGBA buffers without dithering creates visible
banding and contouring. dithr provides deterministic ordered dithering,
diffusion, stochastic binary methods, palette-constrained workflows, and
advanced halftoning methods over typed mutable slices.
§Overview
- Buffer-first API: Operates on mutable pixel slices with explicit width/height/stride.
- Typed sample support:
u8,u16, andf32. - Typed layout support: Gray, Rgb, and Rgba.
- Shared quantization model:
QuantizeModeis used across families. - Algorithm coverage: Stochastic, ordered, palette-oriented ordered, diffusion, variable diffusion, and advanced halftoning.
- Optional integrations:
imageadapters andrayonparallel wrappers.
§Quick Start
use dithr::{gray_u8, QuantizeMode, Result};
use dithr::ordered::bayer_8x8_in_place;
fn main() -> Result<()> {
let width = 64_usize;
let height = 64_usize;
let mut data = Vec::with_capacity(width * height);
for y in 0..height {
for x in 0..width {
let value = ((x + y * width) * 255 / (width * height - 1)) as u8;
data.push(value);
}
}
let mut buffer = gray_u8(&mut data, width, height, width)?;
bayer_8x8_in_place(&mut buffer, QuantizeMode::gray_bits(1)?)?;
assert!(data.iter().all(|&v| v == 0 || v == 255));
Ok(())
}§Core Types and Buffer Model
Buffer and format types:
BufferBufferKind(runtime format metadata)PixelFormat(type alias ofBufferKind)BufferError
Generic and typed buffer aliases:
GrayBuffer,RgbBuffer,RgbaBufferGrayBuffer8,RgbBuffer8,RgbaBuffer8GrayBuffer16,RgbBuffer16,RgbaBuffer16GrayBuffer32F,RgbBuffer32F,RgbaBuffer32F
Constructors:
- Gray:
gray_u8,gray_u16,gray_32f - Gray packed:
gray_u8_packed,gray_u16_packed,gray_32f_packed - Rgb:
rgb_u8,rgb_u16,rgb_32f - Rgb packed:
rgb_u8_packed,rgb_u16_packed,rgb_32f_packed - Rgba:
rgba_u8,rgba_u16,rgba_32f - Rgba packed:
rgba_u8_packed,rgba_u16_packed,rgba_32f_packed
Runtime kinds covered by BufferKind:
Gray8,Rgb8,Rgba8Gray16,Rgb16,Rgba16Gray32F,Rgb32F,Rgba32F
§Quantization API
Quantization mode enum:
Quantization constructors/helpers:
QuantizeMode::gray_levelsQuantizeMode::rgb_levelsQuantizeMode::paletteQuantizeMode::single_colorQuantizeMode::gray_bits(u8specialization)QuantizeMode::rgb_bits(u8specialization)levels_from_bits
Quantization functions:
Error alias:
QuantizeError(alias of crateError)
§Palette and Indexed Output API
Palette types:
Indexed image types:
Built-in palette helpers:
§Algorithm Families
Binary stochastic:
threshold_binary_in_placerandom_binary_in_place- compatibility aliases:
threshold_in_place,random_in_place
Ordered:
- Bayer:
bayer_2x2_in_place,bayer_4x4_in_place,bayer_8x8_in_place,bayer_16x16_in_place - Cluster-dot:
cluster_dot_4x4_in_place,cluster_dot_8x8_in_place - Custom map:
custom_ordered_in_place
Palette-oriented ordered (Yliluoma):
Diffusion (classic):
floyd_steinberg_in_placefalse_floyd_steinberg_in_placejarvis_judice_ninke_in_placestucki_in_placeburkes_in_placesierra_in_placetwo_row_sierra_in_placesierra_lite_in_placestevenson_arce_in_placeatkinson_in_place
Diffusion (extended):
Variable diffusion:
Advanced halftoning:
riemersma_in_placeknuth_dot_diffusion_in_placedirect_binary_search_in_placelattice_boltzmann_in_placeelectrostatic_halftoning_in_place
Scope notes:
ostromoukhov_in_place,zhou_fang_in_place, andgradient_based_error_diffusion_in_placeare grayscale-only.direct_binary_search_in_place,lattice_boltzmann_in_place, andelectrostatic_halftoning_in_placeare integer grayscale-only.
§Parallel API (rayon feature)
Parallel ordered wrappers:
bayer_2x2_in_place_parbayer_4x4_in_place_parbayer_8x8_in_place_parbayer_16x16_in_place_parcluster_dot_4x4_in_place_parcluster_dot_8x8_in_place_parcustom_ordered_in_place_paryliluoma_1_in_place_paryliluoma_2_in_place_paryliluoma_3_in_place_par
Parallel stochastic wrappers:
threshold_binary_in_place_parrandom_binary_in_place_par
§Image Adapter API (image feature)
Adapter enum:
DynamicImageBufferGray8,Rgb8,Rgba8Gray16,Rgb16,Rgba16Rgb32F,Rgba32F
Typed adapters:
gray8_image_as_bufferrgb8_image_as_bufferrgba8_image_as_buffergray16_image_as_bufferrgb16_image_as_bufferrgba16_image_as_bufferrgb32f_image_as_bufferrgba32f_image_as_buffer
Compatibility adapter names:
gray_image_as_bufferrgb_image_as_bufferrgba_image_as_buffer
Dynamic adapter:
dynamic_image_as_bufferDynamicImage::ImageLumaA8is promoted toDynamicImageBuffer::Rgba8DynamicImage::ImageLumaA16is promoted toDynamicImageBuffer::Rgba16
§Errors and Result Types
Crate-level error/result:
Family-specific error types re-exported at crate root:
§Convenience Wrappers
For complete workflows and runnable examples, see examples/ and the
repository README.
Re-exports§
pub use buffer::gray_32f;pub use buffer::gray_32f_packed;pub use buffer::gray_u16;pub use buffer::gray_u16_packed;pub use buffer::gray_u8;pub use buffer::gray_u8_packed;pub use buffer::rgb_32f;pub use buffer::rgb_32f_packed;pub use buffer::rgb_u16;pub use buffer::rgb_u16_packed;pub use buffer::rgb_u8;pub use buffer::rgb_u8_packed;pub use buffer::rgba_32f;pub use buffer::rgba_32f_packed;pub use buffer::rgba_u16;pub use buffer::rgba_u16_packed;pub use buffer::rgba_u8;pub use buffer::rgba_u8_packed;pub use buffer::Buffer;pub use buffer::BufferError;pub use buffer::BufferKind;pub use buffer::GrayBuffer;pub use buffer::GrayBuffer16;pub use buffer::GrayBuffer32F;pub use buffer::GrayBuffer8;pub use buffer::PixelFormat;pub use buffer::RgbBuffer;pub use buffer::RgbBuffer16;pub use buffer::RgbBuffer32F;pub use buffer::RgbBuffer8;pub use buffer::RgbaBuffer;pub use buffer::RgbaBuffer16;pub use buffer::RgbaBuffer32F;pub use buffer::RgbaBuffer8;pub use data::cga_palette;pub use data::grayscale_16;pub use data::grayscale_2;pub use data::grayscale_4;pub use error::Error;pub use error::Result;pub use ordered::OrderedError;pub use palette::IndexedImage;pub use palette::IndexedImage16;pub use palette::IndexedImage32F;pub use palette::IndexedImage8;pub use palette::Palette;pub use palette::Palette16;pub use palette::Palette32F;pub use palette::Palette8;pub use palette::PaletteError;pub use quantize::levels_from_bits;pub use quantize::quantize_error;pub use quantize::quantize_gray;pub use quantize::quantize_gray_u8;pub use quantize::quantize_pixel;pub use quantize::quantize_rgb;pub use quantize::quantize_rgb_u8;pub use quantize::QuantizeError;pub use quantize::QuantizeMode;pub use buffer::gray_f32;Deprecated pub use buffer::rgb_f32;Deprecated pub use buffer::rgba_f32;Deprecated pub use dbs::direct_binary_search_in_place;pub use dbs::electrostatic_halftoning_in_place;pub use dbs::lattice_boltzmann_in_place;pub use diffusion::atkinson_in_place;pub use diffusion::burkes_in_place;pub use diffusion::false_floyd_steinberg_in_place;pub use diffusion::fan_in_place;pub use diffusion::floyd_steinberg_in_place;pub use diffusion::gradient_based_error_diffusion_in_place;pub use diffusion::jarvis_judice_ninke_in_place;pub use diffusion::ostromoukhov_in_place;pub use diffusion::shiau_fan_2_in_place;pub use diffusion::shiau_fan_in_place;pub use diffusion::sierra_in_place;pub use diffusion::sierra_lite_in_place;pub use diffusion::stevenson_arce_in_place;pub use diffusion::stucki_in_place;pub use diffusion::two_row_sierra_in_place;pub use diffusion::zhou_fang_in_place;pub use dot_diffusion::knuth_dot_diffusion_in_place;pub use ordered::bayer_16x16_in_place;pub use ordered::bayer_2x2_in_place;pub use ordered::bayer_4x4_in_place;pub use ordered::bayer_8x8_in_place;pub use ordered::cluster_dot_4x4_in_place;pub use ordered::cluster_dot_8x8_in_place;pub use ordered::custom_ordered_in_place;pub use ordered::yliluoma_1_in_place;pub use ordered::yliluoma_2_in_place;pub use ordered::yliluoma_3_in_place;pub use riemersma::riemersma_in_place;pub use stochastic::random_binary_in_place;pub use stochastic::random_in_place;Deprecated pub use stochastic::threshold_binary_in_place;pub use stochastic::threshold_in_place;Deprecated
Modules§
Functions§
- bayer_
8x8_ rgb16_ in_ place Deprecated - floyd_
steinberg_ gray_ u16_ in_ place Deprecated