seperate adjust

This commit is contained in:
Julian Freeman
2026-01-19 00:41:28 -04:00
parent de0ed2bdc2
commit 3e5d5aa848
5 changed files with 76 additions and 35 deletions

View File

@@ -106,6 +106,7 @@ struct ZcaResult {
#[derive(serde::Deserialize)]
struct ExportImageTask {
path: String,
manual_position: Option<ManualPosition>,
}
#[derive(serde::Deserialize)]
@@ -116,8 +117,9 @@ struct WatermarkSettings {
color: String, // Hex code e.g. "#FFFFFF"
opacity: f64,
scale: f64, // Font size relative to image height (e.g., 0.05 = 5% of height)
manual_override: bool,
manual_position: ManualPosition,
// Global manual override is deprecated in favor of per-task control, but kept for struct compatibility if needed
_manual_override: bool,
_manual_position: ManualPosition,
}
#[derive(serde::Deserialize)]
@@ -169,9 +171,10 @@ async fn export_batch(images: Vec<ExportImageTask>, watermark: WatermarkSettings
let final_scale = PxScale::from(scale_px);
let (final_t_width, final_t_height) = imageproc::drawing::text_size(final_scale, &font, &watermark.text);
// 4. Determine Position (Center based)
let (pos_x_pct, pos_y_pct) = if watermark.manual_override {
(watermark.manual_position.x, watermark.manual_position.y)
// 4. Determine Position (Task Specific > ZCA)
// If task has manual_position, use it. Otherwise calculate ZCA.
let (pos_x_pct, pos_y_pct) = if let Some(pos) = &task.manual_position {
(pos.x, pos.y)
} else {
match calculate_zca_internal(&dynamic_img) {
Ok(res) => (res.x, res.y),
@@ -231,7 +234,21 @@ async fn export_batch(images: Vec<ExportImageTask>, watermark: WatermarkSettings
// Save
let file_name = input_path.file_name().unwrap_or_default();
let output_path = Path::new(&output_dir).join(file_name);
base_img.save(output_path).map_err(|e| e.to_string())?;
// Handle format specific saving
// JPEG does not support Alpha channel. If we save Rgba8 to Jpeg, it might fail or look wrong.
let ext = output_path.extension().and_then(|s| s.to_str()).unwrap_or("").to_lowercase();
if ext == "jpg" || ext == "jpeg" {
// Convert to RGB8 (dropping alpha)
// Note: This simply drops alpha. If background was transparent, it becomes black.
// For photos (JPEGs) this is usually fine as they don't have alpha.
let rgb_img = image::DynamicImage::ImageRgba8(base_img).to_rgb8();
rgb_img.save(&output_path).map_err(|e| e.to_string())?;
} else {
// For PNG/WebP etc, keep RGBA
base_img.save(&output_path).map_err(|e| e.to_string())?;
}
Ok(())
} else {
Err(format!("Failed to open {}", task.path))