// services/pdfExportService.ts
import type { ProfitLossReport } from '@/types/services/analytic'

export class PDFExportProfitLossService {
  /**
   * Export Profit Loss Report to PDF (Simple approach)
   */
  static async exportProfitLossToPDF(profitData: ProfitLossReport, filename?: string) {
    try {
      // Dynamic import untuk jsPDF
      const jsPDFModule = await import('jspdf')
      const jsPDF = jsPDFModule.default

      // Create new PDF document - PORTRAIT A4
      const pdf = new jsPDF('p', 'mm', 'a4') // portrait

      // Add content
      this.addBasicContent(pdf, profitData)

      // Generate filename
      const exportFilename = filename || this.generateFilename('Laba_Rugi', 'pdf')

      // Save PDF
      pdf.save(exportFilename)

      return { success: true, filename: exportFilename }
    } catch (error) {
      console.error('Error exporting to PDF:', error)
      return { success: false, error: `PDF export failed: ${(error as Error).message}` }
    }
  }

  /**
   * Add basic content to PDF with proper page management
   */
  private static addBasicContent(pdf: any, profitData: ProfitLossReport) {
    let yPos = 20 // Reduced from 30
    const pageWidth = pdf.internal.pageSize.getWidth()
    const pageHeight = pdf.internal.pageSize.getHeight()
    const marginBottom = 15 // Reduced from 20

    // Title - Center aligned
    pdf.setFontSize(18) // Reduced from 20
    pdf.setFont('helvetica', 'bold')
    pdf.text('Laporan Laba Rugi', pageWidth / 2, yPos, { align: 'center' })
    yPos += 10 // Reduced from 15

    // Period - Center aligned
    pdf.setFontSize(11) // Reduced from 12
    pdf.setFont('helvetica', 'normal')
    const periodText = `${profitData.date_from.split('T')[0]} - ${profitData.date_to.split('T')[0]}`
    pdf.text(periodText, pageWidth / 2, yPos, { align: 'center' })
    yPos += 12 // Reduced from 20

    // Purple line separator
    pdf.setDrawColor(102, 45, 145) // Purple color
    pdf.setLineWidth(1.5) // Reduced from 2
    pdf.line(20, yPos, pageWidth - 20, yPos)
    yPos += 15 // Reduced from 25

    // Ringkasan section
    pdf.setFontSize(14) // Reduced from 16
    pdf.setFont('helvetica', 'bold')
    pdf.setTextColor(102, 45, 145) // Purple color
    pdf.text('Ringkasan', 20, yPos)
    yPos += 12 // Reduced from 20

    // Reset text color to black
    pdf.setTextColor(0, 0, 0)
    pdf.setFont('helvetica', 'normal')
    pdf.setFontSize(11) // Reduced from 12

    // Summary items with consistent spacing
    const summaryItems = [
      { label: 'Total Penjualan', value: this.formatCurrency(profitData.summary.total_revenue) },
      { label: 'Total Biaya', value: this.formatCurrency(profitData.summary.total_cost) },
      { label: 'Total Diskon', value: this.formatCurrency(profitData.summary.total_discount) },
      { label: 'Total Pajak', value: this.formatCurrency(profitData.summary.total_tax) },
      { label: 'Laba Kotor', value: this.formatCurrency(profitData.summary.gross_profit) },
      { label: 'Laba Bersih', value: this.formatCurrency(profitData.summary.net_profit) }
    ]

    summaryItems.forEach((item, index) => {
      // Add some spacing between items
      if (index > 0) yPos += 8 // Reduced from 12

      // Check if we need new page for summary items
      if (yPos > pageHeight - marginBottom - 15) {
        pdf.addPage()
        yPos = 20 // Reduced from 30
      }

      // Label on left
      pdf.text(item.label, 20, yPos)

      // Value on right
      pdf.text(item.value, pageWidth - 20, yPos, { align: 'right' })

      // Light gray line separator
      pdf.setDrawColor(230, 230, 230)
      pdf.setLineWidth(0.3)
      pdf.line(20, yPos + 3, pageWidth - 20, yPos + 3)
    })

    yPos += 20 // Reduced from 30

    // Check if we need new page before daily breakdown
    if (yPos > pageHeight - marginBottom - 40) {
      pdf.addPage()
      yPos = 20 // Reduced from 30
    }

    // Daily breakdown section
    pdf.setFontSize(14) // Reduced from 16
    pdf.setFont('helvetica', 'bold')
    pdf.setTextColor(102, 45, 145) // Purple color
    pdf.text('Rincian Harian', 20, yPos)
    yPos += 12 // Reduced from 20

    // Reset text color
    pdf.setTextColor(0, 0, 0)

    // Create simple daily breakdown with page management
    profitData.data.forEach((daily, index) => {
      // Estimate space needed for this daily section (approx 100mm)
      const estimatedSpace = 100

      // Check if we need new page before adding daily section
      if (yPos + estimatedSpace > pageHeight - marginBottom) {
        pdf.addPage()
        yPos = 20 // Reduced from 30
      }

      yPos = this.addCleanDailySection(pdf, daily, yPos, pageWidth, pageHeight, marginBottom)
      yPos += 10 // Reduced from 15 - Space between daily sections
    })
  }

  /**
   * Add clean daily section with page break management
   */
  private static addCleanDailySection(
    pdf: any,
    dailyData: any,
    startY: number,
    pageWidth: number,
    pageHeight: number,
    marginBottom: number
  ) {
    const date = new Date(dailyData.date).toLocaleDateString('id-ID', {
      day: '2-digit',
      month: 'long',
      year: 'numeric'
    })

    let yPos = startY

    // Check if we have enough space for the header
    if (yPos > pageHeight - marginBottom - 20) {
      pdf.addPage()
      yPos = 20 // Reduced from 30
    }

    // Date header
    pdf.setFontSize(12) // Reduced from 14
    pdf.setFont('helvetica', 'bold')
    pdf.text(date, 20, yPos)
    yPos += 10 // Reduced from 15

    // Daily data items
    pdf.setFontSize(10) // Reduced from 11
    pdf.setFont('helvetica', 'normal')

    const dailyItems = [
      { label: 'Penjualan', value: this.formatCurrency(dailyData.revenue) },
      { label: 'HPP (Biaya Pokok)', value: this.formatCurrency(dailyData.cost) },
      { label: 'Laba Kotor', value: this.formatCurrency(dailyData.gross_profit) },
      { label: 'Pajak', value: this.formatCurrency(dailyData.tax) },
      { label: 'Diskon', value: this.formatCurrency(dailyData.discount) },
      { label: 'Jumlah Order', value: dailyData.orders.toString() + ' transaksi' },
      { label: 'Laba Bersih', value: this.formatCurrency(dailyData.net_profit), isTotal: true }
    ]

    dailyItems.forEach((item, index) => {
      if (index > 0) yPos += 7 // Reduced from 10

      // Check if we need new page for each item
      if (yPos > pageHeight - marginBottom - 15) {
        pdf.addPage()
        yPos = 20 // Reduced from 30
      }

      // Special styling for total (Laba Bersih)
      if (item.isTotal) {
        pdf.setFont('helvetica', 'bold')

        // Light background for total row - adjusted to center with text
        pdf.setFillColor(248, 248, 248)
        pdf.rect(20, yPos - 4, pageWidth - 40, 9, 'F') // Slightly bigger and better positioned
      } else {
        pdf.setFont('helvetica', 'normal')
      }

      // Label on left - consistent with other rows
      pdf.text(item.label, 25, yPos)

      // Value on right - consistent with other rows
      pdf.text(item.value, pageWidth - 25, yPos, { align: 'right' })

      // Subtle line separator (except for last item)
      if (index < dailyItems.length - 1) {
        pdf.setDrawColor(245, 245, 245)
        pdf.setLineWidth(0.2)
        pdf.line(25, yPos + 1.5, pageWidth - 25, yPos + 1.5) // Reduced from yPos + 2
      }
    })

    return yPos + 6 // Reduced from 8
  }

  /**
   * Format currency for display
   */
  private static formatCurrency(amount: number): string {
    return `Rp ${amount.toLocaleString('id-ID')}`
  }

  /**
   * Generate filename with timestamp
   */
  private static generateFilename(prefix: string, extension: string): string {
    const now = new Date()
    const year = now.getFullYear()
    const month = (now.getMonth() + 1).toString().padStart(2, '0')
    const day = now.getDate().toString().padStart(2, '0')
    const hour = now.getHours().toString().padStart(2, '0')
    const minute = now.getMinutes().toString().padStart(2, '0')

    return `${prefix}_${year}_${month}_${day}_${hour}${minute}.${extension}`
  }

  /**
   * Alternative: More precise page break management
   */
  static async exportWithBetterPageBreaks(profitData: ProfitLossReport, filename?: string) {
    try {
      const jsPDFModule = await import('jspdf')
      const jsPDF = jsPDFModule.default
      const pdf = new jsPDF('p', 'mm', 'a4')

      // Use more precise measurements
      const pageHeight = pdf.internal.pageSize.getHeight() // ~297mm for A4
      const safeHeight = pageHeight - 30 // Keep 30mm margin from bottom

      let currentY = 30

      // Helper function to check and add new page
      const checkPageBreak = (neededSpace: number) => {
        if (currentY + neededSpace > safeHeight) {
          pdf.addPage()
          currentY = 30
          return true
        }
        return false
      }

      // Add title and header
      currentY = this.addTitleSection(pdf, profitData, currentY)

      // Add summary with page break check
      checkPageBreak(80) // Estimate 80mm needed for summary
      currentY = this.addSummarySection(pdf, profitData, currentY, checkPageBreak)

      // Add daily breakdown
      checkPageBreak(40) // Space for section header
      currentY = this.addDailyBreakdownSection(pdf, profitData, currentY, checkPageBreak)

      const exportFilename = filename || this.generateFilename('Laba_Rugi', 'pdf')
      pdf.save(exportFilename)

      return { success: true, filename: exportFilename }
    } catch (error) {
      console.error('Error exporting to PDF:', error)
      return { success: false, error: `PDF export failed: ${(error as Error).message}` }
    }
  }

  /**
   * Add title section
   */
  private static addTitleSection(pdf: any, profitData: ProfitLossReport, startY: number): number {
    let yPos = startY
    const pageWidth = pdf.internal.pageSize.getWidth()

    // Title
    pdf.setFontSize(20)
    pdf.setFont('helvetica', 'bold')
    pdf.text('Laporan Laba Rugi', pageWidth / 2, yPos, { align: 'center' })
    yPos += 15

    // Period
    pdf.setFontSize(12)
    pdf.setFont('helvetica', 'normal')
    const periodText = `${profitData.date_from.split('T')[0]} - ${profitData.date_to.split('T')[0]}`
    pdf.text(periodText, pageWidth / 2, yPos, { align: 'center' })
    yPos += 20

    // Separator line
    pdf.setDrawColor(102, 45, 145)
    pdf.setLineWidth(2)
    pdf.line(20, yPos, pageWidth - 20, yPos)
    yPos += 25

    return yPos
  }

  /**
   * Add summary section with page break callback
   */
  private static addSummarySection(
    pdf: any,
    profitData: ProfitLossReport,
    startY: number,
    checkPageBreak: (space: number) => boolean
  ): number {
    let yPos = startY
    const pageWidth = pdf.internal.pageSize.getWidth()

    // Section title
    pdf.setFontSize(16)
    pdf.setFont('helvetica', 'bold')
    pdf.setTextColor(102, 45, 145)
    pdf.text('Ringkasan', 20, yPos)
    yPos += 20

    // Reset formatting
    pdf.setTextColor(0, 0, 0)
    pdf.setFont('helvetica', 'normal')
    pdf.setFontSize(12)

    const summaryItems = [
      { label: 'Total Penjualan', value: this.formatCurrency(profitData.summary.total_revenue) },
      { label: 'Total Biaya', value: this.formatCurrency(profitData.summary.total_cost) },
      { label: 'Total Diskon', value: this.formatCurrency(profitData.summary.total_discount) },
      { label: 'Total Pajak', value: this.formatCurrency(profitData.summary.total_tax) },
      { label: 'Laba Kotor', value: this.formatCurrency(profitData.summary.gross_profit) },
      { label: 'Laba Bersih', value: this.formatCurrency(profitData.summary.net_profit) }
    ]

    summaryItems.forEach((item, index) => {
      if (index > 0) yPos += 12

      // Check page break for each item
      if (checkPageBreak(15)) {
        yPos = 30
      }

      pdf.text(item.label, 20, yPos)
      pdf.text(item.value, pageWidth - 20, yPos, { align: 'right' })

      // Separator line
      pdf.setDrawColor(230, 230, 230)
      pdf.setLineWidth(0.3)
      pdf.line(20, yPos + 3, pageWidth - 20, yPos + 3)
    })

    return yPos + 30
  }

  /**
   * Add daily breakdown section with page break management
   */
  private static addDailyBreakdownSection(
    pdf: any,
    profitData: ProfitLossReport,
    startY: number,
    checkPageBreak: (space: number) => boolean
  ): number {
    let yPos = startY

    // Section title
    pdf.setFontSize(16)
    pdf.setFont('helvetica', 'bold')
    pdf.setTextColor(102, 45, 145)
    pdf.text('Rincian Harian', 20, yPos)
    yPos += 20

    pdf.setTextColor(0, 0, 0)

    profitData.data.forEach((daily, index) => {
      // Check if we need space for this daily section (estimate ~90mm)
      if (checkPageBreak(90)) {
        yPos = 30
      }

      yPos = this.addSingleDayData(pdf, daily, yPos)
      yPos += 15
    })

    return yPos
  }

  /**
   * Add single day data
   */
  private static addSingleDayData(pdf: any, dailyData: any, startY: number): number {
    const pageWidth = pdf.internal.pageSize.getWidth()
    let yPos = startY

    const date = new Date(dailyData.date).toLocaleDateString('id-ID', {
      day: '2-digit',
      month: 'long',
      year: 'numeric'
    })

    // Date header
    pdf.setFontSize(14)
    pdf.setFont('helvetica', 'bold')
    pdf.text(date, 20, yPos)
    yPos += 15

    // Daily items
    pdf.setFontSize(11)
    pdf.setFont('helvetica', 'normal')

    const items = [
      { label: 'Penjualan', value: this.formatCurrency(dailyData.revenue) },
      { label: 'HPP (Biaya Pokok)', value: this.formatCurrency(dailyData.cost) },
      { label: 'Laba Kotor', value: this.formatCurrency(dailyData.gross_profit) },
      { label: 'Pajak', value: this.formatCurrency(dailyData.tax) },
      { label: 'Diskon', value: this.formatCurrency(dailyData.discount) },
      { label: 'Jumlah Order', value: dailyData.orders.toString() + ' transaksi' },
      { label: 'Laba Bersih', value: this.formatCurrency(dailyData.net_profit), isTotal: true }
    ]

    items.forEach((item, index) => {
      if (index > 0) yPos += 10

      if (item.isTotal) {
        pdf.setFont('helvetica', 'bold')
        pdf.setFillColor(248, 248, 248)
        pdf.rect(20, yPos - 4, pageWidth - 40, 10, 'F')
      } else {
        pdf.setFont('helvetica', 'normal')
      }

      pdf.text(item.label, 25, yPos)
      pdf.text(item.value, pageWidth - 25, yPos, { align: 'right' })

      if (index < items.length - 1) {
        pdf.setDrawColor(245, 245, 245)
        pdf.setLineWidth(0.2)
        pdf.line(25, yPos + 2, pageWidth - 25, yPos + 2)
      }
    })

    return yPos + 8
  }

  /**
   * Alternative HTML to PDF method (if needed)
   */
  static async exportToHTMLPDF(profitData: ProfitLossReport, filename?: string) {
    try {
      const htmlContent = this.generateSimpleHTML(profitData)

      // Create a temporary element and trigger print
      const printWindow = window.open('', '_blank')
      if (printWindow) {
        printWindow.document.write(htmlContent)
        printWindow.document.close()
        printWindow.focus()
        printWindow.print()
        printWindow.close()
      }

      return { success: true, filename: filename || 'Laba_Rugi.pdf' }
    } catch (error) {
      return { success: false, error: `HTML PDF export failed: ${(error as Error).message}` }
    }
  }

  /**
   * Generate simple HTML for printing
   */
  private static generateSimpleHTML(profitData: ProfitLossReport): string {
    const dateColumns = profitData.data.map(daily => {
      const date = new Date(daily.date)
      return date.toLocaleDateString('id-ID', { day: '2-digit', month: 'short' })
    })

    return `
      <!DOCTYPE html>
      <html>
        <head>
          <title>Laporan Laba Rugi</title>
          <style>
            body { font-family: Arial, sans-serif; margin: 20px; }
            h1 { color: #1f4e79; text-align: center; }
            h2 { color: #333; border-bottom: 2px solid #ccc; }
            .summary { margin-bottom: 30px; }
            .summary-item { margin: 5px 0; padding: 5px; background: #f9f9f9; }
            table { width: 100%; border-collapse: collapse; margin-top: 20px; }
            th, td { border: 1px solid #ccc; padding: 8px; text-align: left; }
            th { background-color: #d35400; color: white; text-align: center; }
            .number { text-align: right; }
            .center { text-align: center; }
            @media print { 
              body { margin: 10px; } 
              .page-break { page-break-before: always; }
            }
          </style>
        </head>
        <body>
          <h1>LAPORAN LABA RUGI</h1>
          <p style="text-align: center;">
            Periode: ${profitData.date_from.split('T')[0]} - ${profitData.date_to.split('T')[0]}
          </p>
          
          <h2>RINGKASAN PERIODE</h2>
          <div class="summary">
            <div class="summary-item">Total Revenue: <strong>${this.formatCurrency(profitData.summary.total_revenue)}</strong></div>
            <div class="summary-item">Total Cost: <strong>${this.formatCurrency(profitData.summary.total_cost)}</strong></div>
            <div class="summary-item">Gross Profit: <strong>${this.formatCurrency(profitData.summary.gross_profit)}</strong></div>
            <div class="summary-item">Net Profit: <strong>${this.formatCurrency(profitData.summary.net_profit)}</strong></div>
            <div class="summary-item">Total Orders: <strong>${profitData.summary.total_orders}</strong></div>
          </div>
          
          <div class="page-break"></div>
          <h2>RINCIAN HARIAN</h2>
          <table>
            <thead>
              <tr>
                <th>NO</th>
                <th>KETERANGAN</th>
                <th></th>
                ${dateColumns.map(date => `<th>${date}</th>`).join('')}
              </tr>
            </thead>
            <tbody>
              <tr>
                <td class="center">1</td>
                <td><strong>TOTAL PENJ</strong></td>
                <td class="center">:</td>
                ${profitData.data.map(daily => `<td class="number">${this.formatCurrency(daily.revenue)}</td>`).join('')}
              </tr>
              <tr>
                <td class="center">2</td>
                <td><strong>HPP</strong></td>
                <td class="center">:</td>
                ${profitData.data.map(daily => `<td class="number">${this.formatCurrency(daily.cost)}</td>`).join('')}
              </tr>
              <tr>
                <td class="center">3</td>
                <td><strong>Laba Kotor</strong></td>
                <td class="center">:</td>
                ${profitData.data.map(daily => `<td class="number">${this.formatCurrency(daily.gross_profit)}</td>`).join('')}
              </tr>
              <tr>
                <td class="center">4</td>
                <td><strong>Biaya lain</strong></td>
                <td class="center">:</td>
                ${profitData.data.map(daily => `<td class="number">${this.formatCurrency(daily.tax + daily.discount)}</td>`).join('')}
              </tr>
              <tr style="background-color: #154360; color: white; font-weight: bold;">
                <td class="center">5</td>
                <td>Laba/Rugi</td>
                <td class="center">:</td>
                ${profitData.data.map(daily => `<td class="number">${this.formatCurrency(daily.net_profit)}</td>`).join('')}
              </tr>
            </tbody>
          </table>
        </body>
      </html>
    `
  }
}
