#[derive(Debug, Clone, PartialEq, Eq)]
pub enum DiffStatus {
Perfect,
Good,
Minor,
Moderate,
High,
Skip,
Error,
}
impl DiffStatus {
pub fn from_percent(percent: f64) -> Self {
if percent < 0.0 {
DiffStatus::Skip
} else if percent == 0.0 {
DiffStatus::Perfect
} else if percent < 1.0 {
DiffStatus::Good
} else if percent < 5.0 {
DiffStatus::Minor
} else if percent < 15.0 {
DiffStatus::Moderate
} else {
DiffStatus::High
}
}
pub fn from_report_str(s: &str) -> Self {
let s = s.trim();
if s.starts_with("PERFECT") {
DiffStatus::Perfect
} else if s.starts_with("GOOD") {
DiffStatus::Good
} else if s.starts_with("MINOR") {
DiffStatus::Minor
} else if s.starts_with("MODERATE") {
DiffStatus::Moderate
} else if s.starts_with("HIGH") {
DiffStatus::High
} else if s.starts_with("SKIP") {
DiffStatus::Skip
} else {
DiffStatus::Error
}
}
}
#[derive(Debug, Clone)]
pub struct DiffReportEntry {
pub label_name: String,
pub extension: String,
pub diff_percent: f64,
pub actual_dims: (u32, u32),
pub expected_dims: (u32, u32),
pub status: DiffStatus,
pub tolerance: Option<f64>,
}
#[derive(Debug, Clone)]
pub struct DiffReport {
pub entries: Vec<DiffReportEntry>,
pub total_labels: usize,
pub perfect_count: usize,
pub good_count: usize,
pub minor_count: usize,
pub moderate_count: usize,
pub high_count: usize,
pub skip_count: usize,
pub error_count: usize,
}
#[derive(Debug, Clone)]
pub struct ElementBBox {
pub x: i32,
pub y: i32,
pub width: i32,
pub height: i32,
pub element_index: usize,
pub element_type: ElementType,
pub zpl_command: String,
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum ElementType {
Text,
GraphicBox,
GraphicCircle,
DiagonalLine,
GraphicField,
GraphicSymbol,
Barcode128,
BarcodeEan13,
Barcode2of5,
Barcode39,
BarcodePdf417,
BarcodeAztec,
BarcodeDatamatrix,
BarcodeQr,
Maxicode,
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum DiffClassification {
ContentDiff,
PositionDiff,
Mixed,
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum OffsetDetectionMethod {
CrossCorrelation,
CentroidShift,
ShadowDetection,
}
#[derive(Debug, Clone)]
pub struct PositionOffsetInfo {
pub dx: i32,
pub dy: i32,
pub confidence: f64,
pub method: OffsetDetectionMethod,
}
#[derive(Debug, Clone)]
pub struct ElementDiffContribution {
pub bbox: ElementBBox,
pub diff_pixels_in_bbox: u64,
pub total_pixels_in_bbox: u64,
pub local_diff_percent: f64,
pub contribution_to_total: f64,
pub classification: Option<DiffClassification>,
pub position_offset: Option<PositionOffsetInfo>,
}
#[derive(Debug, Clone)]
pub struct ZplSnippet {
pub label_name: String,
pub element_index: usize,
pub zpl_content: String,
pub file_path: String,
pub original_diff_percent: f64,
}
#[derive(Debug, Clone)]
pub struct ZplCommandSpan {
pub start_offset: usize,
pub end_offset: usize,
pub commands: Vec<ZplCommand>,
pub element_index: usize,
}
#[derive(Debug, Clone)]
pub struct ZplCommand {
pub prefix: String,
pub params: String,
pub offset: usize,
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum FixCategory {
FontMetrics,
BarcodeEncoding,
PositionOffset,
GraphicRendering,
CommandParsing,
}
impl FixCategory {
pub fn from_element_type(et: &ElementType) -> Self {
match et {
ElementType::Text => FixCategory::FontMetrics,
ElementType::Barcode128
| ElementType::BarcodeEan13
| ElementType::Barcode2of5
| ElementType::Barcode39
| ElementType::BarcodePdf417
| ElementType::BarcodeAztec
| ElementType::BarcodeDatamatrix
| ElementType::BarcodeQr
| ElementType::Maxicode => FixCategory::BarcodeEncoding,
ElementType::GraphicBox
| ElementType::GraphicCircle
| ElementType::DiagonalLine
| ElementType::GraphicField
| ElementType::GraphicSymbol => FixCategory::GraphicRendering,
}
}
pub fn from_classification(et: &ElementType, classification: &DiffClassification) -> Self {
match classification {
DiffClassification::ContentDiff => Self::from_element_type(et),
DiffClassification::PositionDiff | DiffClassification::Mixed => {
FixCategory::PositionOffset
}
}
}
}