use image::{GrayImage, Luma};
use imageproc::region_labelling::connected_components;
use imageproc::region_labelling::Connectivity;
use crate::component::Component;
use crate::config::Config;
pub fn component_detection(
binary: &GrayImage,
config: &Config,
rect_detect: bool,
) -> (Vec<Component>, Vec<Component>) {
let (rows, cols) = (binary.height() as u32, binary.width() as u32);
let labels = connected_components(binary, Connectivity::Eight, Luma([0u8]));
let mut label_pixels: Vec<Vec<(u32, u32)>> = Vec::new();
label_pixels.push(vec![]);
for y in 0..rows {
for x in 0..cols {
let label = labels.get_pixel(x, y)[0];
if label > 0 {
let idx = label as usize;
if idx >= label_pixels.len() {
label_pixels.push(vec![]);
}
label_pixels[idx].push((y, x)); }
}
}
let mut comps_all = Vec::new();
let mut comps_rect = Vec::new();
let mut comps_nonrect = Vec::new();
for (label, pixels) in label_pixels.iter().enumerate() {
if label == 0 || pixels.len() < config.obj_min_area as usize {
continue;
}
let mut comp = Component::new(pixels.clone());
if comp.bbox.width() <= 3 || comp.bbox.height() <= 3 {
continue;
}
if rect_detect {
if comp.is_rectangle(
config.rec_max_dent_ratio,
config.rec_min_evenness,
config.rec_corner_skip_ratio,
) {
comps_rect.push(comp);
} else {
comps_nonrect.push(comp);
}
} else {
comps_all.push(comp);
}
}
if rect_detect {
(comps_rect, comps_nonrect)
} else {
(comps_all, vec![])
}
}