/**
 * WidgetGrid - Draggable grid layout for widgets
 * Uses react-grid-layout for drag-and-drop functionality
 */

import { useCallback, useMemo } from "react";
import GridLayout from "react-grid-layout";
import type { Layout } from "react-grid-layout";
import type { WidgetPlacement } from "@mosaic/shared";
import { cn } from "@mosaic/ui/lib/utils";
import { getWidgetByName } from "./WidgetRegistry";
import { BaseWidget } from "./BaseWidget";
import "react-grid-layout/css/styles.css";

export interface WidgetGridProps {
  layout: WidgetPlacement[];
  onLayoutChange: (layout: WidgetPlacement[]) => void;
  onRemoveWidget?: (widgetId: string) => void;
  isEditing?: boolean;
  className?: string;
}

export function WidgetGrid({
  layout,
  onLayoutChange,
  onRemoveWidget,
  isEditing = false,
  className,
}: WidgetGridProps) {
  // Convert WidgetPlacement to react-grid-layout Layout format
  const gridLayout: Layout[] = useMemo(
    () =>
      layout.map((item) => ({
        i: item.i,
        x: item.x,
        y: item.y,
        w: item.w,
        h: item.h,
        minW: item.minW,
        maxW: item.maxW,
        minH: item.minH,
        maxH: item.maxH,
        static: !isEditing || item.static,
        isDraggable: isEditing && (item.isDraggable !== false),
        isResizable: isEditing && (item.isResizable !== false),
      })),
    [layout, isEditing]
  );

  const handleLayoutChange = useCallback(
    (newLayout: Layout[]) => {
      const updatedLayout: WidgetPlacement[] = newLayout.map((item) => ({
        i: item.i,
        x: item.x,
        y: item.y,
        w: item.w,
        h: item.h,
        minW: item.minW,
        maxW: item.maxW,
        minH: item.minH,
        maxH: item.maxH,
        static: item.static,
        isDraggable: item.isDraggable,
        isResizable: item.isResizable,
      }));
      onLayoutChange(updatedLayout);
    },
    [onLayoutChange]
  );

  const handleRemoveWidget = useCallback(
    (widgetId: string) => {
      if (onRemoveWidget) {
        onRemoveWidget(widgetId);
      }
    },
    [onRemoveWidget]
  );

  // Empty state
  if (layout.length === 0) {
    return (
      <div className="flex items-center justify-center h-full min-h-[400px] bg-gray-50 rounded-lg border-2 border-dashed border-gray-300">
        <div className="text-center">
          <p className="text-gray-500 text-lg font-medium">No widgets yet</p>
          <p className="text-gray-400 text-sm mt-1">
            Add widgets to customize your dashboard
          </p>
        </div>
      </div>
    );
  }

  return (
    <div className={cn("widget-grid-container", className)}>
      <GridLayout
        className="layout"
        layout={gridLayout}
        onLayoutChange={handleLayoutChange}
        cols={12}
        rowHeight={100}
        width={1200}
        isDraggable={isEditing}
        isResizable={isEditing}
        compactType="vertical"
        preventCollision={false}
        data-testid="grid-layout"
      >
        {layout.map((item) => {
          // Extract widget type from widget ID (format: "WidgetType-uuid")
          const widgetType = item.i.split("-")[0];
          const widgetDef = getWidgetByName(widgetType);

          if (!widgetDef) {
            return (
              <div key={item.i} data-testid={`widget-${item.i}`}>
                <BaseWidget id={item.i} title="Unknown Widget" error="Widget not found" />
              </div>
            );
          }

          const WidgetComponent = widgetDef.component;

          return (
            <div key={item.i} data-testid={`widget-${item.i}`}>
              <BaseWidget
                id={item.i}
                title={widgetDef.displayName}
                description={widgetDef.description}
                onEdit={isEditing ? undefined : undefined} // TODO: Implement edit
                onRemove={
                  isEditing && onRemoveWidget
                    ? () => handleRemoveWidget(item.i)
                    : undefined
                }
              >
                <WidgetComponent id={item.i} />
              </BaseWidget>
            </div>
          );
        })}
      </GridLayout>
    </div>
  );
}
