use clap::{arg, value_parser, Command};
use std::{num::NonZeroU32, path::PathBuf};

fn main() {
    let matches = Command::new("smartcrop-cli")
        .arg(arg!(<INPUT> "Input image file").value_parser(value_parser!(PathBuf)))
        .arg(arg!([OUTPUT] "Output image file").value_parser(value_parser!(PathBuf)))
        .arg(
            arg!(--width)
                .default_value("100")
                .value_parser(value_parser!(NonZeroU32)),
        )
        .arg(
            arg!(--height)
                .default_value("100")
                .value_parser(value_parser!(NonZeroU32)),
        )
        .arg(arg!(--scaled "Scale the image to exactly the given size"))
        .arg(arg!(--"no-borders" "Remove black borders around an image before finding the best crop"))
        .get_matches();

    let file_in = matches.get_one::<PathBuf>("INPUT").unwrap();
    let file_out = matches
        .get_one::<PathBuf>("OUTPUT")
        .cloned()
        .unwrap_or_else(|| {
            file_in.with_file_name(format!(
                "{}.crop.{}",
                file_in
                    .file_stem()
                    .and_then(|s| s.to_str())
                    .unwrap_or("image"),
                file_in
                    .extension()
                    .and_then(|s| s.to_str())
                    .unwrap_or("jpg")
            ))
        });
    let width = *matches.get_one::<NonZeroU32>("width").unwrap();
    let height = *matches.get_one::<NonZeroU32>("height").unwrap();

    // Use the open function to load an image from a Path.
    // ```open``` returns a `DynamicImage` on success.
    let mut img = image::open(file_in).unwrap();

    let crop = if matches.get_flag("no-borders") {
        smartcrop::find_best_crop_no_borders(&img, width, height).unwrap()
    } else {
        smartcrop::find_best_crop(&img, width, height).unwrap()
    };
    let c = &crop.crop;
    let mut cropped = img.crop(c.x, c.y, c.width, c.height);

    if matches.get_flag("scaled") {
        cropped = cropped.resize(
            width.into(),
            height.into(),
            image::imageops::FilterType::Lanczos3,
        );
    }

    cropped.save(file_out).unwrap();
    println!("{:#?}", crop);
}
