/**
 * Browser-side Tesseract OCR for Layer-1 card name strip recognition.
 * Uses tesseract.js workers (off main thread). Language data loads from CDN on first use.
 */

let workerPromise = null;

async function getWorker() {
  if (!workerPromise) {
    workerPromise = (async () => {
      const { createWorker } = await import('tesseract.js');
      const worker = await createWorker('eng', 1, {
        logger: () => {},
      });
      await worker.setParameters({
        tessedit_pageseg_mode: '6',
      });
      return worker;
    })();
  }
  return workerPromise;
}

function cropNameStrip(imageDataUrl) {
  return new Promise((resolve, reject) => {
    const img = new Image();
    img.onload = () => {
      const stripHeight = Math.max(1, Math.floor(img.height * 0.35));
      const canvas = document.createElement('canvas');
      canvas.width = img.width;
      canvas.height = stripHeight;
      const ctx = canvas.getContext('2d');
      ctx.drawImage(img, 0, 0, img.width, stripHeight, 0, 0, img.width, stripHeight);
      resolve(canvas.toDataURL('image/jpeg', 0.92));
    };
    img.onerror = () => reject(new Error('Failed to load image for OCR'));
    img.src = imageDataUrl;
  });
}

/**
 * OCR the top name strip of a card crop.
 * @param {string} imageDataUrl - full card crop data URL
 * @returns {Promise<{ text: string, confidence: number }>}
 */
export async function recognizeCardNameStrip(imageDataUrl) {
  if (typeof window === 'undefined') {
    return { text: '', confidence: 0 };
  }

  try {
    const stripUrl = await cropNameStrip(imageDataUrl);
    const worker = await getWorker();
    const { data } = await worker.recognize(stripUrl);
    return {
      text: (data.text || '').trim(),
      confidence: Math.round(data.confidence || 0),
    };
  } catch (error) {
    console.warn('[ocr-worker] recognizeCardNameStrip failed:', error);
    return { text: '', confidence: 0 };
  }
}

export async function terminateOcrWorker() {
  if (!workerPromise) return;
  try {
    const worker = await workerPromise;
    await worker.terminate();
  } catch {
    // ignore teardown errors
  }
  workerPromise = null;
}
