/**
 * PreviewScaler - Adaptive Image Downsampling Component
 * Handles device performance detection and optimal preview resolution
 * Requirements: 2.1, 2.2, 4.1, 4.2, 4.3
 */

class PreviewScaler {
  constructor() {
    this.deviceLevel = this.detectDevicePerformance();
    this.fullResolutionImage = null;
    this.fullResolutionImageData = null;
    this.previewDimensions = null;
    
    console.log(`[PreviewScaler] Device performance level: ${this.deviceLevel}`);
  }

  /**
   * Detect device performance level based on CPU cores and memory
   * Requirement 4.1: Device performance detection
   */
  detectDevicePerformance() {
    // Get hardware information
    const cores = navigator.hardwareConcurrency || 2;
    const memory = navigator.deviceMemory || 4; // GB
    
    // Classify device level
    if (cores >= 4 && memory >= 8) {
      return 'high';
    } else if (cores >= 2 && memory >= 4) {
      return 'medium';
    } else {
      return 'low';
    }
  }

  /**
   * Get device performance level
   */
  getDeviceLevel() {
    return this.deviceLevel;
  }

  /**
   * Calculate optimal preview dimensions based on device level
   * Requirement 4.2: Adaptive preview resolution
   * Requirement 2.1: Downsample images larger than threshold
   */
  getPreviewDimensions(originalWidth, originalHeight) {
    // Maximum dimensions based on device level
    const maxDimensions = {
      high: 3000,
      medium: 2000,
      low: 1000
    };

    const maxDimension = maxDimensions[this.deviceLevel];

    // Check if downsampling is needed
    const currentMax = Math.max(originalWidth, originalHeight);
    
    if (currentMax <= maxDimension) {
      // No downsampling needed
      return {
        width: originalWidth,
        height: originalHeight,
        scale: 1,
        needsDownsampling: false
      };
    }

    // Calculate scale factor to fit within max dimension
    const scale = maxDimension / currentMax;
    
    return {
      width: Math.round(originalWidth * scale),
      height: Math.round(originalHeight * scale),
      scale: scale,
      needsDownsampling: true
    };
  }

  /**
   * Create preview image with high-quality downsampling
   * Requirement 2.1: Downsample preview while maintaining aspect ratio
   */
  createPreviewImage(sourceImage) {
    // Calculate optimal dimensions
    this.previewDimensions = this.getPreviewDimensions(
      sourceImage.width,
      sourceImage.height
    );

    // Store full-resolution reference
    this.fullResolutionImage = sourceImage;

    // If no downsampling needed, return original
    if (!this.previewDimensions.needsDownsampling) {
      return {
        canvas: this.drawImageToCanvas(sourceImage, sourceImage.width, sourceImage.height),
        dimensions: this.previewDimensions,
        isDownsampled: false
      };
    }

    // Create downsampled preview with high-quality smoothing
    const previewCanvas = this.downsampleImage(
      sourceImage,
      this.previewDimensions.width,
      this.previewDimensions.height
    );

    return {
      canvas: previewCanvas,
      dimensions: this.previewDimensions,
      isDownsampled: true
    };
  }

  /**
   * Downsample image using canvas with high-quality smoothing
   * Uses multi-step downsampling for better quality
   */
  downsampleImage(sourceImage, targetWidth, targetHeight) {
    const canvas = document.createElement('canvas');
    const ctx = canvas.getContext('2d');

    // Enable high-quality image smoothing
    ctx.imageSmoothingEnabled = true;
    ctx.imageSmoothingQuality = 'high';

    // For large scale reductions, use multi-step downsampling (Lanczos-like)
    const scale = targetWidth / sourceImage.width;
    
    if (scale < 0.5) {
      // Multi-step downsampling for better quality
      return this.multiStepDownsample(sourceImage, targetWidth, targetHeight);
    } else {
      // Single-step downsampling
      canvas.width = targetWidth;
      canvas.height = targetHeight;
      ctx.drawImage(sourceImage, 0, 0, targetWidth, targetHeight);
      return canvas;
    }
  }

  /**
   * Multi-step downsampling for better quality when scaling down significantly
   * Reduces aliasing artifacts
   */
  multiStepDownsample(sourceImage, targetWidth, targetHeight) {
    let currentCanvas = this.drawImageToCanvas(
      sourceImage,
      sourceImage.width,
      sourceImage.height
    );

    let currentWidth = sourceImage.width;
    let currentHeight = sourceImage.height;

    // Downsample in steps of 50% until we reach target size
    while (currentWidth > targetWidth * 2 || currentHeight > targetHeight * 2) {
      const stepWidth = Math.round(currentWidth * 0.5);
      const stepHeight = Math.round(currentHeight * 0.5);

      const stepCanvas = document.createElement('canvas');
      const stepCtx = stepCanvas.getContext('2d');
      
      stepCanvas.width = stepWidth;
      stepCanvas.height = stepHeight;
      
      stepCtx.imageSmoothingEnabled = true;
      stepCtx.imageSmoothingQuality = 'high';
      stepCtx.drawImage(currentCanvas, 0, 0, stepWidth, stepHeight);

      currentCanvas = stepCanvas;
      currentWidth = stepWidth;
      currentHeight = stepHeight;
    }

    // Final step to exact target size
    const finalCanvas = document.createElement('canvas');
    const finalCtx = finalCanvas.getContext('2d');
    
    finalCanvas.width = targetWidth;
    finalCanvas.height = targetHeight;
    
    finalCtx.imageSmoothingEnabled = true;
    finalCtx.imageSmoothingQuality = 'high';
    finalCtx.drawImage(currentCanvas, 0, 0, targetWidth, targetHeight);

    return finalCanvas;
  }

  /**
   * Helper method to draw image to canvas
   */
  drawImageToCanvas(image, width, height) {
    const canvas = document.createElement('canvas');
    const ctx = canvas.getContext('2d');
    
    canvas.width = width;
    canvas.height = height;
    
    ctx.imageSmoothingEnabled = true;
    ctx.imageSmoothingQuality = 'high';
    ctx.drawImage(image, 0, 0, width, height);
    
    return canvas;
  }

  /**
   * Maintain full-resolution image reference for final export
   * Requirement 2.2: Process full-resolution only on export
   * Requirement 4.3: Store full-resolution for export
   */
  setFullResolutionImage(image) {
    this.fullResolutionImage = image;
  }

  /**
   * Get full-resolution image for export
   */
  getFullResolutionImage() {
    return this.fullResolutionImage;
  }

  /**
   * Check if current preview is downsampled
   */
  isPreviewDownsampled() {
    return this.previewDimensions && this.previewDimensions.needsDownsampling;
  }

  /**
   * Get current preview dimensions
   */
  getCurrentPreviewDimensions() {
    return this.previewDimensions;
  }

  /**
   * Apply filters to full-resolution image for export
   * Requirement 2.2: Process full-resolution on export
   */
  applyFiltersToFullResolution(filterFunction) {
    if (!this.fullResolutionImage) {
      throw new Error('No full-resolution image available');
    }

    // Create canvas at full resolution
    const canvas = document.createElement('canvas');
    const ctx = canvas.getContext('2d');
    
    canvas.width = this.fullResolutionImage.width;
    canvas.height = this.fullResolutionImage.height;
    
    ctx.drawImage(this.fullResolutionImage, 0, 0);
    
    // Get image data
    const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
    
    // Apply filter function
    const processedImageData = filterFunction(imageData);
    
    // Put processed data back
    ctx.putImageData(processedImageData, 0, 0);
    
    return canvas;
  }

  /**
   * Get memory usage estimate for current images
   */
  getMemoryUsage() {
    let usage = 0;
    
    if (this.fullResolutionImage) {
      // 4 bytes per pixel (RGBA)
      usage += this.fullResolutionImage.width * this.fullResolutionImage.height * 4;
    }
    
    if (this.previewDimensions) {
      usage += this.previewDimensions.width * this.previewDimensions.height * 4;
    }
    
    return {
      bytes: usage,
      megabytes: (usage / (1024 * 1024)).toFixed(2)
    };
  }

  /**
   * Clear stored images to free memory
   */
  clear() {
    this.fullResolutionImage = null;
    this.fullResolutionImageData = null;
    this.previewDimensions = null;
  }

  /**
   * Get device-specific configuration
   */
  getDeviceConfig() {
    const configs = {
      high: {
        maxPreviewSize: 3000,
        debounceDelay: 50,
        enableRealTimePreview: true,
        cacheSize: 20
      },
      medium: {
        maxPreviewSize: 2000,
        debounceDelay: 100,
        enableRealTimePreview: true,
        cacheSize: 10
      },
      low: {
        maxPreviewSize: 1000,
        debounceDelay: 200,
        enableRealTimePreview: false,
        cacheSize: 5
      }
    };

    return configs[this.deviceLevel];
  }
}

// Export for use in other modules
if (typeof module !== 'undefined' && module.exports) {
  module.exports = PreviewScaler;
} else {
  window.PreviewScaler = PreviewScaler;
}
