'use client';

import { useState, useEffect, ChangeEvent, FormEvent } from 'react';
import Image from 'next/image';
import { CalculatorConfig, CalculatorValues, CalculationResults } from '@/lib/calculator-types';
import { getCalculator } from '@/lib/calculator-registry';

type CalculatorEngineProps = {
  calculatorId: string;
  chatId?: string | null;
  onBack?: () => void;
};

const toNum = (str: string): number => {
  const n = parseFloat(str.replace(',', '.'));
  return isNaN(n) ? 0 : n;
};

const InputNumber = ({
  id,
  label,
  value,
  onChange,
  gridCols = 2,
}: {
  id: string;
  label: string;
  value: string;
  onChange: (v: string) => void;
  gridCols?: 1 | 2;
}) => {
  return (
    <div className={gridCols === 2 ? '' : 'col-span-2'}>
      <div className="relative mt-6">
        <input
          id={id}
          type="number"
          value={value}
          onChange={(e) => onChange(e.target.value)}
          placeholder=" "
          className={`
            peer
            h-10 w-full
            bg-gray-700
            border-2 border-gray-600
            rounded-md
            text-gray-200
            placeholder-transparent
            pl-3
            focus:outline-none focus:border-sky-500
            appearance-none
          `}
        />
        <label
          htmlFor={id}
          className={`
            absolute left-3
            -top-5
            text-gray-400
            transition-all
            text-xs sm:text-sm md:text-base lg:text-lg
            peer-placeholder-shown:top-2
            peer-placeholder-shown:text-gray-500
            peer-placeholder-shown:text-sm sm:peer-placeholder-shown:text-base md:peer-placeholder-shown:text-lg
            peer-focus:-top-5
            peer-focus:text-gray-200
            peer-focus:text-xs sm:peer-focus:text-sm md:peer-focus:text-base lg:peer-focus:text-lg
          `}
        >
          {label}
        </label>
      </div>
    </div>
  );
};

const InputText = ({
  id,
  label,
  value,
  onChange,
}: {
  id: string;
  label: string;
  value: string;
  onChange: (v: string) => void;
}) => {
  return (
    <div className="relative mt-6 col-span-2">
      <input
        id={id}
        type="text"
        value={value}
        onChange={(e) => onChange(e.target.value)}
        placeholder=" "
        className={`
          peer
          h-10 w-full
          bg-gray-700
          border-2 border-gray-600
          rounded-md
          text-gray-200
          placeholder-transparent
          pl-3
          focus:outline-none focus:border-sky-500
          appearance-none
        `}
      />
      <label
        htmlFor={id}
        className={`
          absolute left-3
          -top-5
          text-gray-400
          transition-all
          text-xs sm:text-sm md:text-base lg:text-lg
          peer-placeholder-shown:top-2
          peer-placeholder-shown:text-gray-500
          peer-placeholder-shown:text-sm sm:peer-placeholder-shown:text-base md:peer-placeholder-shown:text-lg
          peer-focus:-top-5
          peer-focus:text-gray-200
          peer-focus:text-xs sm:peer-focus:text-sm md:peer-focus:text-base lg:peer-focus:text-lg
        `}
      >
        {label}
      </label>
    </div>
  );
};

const CostBlock = ({
  title,
  value,
  highlight = false,
}: {
  title: string;
  value: number;
  highlight?: boolean;
}) => {
  const displayValue = isNaN(value) || !isFinite(value) ? 0 : value;
  return (
    <div
      className={`
        p-2
        ${highlight ? 'bg-gray-600 font-semibold' : 'bg-gray-700'}
        text-gray-200
        rounded
      `}
    >
      {title}: {displayValue.toFixed(1)} руб
    </div>
  );
};

export default function CalculatorEngine({
  calculatorId,
  chatId: externalChatId,
  onBack,
}: CalculatorEngineProps) {
  const [config, setConfig] = useState<CalculatorConfig | null>(null);
  const [values, setValues] = useState<CalculatorValues>({});
  const [photoFile, setPhotoFile] = useState<File | null>(null);
  const [chatId, setChatId] = useState<string | null>(null);

  // Загружаем конфигурацию калькулятора
  useEffect(() => {
    const calculatorConfig = getCalculator(calculatorId);
    if (calculatorConfig) {
      setConfig(calculatorConfig);
      // Инициализируем значения по умолчанию
      const initialValues: CalculatorValues = {};
      calculatorConfig.fields.forEach((field) => {
        initialValues[field.id] = field.defaultValue || '';
      });
      setValues(initialValues);
    }
  }, [calculatorId]);

  // Получаем chat_id из URL или пропсов
  useEffect(() => {
    if (externalChatId) {
      setChatId(externalChatId);
    } else {
      const params = new URLSearchParams(window.location.search);
      const id = params.get('chat_id');
      if (id) {
        setChatId(id);
      }
    }
  }, [externalChatId]);

  if (!config) {
    return (
      <div className="max-w-xl mx-auto p-6 bg-gray-800 text-gray-200 rounded-lg">
        <p>Калькулятор не найден</p>
        {onBack && (
          <button
            onClick={onBack}
            className="mt-4 px-4 py-2 bg-sky-500 hover:bg-sky-600 text-white rounded"
          >
            Назад к меню
          </button>
        )}
      </div>
    );
  }

  // Вычисляем все значения как числа
  const numValues: Record<string, number> = {};
  Object.keys(values).forEach((key) => {
    if (config.fields.find((f) => f.id === key && f.type !== 'file' && f.type !== 'text')) {
      numValues[key] = toNum(values[key]);
    } else if (config.fields.find((f) => f.id === key && f.type === 'text')) {
      numValues[key] = values[key] as any; // Для текстовых полей сохраняем строку
    }
  });

  // Выполняем расчеты
  const results: CalculationResults = {
    steps: {},
    subtotals: {},
    additional: {},
  };

  // Шаги расчета
  config.calculationSteps.forEach((step) => {
    results.steps[step.id] = step.formula(numValues);
  });

  // Подитоги
  config.subtotals.forEach((subtotal) => {
    results.subtotals[subtotal.id] = subtotal.formula(numValues, results.steps);
  });

  // Дополнительные расчеты (нужно делать последовательно, так как некоторые зависят от других)
  if (config.additionalCalculations) {
    config.additionalCalculations.forEach((calc) => {
      results.additional![calc.id] = calc.formula(numValues, results.steps, results.subtotals, results.additional);
    });
  }

  const handleFieldChange = (fieldId: string, newValue: string) => {
    setValues((prev) => ({ ...prev, [fieldId]: newValue }));
  };

  const handlePhotoChange = (e: ChangeEvent<HTMLInputElement>) => {
    if (e.target.files && e.target.files[0]) {
      setPhotoFile(e.target.files[0]);
    } else {
      setPhotoFile(null);
    }
  };

  const handleSubmit = async (e: FormEvent) => {
    e.preventDefault();
    if (!chatId) {
      alert('❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.');
      return;
    }

    const formData = new FormData();
    formData.append('chat_id', chatId);
    formData.append('calculator_id', config.id);
    formData.append('calculator_name', config.name);

    // Добавляем все поля
    config.fields.forEach((field) => {
      if (field.type !== 'file') {
        const value = values[field.id] || '';
        if (field.type === 'number') {
          formData.append(field.id, toNum(value).toString());
        } else {
          formData.append(field.id, value);
        }
      }
    });

    // Добавляем результаты расчетов
    Object.keys(results.steps).forEach((key) => {
      formData.append(`step_${key}`, results.steps[key].toString());
    });
    Object.keys(results.subtotals).forEach((key) => {
      formData.append(`subtotal_${key}`, results.subtotals[key].toString());
    });
    if (results.additional) {
      Object.keys(results.additional).forEach((key) => {
        formData.append(`additional_${key}`, results.additional![key].toString());
      });
    }

    // Добавляем фото если есть
    if (photoFile) {
      formData.append('photo', photoFile);
    }

    // Формируем данные для форматирования сообщения
    const allValues: Record<string, string | number> = {};
    Object.keys(values).forEach((key) => {
      const field = config.fields.find((f) => f.id === key);
      if (field && field.type === 'number') {
        allValues[key] = toNum(values[key]);
      } else {
        allValues[key] = values[key];
      }
    });

    // Форматируем сообщение для Telegram
    const telegramMessage = config.formatTelegramMessage
      ? config.formatTelegramMessage(allValues, results.steps, results.subtotals, results.additional || {})
      : JSON.stringify({ values, results }, null, 2);

    formData.append('telegram_message', telegramMessage);

    try {
      // Для локальной разработки используем localhost, для продакшена - api-dosoap.duckdns.org
      const isLocalhost = typeof window !== 'undefined' && window.location.hostname === 'localhost';
      const apiUrl = isLocalhost
        ? 'http://localhost:3001/api/submit'
        : 'https://api-dosoap.duckdns.org/api/submit';
      
      const res = await fetch(apiUrl, {
        method: 'POST',
        body: formData,
      });

      if (res.ok) {
        alert('✅ Расчёт успешно отправлен в Telegram!');
        // Сброс формы
        const resetValues: CalculatorValues = {};
        config.fields.forEach((field) => {
          resetValues[field.id] = field.defaultValue || '';
        });
        setValues(resetValues);
        setPhotoFile(null);
        window.scrollTo({ top: 0, behavior: 'smooth' });
      } else {
        const text = await res.text();
        alert(`Ошибка при отправке: ${text}`);
      }
    } catch (err) {
      console.error(err);
      alert('Ошибка сети при отправке расчёта');
    }
  };

  // Находим поле для фото
  const photoField = config.fields.find((f) => f.type === 'file');
  const textFields = config.fields.filter((f) => f.type === 'text');
  
  // Группируем числовые поля по группам
  const numberFields = config.fields.filter((f) => f.type === 'number');
  const fieldsByGroup: Record<string, typeof numberFields> = {};
  const ungroupedFields: typeof numberFields = [];
  
  numberFields.forEach((field) => {
    if (field.groupName) {
      if (!fieldsByGroup[field.groupName]) {
        fieldsByGroup[field.groupName] = [];
      }
      fieldsByGroup[field.groupName].push(field);
    } else {
      ungroupedFields.push(field);
    }
  });

  // Определяем порядок групп на основе порядка полей в конфигурации
  const groupOrder: string[] = [];
  const seenGroups = new Set<string>();
  
  numberFields.forEach((field) => {
    if (field.groupName && !seenGroups.has(field.groupName)) {
      groupOrder.push(field.groupName);
      seenGroups.add(field.groupName);
    }
  });
  
  // Добавляем группы, которые не были найдены (на всякий случай)
  Object.keys(fieldsByGroup).forEach((groupName) => {
    if (!seenGroups.has(groupName)) {
      groupOrder.push(groupName);
    }
  });

  return (
    <form
      onSubmit={handleSubmit}
      className="
        max-w-xl mx-auto p-6 space-y-6
        bg-gray-800 text-gray-200
        rounded-lg shadow-lg
      "
    >
      {/* Кнопка назад */}
      {onBack && (
        <button
          type="button"
          onClick={onBack}
          className="mb-4 px-4 py-2 bg-gray-600 hover:bg-gray-500 text-gray-200 rounded"
        >
          ← Назад к меню
        </button>
      )}

      {/* Логотип */}
      <div className="flex justify-center">
        <Image
          src="/logo.svg"
          alt="Logo"
          width={150}
          height={50}
          className="mx-auto w-64 md:w-96 lg:w-112 h-auto"
        />
      </div>

      {chatId === null && (
        <div className="bg-yellow-800 p-2 text-yellow-200 font-semibold rounded">
          ❗ Не найден chat_id. Откройте калькулятор через Telegram-бота.
        </div>
      )}

      {/* Текстовые поля */}
      {textFields.map((field) => (
        <InputText
          key={field.id}
          id={field.id}
          label={field.label}
          value={values[field.id] || ''}
          onChange={(value) => handleFieldChange(field.id, value)}
        />
      ))}

      {/* Поле для фото */}
      {photoField && (
        <>
          <label className="flex flex-col gap-1 col-span-2">
            <span className="text-gray-300">{photoField.label}</span>
            <input
              type="file"
              accept={photoField.accept || 'image/*'}
              onChange={handlePhotoChange}
              className="
                bg-gray-700
                text-gray-200
                rounded-md
                border border-gray-600
                p-2
                focus:outline-none focus:border-sky-500
              "
            />
          </label>
          {photoFile && (
            <img
              src={URL.createObjectURL(photoFile)}
              alt="Предпросмотр"
              className="w-32 h-32 object-cover rounded-lg border border-sky-400"
            />
          )}
        </>
      )}

      {/* Группированные поля с расчетами между ними */}
      {groupOrder.map((groupName) => {
        const groupFields = fieldsByGroup[groupName] || [];
        const firstField = groupFields[0];
        const showStepId = firstField?.showStepAfter;
        
        return (
          <div key={groupName} className="space-y-4">
            {/* Поля группы */}
            <div className="grid grid-cols-2 gap-4">
              {groupFields.map((field) => (
                <InputNumber
                  key={field.id}
                  id={field.id}
                  label={field.label}
                  value={values[field.id] || ''}
                  onChange={(value) => handleFieldChange(field.id, value)}
                  gridCols={field.gridCols}
                />
              ))}
            </div>
            
            {/* Блок расчета после группы */}
            {showStepId && (
              <CostBlock
                title={config.calculationSteps.find((s) => s.id === showStepId)?.name || ''}
                value={results.steps[showStepId] || 0}
              />
            )}
          </div>
        );
      })}

      {/* Несгруппированные поля */}
      {ungroupedFields.length > 0 && (
        <div className="space-y-4">
          <div className="grid grid-cols-2 gap-4">
            {ungroupedFields.map((field) => (
              <InputNumber
                key={field.id}
                id={field.id}
                label={field.label}
                value={values[field.id] || ''}
                onChange={(value) => handleFieldChange(field.id, value)}
                gridCols={field.gridCols}
              />
            ))}
          </div>
        </div>
      )}

      {/* Подитоги */}
      {config.subtotals.map((subtotal) => (
        <CostBlock
          key={subtotal.id}
          title={subtotal.name}
          value={results.subtotals[subtotal.id]}
          highlight={subtotal.highlight}
        />
      ))}

      {/* Дополнительные расчеты */}
      {config.additionalCalculations?.map((calc) => (
        <CostBlock
          key={calc.id}
          title={calc.name}
          value={results.additional![calc.id]}
        />
      ))}

      {/* Кнопка отправки */}
      <button
        type="submit"
        className="
          w-full
          py-2
          rounded-md
          bg-sky-500 hover:bg-sky-600
          text-gray-100 font-semibold
          focus:outline-none focus:ring focus:ring-offset-2 focus:ring-sky-500 focus:ring-opacity-60
        "
      >
        Отправить расчёт в Telegram
      </button>
    </form>
  );
}

