/**
 * extract_stamp.js
 * "Thợ săn dấu đỏ" - Quét màu đỏ và cắt đúng tọa độ con dấu đỏ từ file PDF Scan.
 */

const sharp = require("sharp");
const { fromPath } = require("pdf2pic");
const fs = require("fs");
const path = require("path");

// ─── CẤU HÌNH CƠ BẢN ──────────────────────────────────────────────────────────
const PDF_DIR = path.join(__dirname, "../test"); 
const OUTPUT_DIR = path.join(__dirname, "output_stamps");
const PADDING = 20; // Thêm 20px lề xung quanh con dấu cho đẹp
// ──────────────────────────────────────────────────────────────────────────────

// Cấu hình pdf2pic chuyển PDF -> PNG
const options = {
    density: 200,             // DPI cao để thấy rõ màu
    saveFilename: "temp_page",
    savePath: OUTPUT_DIR,
    format: "png",
    width: 1653,              // Size phổ thông A4 @ 200 DPI
    height: 2339
};

const convert = fromPath(PDF_DIR, options); // Initialize cơ bản

async function extractRedStamp(imagePath, pageNum, pdfName) {
    console.log(`[2] Đang quét dấu đỏ trên trang ${pageNum}...`);
    
    const image = sharp(imagePath);
    const meta = await image.metadata();
    
    // Đổ toàn bộ pixel ảnh ra Buffer thô để lùng sục
    const { data, info } = await image.raw().toBuffer({ resolveWithObject: true });
    
    const channels = info.channels;
    const width = info.width;
    const height = info.height;
    
    // Khởi tạo khung vuông rỗng để vẽ tọa độ bao quanh con dấu
    let minX = width, minY = height, maxX = 0, maxY = 0;
    let hasRed = false;
    let redPixelsCount = 0;
    
    // Xoẹt qua hàng triệu pixels với vận tốc siêu âm
    for (let i = 0; i < data.length; i += channels) {
        const r = data[i];
        const g = data[i + 1];
        const b = data[i + 2];
        
        // TIÊU CHUẨN MÀU ĐỎ CỦA MỰC DẤU CAO SU VIỆT NAM:
        // 1. Chỉ số Red > 120 (Không lấy màu tối sẫm, xám, đen)
        // 2. Độ chênh lệch giữa Red và (Green, Blue) phải đủ mạnh
        if (r > 120 && (r - g > 50) && (r - b > 50)) {
            hasRed = true;
            redPixelsCount++;
            
            // Đổi index của pixel thành hệ trục tọa độ x,y
            const pixelIndex = i / channels;
            const x = pixelIndex % width;
            const y = Math.floor(pixelIndex / width);
            
            // Giăng bẫy bắt tọa độ
            if (x < minX) minX = x;
            if (x > maxX) maxX = x;
            if (y < minY) minY = y;
            if (y > maxY) maxY = y;
        }
    }
    
    // Lọc nhiễu: Phải có ít nhất 100 điểm đỏ thì tao mới tin là con dấu (bỏ qua vết bẩn/chữ đỏ lỗi)
    if (hasRed && redPixelsCount > 100) { 
        console.log(`  => ĐÃ TÌM THẤY DẤU ĐỎ! (Số lượng pixel đỏ: ${redPixelsCount})`);
        console.log(`  => Tại Tọa độ Box[X:${minX}, Y:${minY}, Rộng:${maxX-minX}, Cao:${maxY-minY}]`);
        
        // Căn thêm cái khung (lề khoảng 20px) cho đẹp, tránh trường hợp rách mép dấu
        let cropLeft = Math.max(0, minX - PADDING);
        let cropTop = Math.max(0, minY - PADDING);
        let cropWidth = Math.min(width - cropLeft, (maxX - minX) + PADDING * 2);
        let cropHeight = Math.min(height - cropTop, (maxY - minY) + PADDING * 2);
        
        const outputFilename = `${pdfName}_page${pageNum}_STAMP.png`;
        const outputPath = path.join(OUTPUT_DIR, outputFilename);
        
        // Cầm kéo sharp cắt phát quyết định cuối cùng
        await sharp(imagePath)
            .extract({ left: cropLeft, top: cropTop, width: cropWidth, height: cropHeight })
            .toFile(outputPath);
            
        console.log(`  => [✓] LƯU THÀNH CÔNG: ${outputFilename}`);
        
    } else {
        console.log(`  => [X] Không tìm thấy dấu đỏ trên trang này.`);
    }
    
    // Dọn rác: Xóa file ảnh A4 bự chảng kia đi cho nhẹ máy
    try { fs.unlinkSync(imagePath); } catch(e){}
}

// ─── RUN SERVER ──────────────────────────────────────────────────────────────
async function start() {
    if (!fs.existsSync(OUTPUT_DIR)) {
        fs.mkdirSync(OUTPUT_DIR, { recursive: true });
    }
    
    if (!fs.existsSync(PDF_DIR)) {
        console.log(`[!] Thư mục test không tồn tại: ${PDF_DIR}`);
        return;
    }

    const files = fs.readdirSync(PDF_DIR).filter(f => f.toLowerCase().endsWith('.pdf'));
    if(files.length === 0) {
        console.log(`[!] Không có file PDF nào trong ${PDF_DIR}`);
        return;
    }
    
    console.log(`[*] Đã tìm thấy ${files.length} file PDF. Bắt đầu lùng sục dấu đỏ...`);
    
    for (const file of files) {
        const fullPath = path.join(PDF_DIR, file);
        const pdfName = path.basename(file, '.pdf');
        
        console.log(`\n--- Đang bắt tay xử lý: ${file} ---`);
        
        try {
            // Khởi tạo thư viện convert chuyên biệt cho từng file PDF
            const pdfConverter = fromPath(fullPath, options);
            
            // Loop mò từ trang 1 đến 15 (Max) - Thường hợp đồng không úp sọt con dấu ở trang thứ 20 đâu
            for (let i = 1; i <= 15; i++) {
                try {
                    const result = await pdfConverter(i, { responseType: "image" });
                    if (!result || !result.path) break;
                    
                    // Tìm thấy trang, tung Thợ Săn vào quét màu!
                    await extractRedStamp(result.path, i, pdfName);
                } catch(e) {
                    // pdf2pic sẽ quăng lỗi khi hết số trang (Vd file có 5 trang mà mò tới trang 6) => Break loop
                    break;
                }
            }
        } catch (error) {
            console.error(`[LỖI] Xử lý file ${file} thất bại:`, error.message);
        }
    }
    
    console.log("\n[★] HOÀN THÀNH CHIẾN DỊCH QUÉT DẤU [★]");
}

start().catch(console.error);
