← back to marc47marc47__jpg2ascii

Function bodies 18 total

All specs Real LLM only Function bodies
bench_convert function · rust · L3-L20 (18 LOC)
benches/convert_bench.rs
pub fn bench_convert(c: &mut Criterion) {
    let img = "image2ascii/convert/testdata/husky_300x300.jpg";
    let mut group = c.benchmark_group("convert");
    for &w in &[80u32, 120u32, 160u32] {
        group.throughput(Throughput::Elements((w as u64) * 100));
        group.bench_with_input(BenchmarkId::from_parameter(w), &w, |b, &width| {
            b.iter(|| {
                let cfg = Config {
                    width: Some(width),
                    ..Default::default()
                };
                let _ = convert_path_to_ascii(img, &cfg).unwrap();
            });
        });
    }
    group.finish();
}
main function · rust · L6-L29 (24 LOC)
examples/basic.rs
fn main() -> anyhow::Result<()> {
    // Optional arg: path to image. If not provided, search ./examples for the first image.
    let args: Vec<String> = env::args().skip(1).collect();
    let img_path = if let Some(p) = args.first() {
        PathBuf::from(p)
    } else if let Some(p) = find_example_image()? {
        println!("[info] Using example image: {}", p.display());
        p
    } else {
        println!(
            "No image argument provided and no image found under ./examples.\n  - Run: cargo run --example basic -- <image_path>\n  - Or place a .jpg/.jpeg/.png/.gif in ./examples and rerun"
        );
        std::process::exit(1);
    };

    let cfg = Config {
        width: Some(80),
        ..Default::default()
    };
    let ascii = convert_path_to_ascii(&img_path, &cfg)?;
    println!("{}", ascii);
    Ok(())
}
find_example_image function · rust · L30-L47 (18 LOC)
examples/basic.rs
fn find_example_image() -> anyhow::Result<Option<PathBuf>> {
    let dir = PathBuf::from("examples");
    if !dir.exists() {
        return Ok(None);
    }
    let exts = ["jpg", "jpeg", "png", "gif"];
    for entry in fs::read_dir(dir)? {
        let entry = entry?;
        let p = entry.path();
        if let Some(ext) = p.extension().and_then(|e| e.to_str()) {
            if exts.iter().any(|x| x.eq_ignore_ascii_case(ext)) {
                return Ok(Some(p));
            }
        }
    }
    Ok(None)
}
default function · rust · L28-L43 (16 LOC)
src/lib.rs
    fn default() -> Self {
        Self {
            width: None,
            height: None,
            scale: None,
            charset: DEFAULT_CHARSET.to_string(),
            invert: false,
            color: false,
            brightness: 0.0,
            gamma: 1.0,
            contrast: 1.0,
            threshold: None,
            aspect: 2.0,
            filter: FilterType::Triangle,
        }
    }
convert_path_to_ascii function · rust · L45-L49 (5 LOC)
src/lib.rs
pub fn convert_path_to_ascii<P: AsRef<Path>>(path: P, cfg: &Config) -> Result<String> {
    let img = image::open(path)?;
    Ok(convert_image_to_ascii(&img, cfg))
}
convert_bytes_to_ascii function · rust · L50-L54 (5 LOC)
src/lib.rs
pub fn convert_bytes_to_ascii(bytes: &[u8], cfg: &Config) -> Result<String> {
    let img = image::load_from_memory(bytes)?;
    Ok(convert_image_to_ascii(&img, cfg))
}
convert_gif_bytes_to_ascii_frames function · rust · L55-L68 (14 LOC)
src/lib.rs
pub fn convert_gif_bytes_to_ascii_frames(bytes: &[u8], cfg: &Config) -> Result<Vec<String>> {
    let cursor = Cursor::new(bytes);
    let decoder = GifDecoder::new(cursor)?;
    let frames = decoder.into_frames();
    let mut out = Vec::new();
    for f in frames {
        let f = f?;
        let buf = f.into_buffer();
        let dynimg = DynamicImage::ImageRgba8(buf);
        out.push(convert_image_to_ascii(&dynimg, cfg));
    }
    Ok(out)
}
Repobility · code-quality intelligence platform · https://repobility.com
convert_gif_path_to_ascii_frames function · rust · L69-L76 (8 LOC)
src/lib.rs
pub fn convert_gif_path_to_ascii_frames<P: AsRef<Path>>(
    path: P,
    cfg: &Config,
) -> Result<Vec<String>> {
    let bytes = std::fs::read(path)?;
    convert_gif_bytes_to_ascii_frames(&bytes, cfg)
}
convert_image_to_ascii function · rust · L77-L81 (5 LOC)
src/lib.rs
pub fn convert_image_to_ascii(img: &DynamicImage, cfg: &Config) -> String {
    let lines = convert_image_to_ascii_lines(img, cfg);
    lines.join("\n")
}
convert_image_to_ascii_lines function · rust · L82-L136 (55 LOC)
src/lib.rs
pub fn convert_image_to_ascii_lines(img: &DynamicImage, cfg: &Config) -> Vec<String> {
    let (tw, th) = target_size(img.dimensions(), cfg);
    let resized = img.resize_exact(tw, th, cfg.filter).to_rgba8();

    (0..th)
        .into_par_iter()
        .map(|y| {
            let mut line = String::with_capacity(tw as usize);
            for x in 0..tw {
                let px = resized.get_pixel(x, y);
                let (r, g, b, a) = (px[0], px[1], px[2], px[3]);
                // blend alpha on black background
                let (r, g, b) = if a < 255 {
                    let af = (a as f32) / 255.0;
                    (
                        (r as f32 * af) as u8,
                        (g as f32 * af) as u8,
                        (b as f32 * af) as u8,
                    )
                } else {
                    (r, g, b)
                };
                let mut lum = luminance(r, g, b);
                // brightness offset
                if cfg.brightness !
luminance function · rust · L184-L188 (5 LOC)
src/lib.rs
fn luminance(r: u8, g: u8, b: u8) -> f32 {
    // linearized approximation is omitted; keep simple sRGB weights
    (0.2126 * (r as f32) + 0.7152 * (g as f32) + 0.0722 * (b as f32)) / 255.0
}
map_luma_to_char function · rust · L189-L199 (11 LOC)
src/lib.rs
fn map_luma_to_char(lum: f32, charset: &str, invert: bool) -> char {
    let mut chars: Vec<char> = charset.chars().collect();
    if chars.is_empty() {
        chars = DEFAULT_CHARSET.chars().collect();
    }
    let n = chars.len();
    let v = if invert { 1.0 - lum } else { lum }.clamp(0.0, 1.0);
    let idx = (v * (n as f32 - 1.0)).round() as usize;
    chars[idx]
}
test_luminance_basic function · rust · L207-L212 (6 LOC)
src/lib.rs
    fn test_luminance_basic() {
        assert!((luminance(0, 0, 0) - 0.0).abs() < 1e-6);
        assert!((luminance(255, 255, 255) - 1.0).abs() < 1e-6);
        let gray = luminance(128, 128, 128);
        assert!(gray > 0.4 && gray < 0.6);
    }
test_map_luma_to_char_invert function · rust · L215-L223 (9 LOC)
src/lib.rs
    fn test_map_luma_to_char_invert() {
        let cs = " .#"; // 0 -> space, 1 -> '#'
        let c1 = map_luma_to_char(0.0, cs, false);
        let c2 = map_luma_to_char(1.0, cs, false);
        let c3 = map_luma_to_char(0.0, cs, true);
        assert_eq!(c1, ' ');
        assert_eq!(c2, '#');
        assert_eq!(c3, '#');
    }
test_target_size_defaults function · rust · L226-L231 (6 LOC)
src/lib.rs
    fn test_target_size_defaults() {
        let cfg = Config::default();
        let (w, h) = super::target_size((400, 200), &cfg);
        assert_eq!(w, 80);
        assert!(h > 0);
    }
Methodology: Repobility · https://repobility.com/research/state-of-ai-code-2026/
main function · rust · L78-L159 (82 LOC)
src/main.rs
fn main() -> anyhow::Result<()> {
    let args = Cli::parse();
    let use_color = args.color && !args.no_color && ansi_supported();
    let cfg = Config {
        width: args.width,
        height: args.height,
        scale: args.scale,
        charset: args.charset,
        invert: args.invert,
        color: use_color,
        brightness: args.brightness,
        gamma: args.gamma,
        contrast: args.contrast,
        threshold: args.threshold,
        aspect: args.aspect,
        ..Default::default()
    };

    if args.animate {
        // Render frames (GIF) and animate to stdout with clear between frames
        let frames: Vec<String> = if args.input.as_os_str() == "-" {
            use std::io::Read;
            let mut buf = Vec::new();
            io::stdin().read_to_end(&mut buf)?;
            match convert_gif_bytes_to_ascii_frames(&buf, &cfg) {
                Ok(f) => f,
                Err(_) => vec![convert_bytes_to_ascii(&buf, &cfg)?],
            }
        } el
ansi_supported function · rust · L160-L185 (26 LOC)
src/main.rs
fn ansi_supported() -> bool {
    // Disable if NO_COLOR is set
    if std::env::var_os("NO_COLOR").is_some() {
        return false;
    }
    // Only enable on TTY
    if !atty::is(atty::Stream::Stdout) {
        return false;
    }
    // On Windows, try enabling VT processing
    #[cfg(windows)]
    if enable_windows_ansi() {
        return true;
    }
    // Heuristic using TERM
    if let Ok(term) = std::env::var("TERM") {
        let t = term.to_ascii_lowercase();
        return t.contains("xterm")
            || t.contains("ansi")
            || t.contains("vt100")
            || t.contains("screen");
    }
    // On modern Windows terminals truecolor is typically supported; default to true
    cfg!(windows)
}
enable_windows_ansi function · rust · L188-L205 (18 LOC)
src/main.rs
fn enable_windows_ansi() -> bool {
    use windows_sys::Win32::System::Console::{
        GetConsoleMode, GetStdHandle, SetConsoleMode, ENABLE_VIRTUAL_TERMINAL_PROCESSING,
        STD_OUTPUT_HANDLE,
    };
    unsafe {
        let handle = GetStdHandle(STD_OUTPUT_HANDLE);
        if handle == 0 {
            return false;
        }
        let mut mode: u32 = 0;
        if GetConsoleMode(handle, &mut mode) == 0 {
            return false;
        }
        let new_mode = mode | ENABLE_VIRTUAL_TERMINAL_PROCESSING;
        SetConsoleMode(handle, new_mode) != 0
    }
}