import { Rect, Image as KonvaImage, Group } from 'react-konva';
import { CanvasObject, LogoPlaceholderObject } from '../../types/canvas.types';
import { useEffect, useRef, useState } from 'react';
import Konva from 'konva';
import TextEditable from './TextEditable';

interface CanvasObjectProps {
  object: CanvasObject;
  isSelected: boolean;
  onSelect: (e?: Konva.KonvaEventObject<MouseEvent>) => void;
  onDragStart?: (e: Konva.KonvaEventObject<DragEvent>) => void;
  onDragMove?: (e: Konva.KonvaEventObject<DragEvent>) => void;
  onDragEnd?: (e: Konva.KonvaEventObject<DragEvent>) => void;
  onTransformEnd?: (e: Konva.KonvaEventObject<Event>) => void;
  onEditingChange?: (id: string, isEditing: boolean, clickX?: number, clickY?: number) => void;
  onMouseEnter?: () => void;
  onMouseLeave?: () => void;
  shapeRef?: ((node: Konva.Node | null) => void) | React.RefObject<Konva.Node>;
}

export default function CanvasObjectRenderer({
  object,
  isSelected,
  onSelect,
  onDragStart,
  onDragMove,
  onDragEnd,
  onTransformEnd,
  onEditingChange,
  onMouseEnter,
  onMouseLeave,
  shapeRef
}: CanvasObjectProps) {
  switch (object.type) {
    case 'rect':
      return (
        <Rect
          id={object.id}
          ref={(node) => {
            if (typeof shapeRef === 'function') {
              shapeRef(node);
            } else if (shapeRef) {
              (shapeRef as React.MutableRefObject<Konva.Rect | null>).current = node;
            }
          }}
          x={object.x}
          y={object.y}
          width={object.width}
          height={object.height}
          fill={object.fill}
          stroke={object.stroke}
          strokeWidth={object.strokeWidth}
          rotation={object.rotation}
          draggable
          onClick={(e) => onSelect(e)}
          onTap={(e) => onSelect(e)}
          onDragStart={onDragStart}
          onDragMove={onDragMove}
          onDragEnd={onDragEnd}
          onTransformEnd={onTransformEnd}
          onMouseEnter={onMouseEnter}
          onMouseLeave={onMouseLeave}
        />
      );

    case 'image':
    case 'huggy':
      return (
        <ImageRenderer
          object={object}
          onSelect={onSelect}
          onDragStart={onDragStart}
          onDragMove={onDragMove}
          onDragEnd={onDragEnd}
          onTransformEnd={onTransformEnd}
          onMouseEnter={onMouseEnter}
          onMouseLeave={onMouseLeave}
          shapeRef={shapeRef}
        />
      );

    case 'text':
      return (
        <TextEditable
          object={object}
          isSelected={isSelected}
          onSelect={onSelect}
          onDragStart={onDragStart}
          onDragMove={onDragMove}
          onDragEnd={onDragEnd}
          onTransformEnd={onTransformEnd}
          onEditingChange={onEditingChange || (() => {})}
          onMouseEnter={onMouseEnter}
          onMouseLeave={onMouseLeave}
          shapeRef={shapeRef as React.RefObject<Konva.Text>}
        />
      );

    case 'logoPlaceholder':
      return (
        <LogoPlaceholderRenderer
          object={object}
          onSelect={onSelect}
          onDragStart={onDragStart}
          onDragMove={onDragMove}
          onDragEnd={onDragEnd}
          onTransformEnd={onTransformEnd}
          onMouseEnter={onMouseEnter}
          onMouseLeave={onMouseLeave}
          shapeRef={shapeRef}
        />
      );

    default:
      return null;
  }
}

// Image renderer with image loading
function ImageRenderer({
  object,
  onSelect,
  onDragStart,
  onDragMove,
  onDragEnd,
  onTransformEnd,
  onMouseEnter,
  onMouseLeave,
  shapeRef
}: Omit<CanvasObjectProps, 'isSelected' | 'onEditingChange'>) {
  const [image, setImage] = useState<HTMLImageElement | null>(null);
  const imageRef = useRef<HTMLImageElement | null>(null);
  const nodeRef = useRef<Konva.Image | null>(null);

  useEffect(() => {
    const img = new window.Image();
    img.src = object.type === 'image' || object.type === 'huggy' ? object.src : '';
    img.crossOrigin = 'anonymous';

    img.onload = () => {
      setImage(img);
      imageRef.current = img;
      // Force a small delay to ensure ref is registered and transformer can update
      setTimeout(() => {
        if (nodeRef.current) {
          // Trigger a layer redraw to ensure transformer picks up the node
          const layer = nodeRef.current.getLayer();
          if (layer) {
            layer.batchDraw();
          }
        }
      }, 10);
    };

    return () => {
      imageRef.current = null;
    };
  }, [object]);

  return (
    <>
      {image && (
        <KonvaImage
      id={object.id}
      ref={(node) => {
        nodeRef.current = node;
        if (typeof shapeRef === 'function') {
          shapeRef(node);
        } else if (shapeRef) {
          (shapeRef as React.MutableRefObject<Konva.Image | null>).current = node;
        }
      }}
      x={object.x}
      y={object.y}
      width={object.width}
      height={object.height}
      image={image}
      rotation={object.rotation}
      draggable
      onClick={(e) => onSelect(e)}
      onTap={(e) => onSelect(e)}
      onDragStart={onDragStart}
      onDragMove={onDragMove}
      onDragEnd={onDragEnd}
      onTransformEnd={onTransformEnd}
      onMouseEnter={onMouseEnter}
      onMouseLeave={onMouseLeave}
        />
      )}
    </>
  );
}

// Logo placeholder renderer with blur effect
function LogoPlaceholderRenderer({
  object,
  onSelect,
  onDragStart,
  onDragMove,
  onDragEnd,
  onTransformEnd,
  onMouseEnter,
  onMouseLeave,
  shapeRef
}: Omit<CanvasObjectProps, 'isSelected' | 'onEditingChange'>) {
  const rectRef = useRef<Konva.Rect>(null);

  useEffect(() => {
    if (rectRef.current && object.type === 'logoPlaceholder') {
      rectRef.current.cache();
      rectRef.current.filters([Konva.Filters.Blur]);
      rectRef.current.blurRadius(object.blurRadius);
    }
  }, [object]);

  if (object.type !== 'logoPlaceholder') return null;

  return (
    <Rect
      id={object.id}
      ref={(node) => {
        rectRef.current = node;
        if (typeof shapeRef === 'function') {
          shapeRef(node);
        } else if (shapeRef) {
          (shapeRef as React.MutableRefObject<Konva.Rect | null>).current = node;
        }
      }}
      x={object.x}
      y={object.y}
      width={object.width}
      height={object.height}
      fill="rgba(255, 255, 255, 0.3)"
      stroke="rgba(200, 200, 200, 0.5)"
      strokeWidth={2}
      rotation={object.rotation}
      draggable
      onClick={(e) => onSelect(e)}
      onTap={(e) => onSelect(e)}
      onDragStart={onDragStart}
      onDragMove={onDragMove}
      onDragEnd={onDragEnd}
      onTransformEnd={onTransformEnd}
      onMouseEnter={onMouseEnter}
      onMouseLeave={onMouseLeave}
    />
  );
}
