import { useRef, useImperativeHandle, forwardRef } from 'react'
import { requireNativeViewManager, NativeModulesProxy } from 'expo-modules-core'
import { ViewProps, StyleSheet, ViewStyle } from 'react-native'

// MARK: - Types

/**
 * Aspect ratio for crop
 */
export type CropAspectRatio = {
  label: string
  ratio: number | null // null = free form
}

/**
 * UI Configuration for the Image Editor
 * Provides extensive control over the editor's appearance and behavior
 */
export interface ImageEditorUIConfig {
  // ========== Feature Toggles ==========
  /** Enable adjustment tools (brightness, contrast, etc.) */
  enableAdjustments?: boolean
  /** Enable filter gallery */
  enableFilters?: boolean
  /** Enable transform tools (crop, rotate, flip) */
  enableTransforms?: boolean
  /** Enable layer management */
  enableLayers?: boolean
  /** Enable drawing tools */
  enableDrawing?: boolean
  /** Enable text tool */
  enableText?: boolean
  /** Enable stickers */
  enableStickers?: boolean
  /** Enable LUT (color grading) support */
  enableLUT?: boolean

  // ========== UI Toggles ==========
  /** Show top toolbar with controls */
  showTopToolbar?: boolean
  /** Show bottom toolbar with tools */
  showBottomToolbar?: boolean
  /** Enable undo button */
  enableUndo?: boolean
  /** Enable redo button */
  enableRedo?: boolean
  /** Enable reset button */
  enableReset?: boolean
  /** Enable export button */
  enableExport?: boolean
  /** Show close button */
  showCloseButton?: boolean
  /** Show load new image button */
  showLoadButton?: boolean
  /** Show share button */
  showShareButton?: boolean
  /** Show info/help button */
  showInfoButton?: boolean

  // ========== Export Options ==========
  /** Allowed export formats */
  allowedExportFormats?: ('jpeg' | 'png' | 'heic')[]
  /** Default export format */
  defaultExportFormat?: 'jpeg' | 'png' | 'heic'
  /** Default export quality (0.0 - 1.0) */
  defaultExportQuality?: number
  /** Maximum dimension for export (width/height) */
  maxExportDimension?: number
  /** Show export progress indicator */
  showExportProgress?: boolean
  /** Export progress style */
  exportProgressStyle?: 'bar' | 'circular' | 'minimal'
  /** Embed metadata in exported image */
  embedMetadata?: boolean
  /** Preserve EXIF data */
  preserveExif?: boolean
  /** Compression method */
  compressionMethod?: 'fast' | 'balanced' | 'best'
  /** Automatically save to Photos */
  exportToPhotos?: boolean
  /** Show share sheet after export */
  exportShareSheet?: boolean

  // ========== Filter Configuration ==========
  /** Available filters (null = all) */
  availableFilters?: string[]
  /** Default filter intensity (0.0 - 1.0) */
  defaultFilterIntensity?: number
  /** Show intensity slider for filters */
  showFilterIntensitySlider?: boolean
  /** Filter intensity range */
  filterIntensityRange?: { min: number; max: number }
  /** Show filter preview thumbnails */
  showFilterPreviews?: boolean
  /** Filter preview thumbnail size */
  filterPreviewSize?: number
  /** Enable before/after comparison */
  enableFilterComparison?: boolean
  /** Allow applying multiple filters */
  allowMultipleFilters?: boolean

  // ========== Adjustment Configuration ==========
  /** Available adjustments (null = all) */
  availableAdjustments?: string[]
  /** Custom adjustment ranges */
  adjustmentRanges?: Record<string, { min: number; max: number }>
  /** Slider step increments per adjustment */
  adjustmentSteps?: Record<string, number>
  /** Default values per adjustment */
  adjustmentDefaults?: Record<string, number>
  /** Show adjustment values */
  showAdjustmentValues?: boolean
  /** Show reset button per adjustment */
  showAdjustmentReset?: boolean
  /** Live preview while adjusting */
  adjustmentLivePreview?: boolean

  // ========== Transform Configuration ==========
  /** Enable crop tool */
  enableCrop?: boolean
  /** Enable rotate tool */
  enableRotate?: boolean
  /** Enable flip tools */
  enableFlip?: boolean
  /** Enable resize tool */
  enableResize?: boolean
  /** Rotation step in degrees */
  rotationStep?: number
  /** Crop aspect ratio presets */
  cropAspectRatios?: CropAspectRatio[]
  /** Enable freeform crop */
  enableFreeformCrop?: boolean
  /** Show crop grid overlay */
  showCropGrid?: boolean
  /** Number of grid lines */
  cropGridLines?: number
  /** Allow rotation beyond step increments */
  allowRotationBeyondStep?: boolean
  /** Enable rotation gesture */
  rotationGestureEnabled?: boolean

  // ========== Drawing Configuration ==========
  /** Default brush size */
  defaultBrushSize?: number
  /** Default brush opacity (0.0 - 1.0) */
  defaultBrushOpacity?: number
  /** Enable eraser tool */
  enableEraser?: boolean
  /** Minimum brush size */
  minBrushSize?: number
  /** Maximum brush size */
  maxBrushSize?: number
  /** Brush size step increment */
  brushSizeStep?: number
  /** Available brush colors (null = color picker) */
  availableBrushColors?: string[]
  /** Enable brush opacity control */
  enableBrushOpacity?: boolean
  /** Enable brush blending modes */
  enableBrushBlending?: boolean
  /** Show brush preview */
  showBrushPreview?: boolean
  /** Enable pressure sensitivity (Apple Pencil) */
  enablePressureSensitivity?: boolean
  /** Drawing smoothing (0.0 - 1.0) */
  drawingSmoothing?: number

  // ========== Layer Configuration ==========
  /** Maximum number of layers */
  maxLayers?: number
  /** Default layer opacity */
  defaultLayerOpacity?: number
  /** Available blend modes (null = all) */
  availableBlendModes?: string[]

  // ========== Text Configuration ==========
  /** Default text size */
  defaultTextSize?: number
  /** Available fonts (null = system fonts) */
  availableFonts?: string[]
  /** Enable text shadow */
  enableTextShadow?: boolean
  /** Enable text stroke */
  enableTextStroke?: boolean

  // ========== Performance Configuration ==========
  /** Maximum undo/redo states */
  maxHistoryStates?: number
  /** Enable automatic memory monitoring */
  enableMemoryMonitoring?: boolean
  /** Maximum preview dimension (downsampling) */
  maxPreviewDimension?: number
  /** Enable GPU acceleration */
  enableGPUAcceleration?: boolean
  /** Enable auto-save */
  autoSaveEnabled?: boolean
  /** Auto-save interval in seconds */
  autoSaveInterval?: number
  /** Preload filters for faster application */
  preloadFilters?: boolean
  /** Cache processed images */
  cacheProcessedImages?: boolean
  /** Enable low memory mode (reduces quality) */
  lowMemoryMode?: boolean

  // ========== UI Behavior ==========
  /** Enable haptic feedback */
  enableHapticFeedback?: boolean
  /** Enable animations */
  enableAnimations?: boolean
  /** Animation duration in seconds */
  animationDuration?: number
  /** Animate toolbar transitions */
  toolbarAnimated?: boolean
  /** Animate panel transitions */
  panelAnimated?: boolean
  /** Enable double tap to zoom */
  enableDoubleTapToZoom?: boolean
  /** Double tap zoom scale */
  doubleTapZoomScale?: number
  /** Maximum zoom scale */
  maxZoomScale?: number
  /** Minimum zoom scale */
  minZoomScale?: number

  // ========== Gesture Configuration ==========
  /** Enable pinch to zoom */
  enablePinchToZoom?: boolean
  /** Enable pan gesture */
  enablePanGesture?: boolean
  /** Enable rotation gesture */
  enableRotationGesture?: boolean
  /** Enable swipe gestures */
  enableSwipeGestures?: boolean
  /** Swipe to undo/redo */
  swipeToUndoEnabled?: boolean
  /** Long press for additional options */
  longPressForOptions?: boolean

  // ========== Validation & Constraints ==========
  /** Minimum image dimension (width or height) */
  minImageDimension?: number
  /** Maximum image dimension (width or height) */
  maxImageDimension?: number
  /** Allowed image file formats */
  allowedImageFormats?: string[]
  /** Maximum file size in bytes (null = no limit) */
  maxFileSize?: number | null
  /** Warn user about large images */
  warnOnLargeImages?: boolean
  /** Threshold for large image warning (pixels) */
  largeImageThreshold?: number

  // ========== Toolbar Layout ==========
  /** Toolbar position */
  toolbarPosition?: 'top' | 'bottom' | 'floating'
  /** Toolbar height */
  toolbarHeight?: number
  /** Toolbar padding */
  toolbarPadding?: number
  /** Toolbar item spacing */
  toolbarSpacing?: number
  /** Bottom toolbar layout style */
  bottomToolbarLayout?: 'scrollable' | 'grid' | 'grouped'
  /** Make toolbar collapsible */
  toolbarCollapsible?: boolean

  // ========== Panel Configuration ==========
  /** Panel position */
  panelPosition?: 'bottom' | 'side' | 'overlay'
  /** Panel height */
  panelHeight?: number
  /** Allow panel dismissal */
  panelDismissable?: boolean
  /** Show panel drag handle */
  panelDragHandle?: boolean
  /** Apply blur effect to panel background */
  panelBlurEffect?: boolean

  // ========== Localization ==========
  /** Localized strings map */
  localizedStrings?: Record<string, string>
  /** Date format string */
  dateFormat?: string
  /** Use system language */
  useSystemLanguage?: boolean
}

/**
 * Image source for loading
 */
export interface ImageSource {
  uri: string
}

/**
 * Export result
 */
export interface ExportResult {
  uri: string
  path: string
}

/**
 * Error event
 */
export interface ErrorEvent {
  error: string
}

/**
 * Props for ImageEditorUI component
 */
export interface ImageEditorUIProps extends ViewProps {
  /**
   * Image source to load
   */
  source?: ImageSource

  /**
   * UI configuration
   */
  config?: ImageEditorUIConfig

  /**
   * Called when the editor is ready
   */
  onReady?: () => void

  /**
   * Called when an image is loaded
   */
  onImageLoaded?: () => void

  /**
   * Called when the image is changed
   */
  onImageChanged?: () => void

  /**
   * Called when an image is exported
   */
  onExport?: (result: ExportResult) => void

  /**
   * Called when an error occurs
   */
  onError?: (error: ErrorEvent) => void

  /**
   * Called when the editor is closed
   */
  onClose?: () => void

  /**
   * Style for the view
   */
  style?: ViewStyle
}

/**
 * Ref methods for imperative API
 */
export interface ImageEditorUIRef {
  /**
   * Load an image from a source
   */
  loadImage: (source: ImageSource) => Promise<void>

  /**
   * Update the configuration
   */
  updateConfig: (config: ImageEditorUIConfig) => Promise<void>

  /**
   * Get the current image
   */
  getCurrentImage: () => Promise<ExportResult>
}

// MARK: - Native View Manager

const NativeView = requireNativeViewManager('ImageEditorUI')

// MARK: - Component

/**
 * Image Editor UI Component
 *
 * A complete native image editing interface with all tools built-in.
 * This component provides a full-featured UI that can be configured via props.
 *
 * @example
 * ```tsx
 * import { ImageEditorUI } from 'react-native-image-editor-sdk';
 *
 * function MyEditor() {
 *   const editorRef = useRef<ImageEditorUIRef>(null);
 *
 *   return (
 *     <ImageEditorUI
 *       ref={editorRef}
 *       source={{ uri: 'file:///path/to/image.jpg' }}
 *       config={{
 *         enableAdjustments: true,
 *         enableFilters: true,
 *         enableDrawing: true,
 *         allowedExportFormats: ['jpeg', 'png']
 *       }}
 *       onExport={(result) => {
 *         console.log('Exported:', result.uri);
 *       }}
 *       onError={(error) => {
 *         console.error('Error:', error.error);
 *       }}
 *       style={{ flex: 1 }}
 *     />
 *   );
 * }
 * ```
 */
export const ImageEditorUI = forwardRef<ImageEditorUIRef, ImageEditorUIProps>(
  ({ source, config, onReady, onImageLoaded, onImageChanged, onExport, onError, onClose, style, ...props }, ref) => {
    const nativeRef = useRef<any>(null)

    // Expose imperative methods
    useImperativeHandle(ref, () => ({
      loadImage: async (source: ImageSource) => {
        if (nativeRef.current) {
          await NativeModulesProxy.ImageEditorUI.loadImage(nativeRef.current, source)
        }
      },
      updateConfig: async (config: ImageEditorUIConfig) => {
        if (nativeRef.current) {
          await NativeModulesProxy.ImageEditorUI.updateConfig(nativeRef.current, config)
        }
      },
      getCurrentImage: async (): Promise<ExportResult> => {
        if (nativeRef.current) {
          return await NativeModulesProxy.ImageEditorUI.getCurrentImage(nativeRef.current)
        }
        throw new Error('Editor not initialized')
      },
    }))

    return (
      <NativeView
        ref={nativeRef}
        source={source}
        config={config}
        onReady={onReady}
        onImageLoaded={onImageLoaded}
        onImageChanged={onImageChanged}
        onExport={onExport}
        onError={onError}
        onClose={onClose}
        style={[styles.default, style]}
        {...props}
      />
    )
  }
)

ImageEditorUI.displayName = 'ImageEditorUI'

// MARK: - Preset Configurations

/**
 * Preset configurations for common use cases
 */
export const ImageEditorUIPresets = {
  /**
   * Minimal configuration with only essential features
   */
  minimal: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: false,
    enableDrawing: false,
    enableText: false,
    enableStickers: false,
    enableLUT: false,
    showFilterPreviews: false,
    enableAnimations: true,
    enableHapticFeedback: true,
  }),

  /**
   * Photo editor configuration
   */
  photoEditor: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: true,
    enableDrawing: true,
    enableText: false,
    enableStickers: false,
    enableLUT: true,
    showFilterPreviews: true,
    showFilterIntensitySlider: true,
    adjustmentLivePreview: true,
    enableFilterComparison: true,
    showCropGrid: true,
    enableHapticFeedback: true,
  }),

  /**
   * Social media configuration with popular filters
   */
  socialMedia: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: false,
    enableDrawing: false,
    enableText: true,
    enableStickers: true,
    enableLUT: false,
    availableFilters: ['vintage', 'dramatic', 'noir', 'fade', 'instant'],
    maxExportDimension: 2048,
    cropAspectRatios: [
      { label: 'Square', ratio: 1.0 },
      { label: 'Instagram', ratio: 4.0 / 5.0 },
      { label: 'Story', ratio: 9.0 / 16.0 },
      { label: 'Free', ratio: null },
    ],
    showShareButton: true,
    exportShareSheet: true,
    enableHapticFeedback: true,
    enableAnimations: true,
  }),

  /**
   * Professional configuration with all features
   */
  professional: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: true,
    enableDrawing: true,
    enableText: true,
    enableStickers: true,
    enableLUT: true,
    maxHistoryStates: 100,
    allowedExportFormats: ['jpeg', 'png', 'heic'],
    showFilterPreviews: true,
    showFilterIntensitySlider: true,
    adjustmentLivePreview: true,
    showAdjustmentValues: true,
    showAdjustmentReset: true,
    enableFilterComparison: true,
    showCropGrid: true,
    enableFreeformCrop: true,
    allowRotationBeyondStep: true,
    enablePressureSensitivity: true,
    showBrushPreview: true,
    enableBrushOpacity: true,
    enableBrushBlending: true,
    showExportProgress: true,
    preserveExif: true,
    embedMetadata: true,
    autoSaveEnabled: true,
    autoSaveInterval: 60,
    preloadFilters: true,
    cacheProcessedImages: true,
    enableHapticFeedback: true,
    enableAnimations: true,
    enableDoubleTapToZoom: true,
    longPressForOptions: true,
  }),

  /**
   * Drawing-focused configuration
   */
  drawing: (): ImageEditorUIConfig => ({
    enableAdjustments: false,
    enableFilters: false,
    enableTransforms: true,
    enableLayers: true,
    enableDrawing: true,
    enableText: true,
    enableStickers: false,
    enableLUT: false,
    minBrushSize: 1,
    maxBrushSize: 100,
    brushSizeStep: 0.5,
    defaultBrushSize: 10,
    showBrushPreview: true,
    enableBrushOpacity: true,
    enablePressureSensitivity: true,
    drawingSmoothing: 0.7,
    enableHapticFeedback: true,
    maxHistoryStates: 200,
  }),

  /**
   * Quick edit - fast and simple adjustments
   */
  quickEdit: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: false,
    enableDrawing: false,
    enableText: false,
    enableStickers: false,
    availableAdjustments: ['brightness', 'contrast', 'saturation'],
    availableFilters: ['vintage', 'mono', 'warm', 'cool'],
    cropAspectRatios: [
      { label: 'Free', ratio: null },
      { label: 'Square', ratio: 1.0 },
    ],
    showFilterPreviews: false,
    showAdjustmentReset: true,
    enableAnimations: true,
    animationDuration: 0.2,
    maxHistoryStates: 20,
  }),

  /**
   * Performance optimized for large images
   */
  performanceOptimized: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: false,
    enableDrawing: false,
    enableText: false,
    enableStickers: false,
    maxPreviewDimension: 1536,
    maxHistoryStates: 30,
    enableGPUAcceleration: true,
    lowMemoryMode: false,
    preloadFilters: true,
    cacheProcessedImages: true,
    showFilterPreviews: false,
    adjustmentLivePreview: true,
    enableAnimations: false,
    compressionMethod: 'fast',
    warnOnLargeImages: true,
    largeImageThreshold: 4096,
  }),

  /**
   * High quality export focused
   */
  highQuality: (): ImageEditorUIConfig => ({
    enableAdjustments: true,
    enableFilters: true,
    enableTransforms: true,
    enableLayers: true,
    enableDrawing: true,
    enableText: true,
    allowedExportFormats: ['png', 'heic'],
    defaultExportFormat: 'heic',
    defaultExportQuality: 1.0,
    maxExportDimension: undefined,
    compressionMethod: 'best',
    preserveExif: true,
    embedMetadata: true,
    showExportProgress: true,
    exportProgressStyle: 'bar',
    maxHistoryStates: 100,
    enableGPUAcceleration: true,
  }),
}

// MARK: - Styles

const styles = StyleSheet.create({
  default: {
    flex: 1,
  },
})

// MARK: - Exports

export default ImageEditorUI
