use super::svg::{wrap_in_svg, DEFAULT_TEXT_COLOR};
pub fn generate_bar_chart(data: &[(String, i64)]) -> String {
if data.is_empty() {
return r##""##.to_string();
}
let bar_height = 24.0;
let gap = 14.0;
let pad_top = 10.0;
let pad_bottom = 10.0;
let pad_left = 130.0;
let pad_right = 70.0;
let width = 600.0;
let height = pad_top + pad_bottom + (data.len() as f64 * (bar_height + gap)) - gap;
let chart_w = width - pad_left - pad_right;
let max_val = data.iter().map(|(_, v)| *v).max().unwrap_or(0);
let max_x = if max_val == 0 { 1.0 } else { max_val as f64 };
let mut bars = String::new();
let total_count: i64 = data.iter().map(|(_, v)| *v).sum();
for (i, (label, val)) in data.iter().enumerate() {
let y = pad_top + (i as f64 * (bar_height + gap));
let bar_w = (*val as f64 / max_x) * chart_w;
let pct = if total_count > 0 {
(*val as f64 / total_count as f64) * 100.0
} else {
0.0
};
// Truncate long labels
let display_label = if label.len() > 18 {
format!("{}...", &label[0..15])
} else {
label.to_string()
};
bars.push_str(&format!(
r##"
{label}
{val} ({pct:.1}%)
"##,
i = i,
pad_left_label = pad_left - 10.0,
text_y = y + (bar_height / 2.0) + 1.0,
label = display_label,
pad_left = pad_left,
y = y,
bar_w = bar_w.max(2.0),
bar_height = bar_height,
val_x = pad_left + bar_w.max(2.0) + 8.0,
val = val,
pct = pct,
text_color = DEFAULT_TEXT_COLOR
));
}
wrap_in_svg(width, height, &bars)
}