"use client";

import React, { useState, useRef, useCallback } from "react";
import { useRouter } from "next/navigation";
import { DashboardCanvas } from "./DashboardCanvas";
import { DashboardTopMenu } from "./DashboardTopMenu";
import { ElementConfigModal } from "./ElementConfigModal";
import { ListWidgetConfigModal } from "./widgets/ListWidgetConfigModal";
import { TodoWidgetConfigModal } from "./widgets/TodoWidgetConfigModal";
import { DashboardElement, ElementType, ElementSubtype } from "./types";
import { GRID_CONFIG, snapToGrid, snapSizeToGrid, calculateCellSize } from "./gridUtils";
import { Resolution, RESOLUTIONS, detectScreenResolution } from "./ResolutionSelector";
import { DashboardProvider } from "@/contexts/DashboardContext";

interface DashboardDesignerProps {
  dashboardId?: string;
}

/**
 * 대시보드 설계 도구 메인 컴포넌트
 * - 드래그 앤 드롭으로 차트/위젯 배치
 * - 그리드 기반 레이아웃 (12 컬럼)
 * - 요소 이동, 크기 조절, 삭제 기능
 * - 레이아웃 저장/불러오기 기능
 */
export default function DashboardDesigner({ dashboardId: initialDashboardId }: DashboardDesignerProps = {}) {
  const router = useRouter();
  const [elements, setElements] = useState<DashboardElement[]>([]);
  const [selectedElement, setSelectedElement] = useState<string | null>(null);
  const [elementCounter, setElementCounter] = useState(0);
  const [configModalElement, setConfigModalElement] = useState<DashboardElement | null>(null);
  const [dashboardId, setDashboardId] = useState<string | null>(initialDashboardId || null);
  const [dashboardTitle, setDashboardTitle] = useState<string>("");
  const [isLoading, setIsLoading] = useState(false);
  const [canvasBackgroundColor, setCanvasBackgroundColor] = useState<string>("#f9fafb");
  const canvasRef = useRef<HTMLDivElement>(null);

  // 화면 해상도 자동 감지
  const [screenResolution] = useState<Resolution>(() => detectScreenResolution());
  const [resolution, setResolution] = useState<Resolution>(screenResolution);

  // resolution 변경 감지 및 요소 자동 조정
  const handleResolutionChange = useCallback(
    (newResolution: Resolution) => {
      console.log("🎯 해상도 변경 요청:", newResolution);
      setResolution((prev) => {
        console.log("🎯 이전 해상도:", prev);

        // 이전 해상도와 새 해상도의 캔버스 너비 비율 계산
        const oldConfig = RESOLUTIONS[prev];
        const newConfig = RESOLUTIONS[newResolution];
        const widthRatio = newConfig.width / oldConfig.width;

        console.log("📐 너비 비율:", widthRatio, `(${oldConfig.width}px → ${newConfig.width}px)`);

        // 요소들의 위치와 크기를 비율에 맞춰 조정
        if (widthRatio !== 1 && elements.length > 0) {
          // 새 해상도의 셀 크기 계산
          const newCellSize = calculateCellSize(newConfig.width);

          const adjustedElements = elements.map((el) => {
            // 비율에 맞춰 조정 (X와 너비만)
            const scaledX = el.position.x * widthRatio;
            const scaledWidth = el.size.width * widthRatio;

            // 그리드에 스냅 (X, Y, 너비, 높이 모두)
            const snappedX = snapToGrid(scaledX, newCellSize);
            const snappedY = snapToGrid(el.position.y, newCellSize);
            const snappedWidth = snapSizeToGrid(scaledWidth, 2, newCellSize);
            const snappedHeight = snapSizeToGrid(el.size.height, 2, newCellSize);

            return {
              ...el,
              position: {
                x: snappedX,
                y: snappedY,
              },
              size: {
                width: snappedWidth,
                height: snappedHeight,
              },
            };
          });

          console.log("✨ 요소 위치/크기 자동 조정 (그리드 스냅 적용):", adjustedElements.length, "개");
          setElements(adjustedElements);
        }

        return newResolution;
      });
    },
    [elements],
  );

  // 현재 해상도 설정 (안전하게 기본값 제공)
  const canvasConfig = RESOLUTIONS[resolution] || RESOLUTIONS.fhd;

  // 캔버스 높이 동적 계산 (요소들의 최하단 위치 기준)
  const calculateCanvasHeight = useCallback(() => {
    if (elements.length === 0) {
      return canvasConfig.height; // 기본 높이
    }

    // 모든 요소의 최하단 y 좌표 계산
    const maxBottomY = Math.max(...elements.map((el) => el.position.y + el.size.height));

    // 최소 높이는 기본 높이, 요소가 아래로 내려가면 자동으로 늘어남
    // 패딩 추가 (100px 여유)
    return Math.max(canvasConfig.height, maxBottomY + 100);
  }, [elements, canvasConfig.height]);

  const dynamicCanvasHeight = calculateCanvasHeight();

  // 대시보드 ID가 props로 전달되면 로드
  React.useEffect(() => {
    if (initialDashboardId) {
      loadDashboard(initialDashboardId);
    }
  }, [initialDashboardId]);

  // 대시보드 데이터 로드
  const loadDashboard = async (id: string) => {
    setIsLoading(true);
    try {
      // console.log('🔄 대시보드 로딩:', id);

      const { dashboardApi } = await import("@/lib/api/dashboard");
      const dashboard = await dashboardApi.getDashboard(id);

      // console.log('✅ 대시보드 로딩 완료:', dashboard);

      // 대시보드 정보 설정
      setDashboardId(dashboard.id);
      setDashboardTitle(dashboard.title);

      // 저장된 설정 복원
      console.log("🔍 로드된 대시보드:", dashboard);
      console.log("📦 저장된 settings:", (dashboard as any).settings);
      console.log("🎯 settings 타입:", typeof (dashboard as any).settings);
      console.log("🔍 resolution 값:", (dashboard as any).settings?.resolution);

      if ((dashboard as any).settings?.resolution) {
        const savedResolution = (dashboard as any).settings.resolution as Resolution;
        console.log("✅ 저장된 해상도 복원:", savedResolution);
        setResolution(savedResolution);
      } else {
        console.log("⚠️ 저장된 해상도 없음");
      }

      if ((dashboard as any).settings?.backgroundColor) {
        console.log("✅ 저장된 배경색 복원:", (dashboard as any).settings.backgroundColor);
        setCanvasBackgroundColor((dashboard as any).settings.backgroundColor);
      }

      // 요소들 설정
      if (dashboard.elements && dashboard.elements.length > 0) {
        setElements(dashboard.elements);

        // elementCounter를 가장 큰 ID 번호로 설정
        const maxId = dashboard.elements.reduce((max, el) => {
          const match = el.id.match(/element-(\d+)/);
          if (match) {
            const num = parseInt(match[1]);
            return num > max ? num : max;
          }
          return max;
        }, 0);
        setElementCounter(maxId);
      }
    } catch (error) {
      // console.error('❌ 대시보드 로딩 오류:', error);
      alert(
        "대시보드를 불러오는 중 오류가 발생했습니다.\n\n" +
          (error instanceof Error ? error.message : "알 수 없는 오류"),
      );
    } finally {
      setIsLoading(false);
    }
  };

  // 새로운 요소 생성 (동적 그리드 기반 기본 크기)
  const createElement = useCallback(
    (type: ElementType, subtype: ElementSubtype, x: number, y: number) => {
      // 좌표 유효성 검사
      if (isNaN(x) || isNaN(y)) {
        console.error("Invalid coordinates:", { x, y });
        return;
      }

      // 기본 크기 설정
      let defaultCells = { width: 2, height: 2 }; // 기본 위젯 크기

      if (type === "chart") {
        defaultCells = { width: 4, height: 3 }; // 차트
      } else if (type === "widget" && subtype === "calendar") {
        defaultCells = { width: 2, height: 3 }; // 달력 최소 크기
      }

      // 현재 해상도에 맞는 셀 크기 계산
      const cellSize = Math.floor((canvasConfig.width + GRID_CONFIG.GAP) / GRID_CONFIG.COLUMNS) - GRID_CONFIG.GAP;
      const cellWithGap = cellSize + GRID_CONFIG.GAP;

      const defaultWidth = defaultCells.width * cellWithGap - GRID_CONFIG.GAP;
      const defaultHeight = defaultCells.height * cellWithGap - GRID_CONFIG.GAP;

      // 크기 유효성 검사
      if (isNaN(defaultWidth) || isNaN(defaultHeight) || defaultWidth <= 0 || defaultHeight <= 0) {
        console.error("Invalid size calculated:", {
          canvasConfig,
          cellSize,
          cellWithGap,
          defaultCells,
          defaultWidth,
          defaultHeight,
        });
        return;
      }

      const newElement: DashboardElement = {
        id: `element-${elementCounter + 1}`,
        type,
        subtype,
        position: { x, y },
        size: { width: defaultWidth, height: defaultHeight },
        title: getElementTitle(type, subtype),
        content: getElementContent(type, subtype),
      };

      setElements((prev) => [...prev, newElement]);
      setElementCounter((prev) => prev + 1);
      setSelectedElement(newElement.id);
    },
    [elementCounter, canvasConfig.width],
  );

  // 메뉴에서 요소 추가 시 (캔버스 중앙에 배치)
  const addElementFromMenu = useCallback(
    (type: ElementType, subtype: ElementSubtype) => {
      // 캔버스 중앙 좌표 계산
      const centerX = Math.floor(canvasConfig.width / 2);
      const centerY = Math.floor(canvasConfig.height / 2);

      // 좌표 유효성 확인
      if (isNaN(centerX) || isNaN(centerY)) {
        console.error("Invalid canvas config:", canvasConfig);
        return;
      }

      createElement(type, subtype, centerX, centerY);
    },
    [canvasConfig.width, canvasConfig.height, createElement],
  );

  // 요소 업데이트
  const updateElement = useCallback((id: string, updates: Partial<DashboardElement>) => {
    setElements((prev) => prev.map((el) => (el.id === id ? { ...el, ...updates } : el)));
  }, []);

  // 요소 삭제
  const removeElement = useCallback(
    (id: string) => {
      setElements((prev) => prev.filter((el) => el.id !== id));
      if (selectedElement === id) {
        setSelectedElement(null);
      }
    },
    [selectedElement],
  );

  // 전체 삭제
  const clearCanvas = useCallback(() => {
    if (window.confirm("모든 요소를 삭제하시겠습니까?")) {
      setElements([]);
      setSelectedElement(null);
      setElementCounter(0);
    }
  }, []);

  // 요소 설정 모달 열기
  const openConfigModal = useCallback((element: DashboardElement) => {
    setConfigModalElement(element);
  }, []);

  // 요소 설정 모달 닫기
  const closeConfigModal = useCallback(() => {
    setConfigModalElement(null);
  }, []);

  // 요소 설정 저장
  const saveElementConfig = useCallback(
    (updatedElement: DashboardElement) => {
      updateElement(updatedElement.id, updatedElement);
    },
    [updateElement],
  );

  // 리스트 위젯 설정 저장 (Partial 업데이트)
  const saveListWidgetConfig = useCallback(
    (updates: Partial<DashboardElement>) => {
      if (configModalElement) {
        updateElement(configModalElement.id, updates);
      }
    },
    [configModalElement, updateElement],
  );

  const saveTodoWidgetConfig = useCallback(
    (updates: Partial<DashboardElement>) => {
      if (configModalElement) {
        updateElement(configModalElement.id, updates);
      }
    },
    [configModalElement, updateElement],
  );

  // 레이아웃 저장
  const saveLayout = useCallback(async () => {
    if (elements.length === 0) {
      alert("저장할 요소가 없습니다. 차트나 위젯을 추가해주세요.");
      return;
    }

    try {
      // 실제 API 호출
      const { dashboardApi } = await import("@/lib/api/dashboard");

      const elementsData = elements.map((el) => ({
        id: el.id,
        type: el.type,
        subtype: el.subtype,
        position: el.position,
        size: el.size,
        title: el.title,
        customTitle: el.customTitle,
        showHeader: el.showHeader,
        content: el.content,
        dataSource: el.dataSource,
        chartConfig: el.chartConfig,
      }));

      let savedDashboard;

      if (dashboardId) {
        // 기존 대시보드 업데이트
        console.log("💾 저장 시작 - 현재 resolution 상태:", resolution);
        console.log("💾 저장 시작 - 현재 배경색 상태:", canvasBackgroundColor);

        const updateData = {
          elements: elementsData,
          settings: {
            resolution,
            backgroundColor: canvasBackgroundColor,
          },
        };

        console.log("💾 저장할 데이터:", updateData);
        console.log("💾 저장할 settings:", updateData.settings);

        savedDashboard = await dashboardApi.updateDashboard(dashboardId, updateData);

        console.log("✅ 저장된 대시보드:", savedDashboard);
        console.log("✅ 저장된 settings:", (savedDashboard as any).settings);

        alert(`대시보드 "${savedDashboard.title}"이 업데이트되었습니다!`);

        // Next.js 라우터로 뷰어 페이지 이동
        router.push(`/dashboard/${savedDashboard.id}`);
      } else {
        // 새 대시보드 생성
        const title = prompt("대시보드 제목을 입력하세요:", "새 대시보드");
        if (!title) return;

        const description = prompt("대시보드 설명을 입력하세요 (선택사항):", "");

        const dashboardData = {
          title,
          description: description || undefined,
          isPublic: false,
          elements: elementsData,
          settings: {
            resolution,
            backgroundColor: canvasBackgroundColor,
          },
        };

        savedDashboard = await dashboardApi.createDashboard(dashboardData);

        const viewDashboard = confirm(`대시보드 "${title}"이 저장되었습니다!\n\n지금 확인해보시겠습니까?`);
        if (viewDashboard) {
          // Next.js 라우터로 뷰어 페이지 이동
          router.push(`/dashboard/${savedDashboard.id}`);
        }
      }
    } catch (error) {
      const errorMessage = error instanceof Error ? error.message : "알 수 없는 오류";
      alert(`대시보드 저장 중 오류가 발생했습니다.\n\n오류: ${errorMessage}\n\n관리자에게 문의하세요.`);
    }
  }, [elements, dashboardId, router, resolution, canvasBackgroundColor]);

  // 로딩 중이면 로딩 화면 표시
  if (isLoading) {
    return (
      <div className="flex h-full items-center justify-center bg-gray-50">
        <div className="text-center">
          <div className="border-primary mx-auto mb-4 h-12 w-12 animate-spin rounded-full border-4 border-t-transparent" />
          <div className="text-lg font-medium text-gray-700">대시보드 로딩 중...</div>
          <div className="mt-1 text-sm text-gray-500">잠시만 기다려주세요</div>
        </div>
      </div>
    );
  }

  return (
    <DashboardProvider>
      <div className="flex h-full flex-col bg-gray-50">
        {/* 상단 메뉴바 */}
        <DashboardTopMenu
          onSaveLayout={saveLayout}
          onClearCanvas={clearCanvas}
          onViewDashboard={dashboardId ? () => router.push(`/dashboard/${dashboardId}`) : undefined}
          dashboardTitle={dashboardTitle}
          onAddElement={addElementFromMenu}
          resolution={resolution}
          onResolutionChange={handleResolutionChange}
          currentScreenResolution={screenResolution}
          backgroundColor={canvasBackgroundColor}
          onBackgroundColorChange={setCanvasBackgroundColor}
        />

      {/* 캔버스 영역 - 해상도에 따른 크기, 중앙 정렬 */}
      <div className="flex flex-1 items-start justify-center overflow-auto bg-gray-100 p-8">
        <div
          className="relative shadow-2xl"
          style={{
            width: `${canvasConfig.width}px`,
            minHeight: `${canvasConfig.height}px`,
          }}
        >
          <DashboardCanvas
            ref={canvasRef}
            elements={elements}
            selectedElement={selectedElement}
            onCreateElement={createElement}
            onUpdateElement={updateElement}
            onRemoveElement={removeElement}
            onSelectElement={setSelectedElement}
            onConfigureElement={openConfigModal}
            backgroundColor={canvasBackgroundColor}
            canvasWidth={canvasConfig.width}
            canvasHeight={dynamicCanvasHeight}
          />
        </div>
      </div>

      {/* 요소 설정 모달 */}
      {configModalElement && (
        <>
          {configModalElement.type === "widget" && configModalElement.subtype === "list" ? (
            <ListWidgetConfigModal
              element={configModalElement}
              isOpen={true}
              onClose={closeConfigModal}
              onSave={saveListWidgetConfig}
            />
          ) : configModalElement.type === "widget" && configModalElement.subtype === "todo" ? (
            <TodoWidgetConfigModal
              element={configModalElement}
              isOpen={true}
              onClose={closeConfigModal}
              onSave={saveTodoWidgetConfig}
            />
          ) : (
            <ElementConfigModal
              element={configModalElement}
              isOpen={true}
              onClose={closeConfigModal}
              onSave={saveElementConfig}
            />
          )}
        </>
      )}
      </div>
    </DashboardProvider>
  );
}

// 요소 제목 생성 헬퍼 함수
function getElementTitle(type: ElementType, subtype: ElementSubtype): string {
  if (type === "chart") {
    switch (subtype) {
      case "bar":
        return "📊 바 차트";
      case "horizontal-bar":
        return "📊 수평 바 차트";
      case "pie":
        return "🥧 원형 차트";
      case "line":
        return "📈 꺾은선 차트";
      default:
        return "📊 차트";
    }
  } else if (type === "widget") {
    switch (subtype) {
      case "exchange":
        return "💱 환율 위젯";
      case "weather":
        return "☁️ 날씨 위젯";
      case "clock":
        return "⏰ 시계 위젯";
      case "calculator":
        return "🧮 계산기 위젯";
      case "vehicle-map":
        return "🚚 차량 위치 지도";
      case "calendar":
        return "📅 달력 위젯";
      case "driver-management":
        return "🚚 기사 관리 위젯";
      case "list":
        return "📋 리스트 위젯";
      default:
        return "🔧 위젯";
    }
  }
  return "요소";
}

// 요소 내용 생성 헬퍼 함수
function getElementContent(type: ElementType, subtype: ElementSubtype): string {
  if (type === "chart") {
    switch (subtype) {
      case "bar":
        return "바 차트가 여기에 표시됩니다";
      case "horizontal-bar":
        return "수평 바 차트가 여기에 표시됩니다";
      case "pie":
        return "원형 차트가 여기에 표시됩니다";
      case "line":
        return "꺾은선 차트가 여기에 표시됩니다";
      default:
        return "차트가 여기에 표시됩니다";
    }
  } else if (type === "widget") {
    switch (subtype) {
      case "exchange":
        return "USD: ₩1,320\nJPY: ₩900\nEUR: ₩1,450";
      case "weather":
        return "서울\n23°C\n구름 많음";
      case "clock":
        return "clock";
      case "calculator":
        return "calculator";
      case "vehicle-map":
        return "vehicle-map";
      case "calendar":
        return "calendar";
      case "driver-management":
        return "driver-management";
      case "list":
        return "list-widget";
      default:
        return "위젯 내용이 여기에 표시됩니다";
    }
  }
  return "내용이 여기에 표시됩니다";
}
