import { CloudinaryService } from 'config/multer/cloudinary.service';
import { PDFDocument, PDFImage, PDFPage, rgb, StandardFonts } from 'pdf-lib';
import fontkit from '@pdf-lib/fontkit';
import 'regenerator-runtime/runtime';
import fs from 'fs';

import NepaliDate from 'nepali-datetime';

const nepaliDate = new NepaliDate();
const NepaliMonth = (nepaliDate.getMonth() + 1).toString();
const NepaliDay = nepaliDate.getDate().toString();

export async function generateFilledFinancialFraduForm(formData: FinancialFraudFormData): Promise<Buffer> {
  try {
    // Read the existing PDF template
    const templatePath = './public/templates/financial-fraud-p-2-ccb-2082.pdf';
    const existingPdfBytes = fs.readFileSync(templatePath);

    // Load the PDF document
    const pdfDoc = await PDFDocument.load(existingPdfBytes);

    // Register fontkit with the PDF document
    pdfDoc.registerFontkit(fontkit);

    // Get the pages
    const pages = pdfDoc.getPages();
    const firstPage = pages[0];

    // Create a helper function for Devanagari text support
    // Note: Preserving Nepali characters
    const formatText = (text: string | number | undefined): string => {
      if (text === undefined || text === null) return '';
      return text.toString();
    };

    // For Nepali text support:
    const nepaliFontBytes = fs.readFileSync('./public/fonts/nepali.ttf');
    const font = await pdfDoc.embedFont(nepaliFontBytes);

    // Standard font for English text (optional)
    const standardFont = await pdfDoc.embedFont(StandardFonts.Helvetica);

    const drawText = (page: PDFPage, text: string, x: number, y: number, fontSize: number = 10, useNepaliFonts: boolean = true) => {
      page.drawText(formatText(text), {
        x,
        y: page.getHeight() - y, // PDF coordinates start from bottom left
        size: fontSize,
        font: useNepaliFonts ? font : standardFont,
        color: rgb(0, 0, 0),
      });
    };

    // Helper function to draw checkbox - FIXED with WinAnsi compatible approach
    const drawCheckbox = (page: PDFPage, isChecked: boolean | undefined, x: number, y: number) => {
      if (isChecked) {
        // Convert y coordinate to PDF coordinates (from top-left to bottom-left origin)
        const pdfY = page.getHeight() - y;

        // Draw a small checkmark using lines
        page.drawLine({
          start: { x: x - 2, y: pdfY - 2 },
          end: { x: x, y: pdfY - 4 },
          thickness: 2,
          color: rgb(0, 0, 0),
        });

        page.drawLine({
          start: { x: x, y: pdfY - 4 },
          end: { x: x + 4, y: pdfY + 2 },
          thickness: 1,
          color: rgb(0, 0, 0),
        });
      }
    };
    //complaint month and date
    drawText(firstPage, NepaliMonth, 485, 46);
    drawText(firstPage, NepaliDay, 518, 46);

    // Original ID/URL field (line #1)
    drawText(firstPage, formData.originalID_URL, 219, 240);

    // Fraudster ID/URL field (line #2)
    drawText(firstPage, formData.fraudsterID_URL, 240, 260);

    // Social media platform (line #3) - Adjusted position
    const socialMediaPlatform = formData.socialMediaPlatform || '';

    const platformsWithCheckbox = ['FB/Messenger', 'Insta', 'WhatsApp', 'Tiktok'];

    if (platformsWithCheckbox.includes(socialMediaPlatform)) {
      drawCheckbox(firstPage, true, 159, 276);
    } else {
      drawText(firstPage, socialMediaPlatform, 435, 278);
    }

    // Incident description (line #4)
    const description = formData.incidentDescription || '';

    // Improved text wrapping for description
    const wrappedDescription = wrapTextWithNepali(description, 100); // Character count per line
    let descY = 312; // Starting Y position
    const descX = 50; // Starting X position

    // Draw each line of the description with proper spacing
    const lineSpacing = 17; // Adjust for proper line spacing
    wrappedDescription.forEach((line, index) => {
      if (index < 10) {
        // Limit to prevent overflow
        drawText(firstPage, line, descX, descY + index * lineSpacing, 10);
      }
    });

    // Checkboxes for attached documents (line #5) - All checkboxes

    // Citizenship copy checkbox
    drawCheckbox(firstPage, formData.hasCitizenshipCopy, 183, 515);

    // Passport checkbox
    drawCheckbox(firstPage, formData.hasPassport, 295, 515);

    // National ID card checkbox
    drawCheckbox(firstPage, formData.hasNationalIDCard, 397, 515);

    // Employee or student ID checkbox
    drawCheckbox(firstPage, formData.hasEmployeeOrStudentID, 184, 540);

    // Other document field
    if (formData.otherDocument) {
      drawText(firstPage, formData.otherDocument, 434, 542);
    }

    // Complainant details (line #6)

    // Name field
    drawText(firstPage, formData.complainantName, 103, 620);

    // Date of birth field
    drawText(firstPage, formData.complainantDateOfBirth, 121, 643);

    // Address field
    drawText(firstPage, formData.complainantAddress, 102, 668);

    // ID number field
    drawText(firstPage, formData.complainantIdNumber, 425, 618);

    // Contact number field
    drawText(firstPage, formData.complainantContactNumber, 419, 647);

    // Guardian contact number field
    drawText(firstPage, formData.complainantGuardianContactNumber, 435, 671);

    // Save the PDF
    const pdfBytes = await pdfDoc.save();
    return Buffer.from(pdfBytes);
  } catch (error) {
    console.error('Error generating filled form:', error);
    throw error;
  }
}

function wrapTextWithNepali(text: string, maxChars: number): string[] {
  if (!text) return [''];
  const words = text.split(' ');
  const lines: string[] = [];
  let currentLine = '';

  words.forEach(word => {
    if ((currentLine + word).length <= maxChars) {
      currentLine += word + ' ';
    } else {
      lines.push(currentLine.trim());
      currentLine = word + ' ';
    }
  });
  if (currentLine.trim()) {
    lines.push(currentLine.trim());
  }
  return lines;
}
