import { mdiContentSave, mdiPaletteSwatch } from '@mdi/js';
import axios from 'axios';
import Head from 'next/head';
import Link from 'next/link';
import { useRouter } from 'next/router';
import React, {
  ReactElement,
  useCallback,
  useEffect,
  useMemo,
  useState,
} from 'react';
import BaseButton from '../../components/BaseButton';
import CardBox from '../../components/CardBox';
import FormField from '../../components/FormField';
import LayoutAuthenticated from '../../layouts/Authenticated';
import SectionMain from '../../components/SectionMain';
import SectionTitleLineWithButton from '../../components/SectionTitleLineWithButton';
import { getPageTitle } from '../../config';
import { logger } from '../../lib/logger';
import type {
  CanvasElementType,
  UiElementDefault,
} from '../../types/constructor';

// Import shared element settings components
import {
  ElementSettingsTabs,
  StyleSettingsSection,
  EffectsSettingsSection,
  CommonSettingsSection,
  NavigationSettingsSection,
  TooltipSettingsSection,
  DescriptionSettingsSection,
  MediaSettingsSection,
  GallerySettingsSection,
  CarouselSettingsSection,
  useElementSettingsForm,
} from '../../components/ElementSettings';

type ElementTypeDefault = UiElementDefault & {
  element_type: string;
  name?: string;
  sort_order?: number;
};

const SETTINGS_TABS = [
  { id: 'general', label: 'General Settings' },
  { id: 'css', label: 'CSS Styles' },
  { id: 'effects', label: 'Effects' },
];

const ElementTypeDefaultDetailsPage = () => {
  const router = useRouter();
  const id = useMemo(() => {
    const routeValue = router.query.id;
    if (Array.isArray(routeValue)) return routeValue[0] || '';
    return String(routeValue || '');
  }, [router.query.id]);

  const [item, setItem] = useState<ElementTypeDefault | null>(null);
  const [sortOrder, setSortOrder] = useState(0);
  const [isActive, setIsActive] = useState(true);
  const [activeTab, setActiveTab] = useState('general');

  const [isLoading, setIsLoading] = useState(false);
  const [isSaving, setIsSaving] = useState(false);
  const [errorMessage, setErrorMessage] = useState('');
  const [successMessage, setSuccessMessage] = useState('');

  const currentElementType = (item?.element_type || '') as CanvasElementType;

  // Use shared form hook
  const form = useElementSettingsForm({ elementType: currentElementType });

  // Extract stable callback reference to avoid infinite loop
  const applySettings = form.applySettings;

  const loadItem = useCallback(async () => {
    if (!id) return;

    try {
      setIsLoading(true);
      setErrorMessage('');
      setSuccessMessage('');

      const response = await axios.get(`/element-type-defaults/${id}`);
      const nextItem: ElementTypeDefault | null = response?.data || null;

      if (!nextItem) {
        setErrorMessage('Element type default not found.');
        setItem(null);
        return;
      }

      setItem(nextItem);
      setSortOrder(Number(nextItem.sort_order || 0));
      setIsActive(Boolean(nextItem.is_active));
      applySettings(nextItem.default_settings_json);
    } catch (error: unknown) {
      const err = error as {
        response?: { data?: { message?: string } };
        message?: string;
      };
      const message =
        err?.response?.data?.message ||
        err?.message ||
        'Failed to load element type default.';
      logger.error(
        'Failed to load element type default details:',
        error instanceof Error ? error : { error },
      );
      setErrorMessage(message);
      setItem(null);
    } finally {
      setIsLoading(false);
    }
  }, [applySettings, id]);

  useEffect(() => {
    if (!router.isReady) return;
    loadItem();
  }, [loadItem, router.isReady]);

  // Extract stable callback reference for buildSettingsJson
  const buildSettingsJson = form.buildSettingsJson;

  const handleSave = useCallback(async () => {
    if (!id || !item) return;

    const defaultSettings = buildSettingsJson();

    try {
      setIsSaving(true);
      setErrorMessage('');
      setSuccessMessage('');

      await axios.put(`/element-type-defaults/${id}`, {
        id,
        data: {
          element_type: item.element_type,
          name: item.name || item.element_type,
          sort_order: Number.isFinite(Number(sortOrder))
            ? Number(sortOrder)
            : 0,
          is_active: Boolean(isActive),
          default_settings_json: defaultSettings,
        },
      });

      setSuccessMessage('Default settings saved.');
      await loadItem();
    } catch (error: unknown) {
      const err = error as {
        response?: { data?: { message?: string } };
        message?: string;
      };
      const message =
        err?.response?.data?.message ||
        err?.message ||
        'Failed to save element type defaults.';
      logger.error(
        'Failed to save element type defaults:',
        error instanceof Error ? error : { error },
      );
      setErrorMessage(message);
      setSuccessMessage('');
    } finally {
      setIsSaving(false);
    }
  }, [buildSettingsJson, id, isActive, item, loadItem, sortOrder]);

  // Extract stable callback reference for setField
  const setField = form.setField;

  // Handler for style section changes
  const handleStyleChange = useCallback(
    (prop: string, value: string) => {
      setField(prop as keyof typeof form.state, value);
    },
    [setField],
  );

  // Handler for effects section changes
  const handleEffectChange = useCallback(
    (prop: string, value: string) => {
      setField(prop as keyof typeof form.state, value);
    },
    [setField],
  );

  // Handler for common section changes
  const handleCommonChange = useCallback(
    (field: string, value: string) => {
      setField(field as keyof typeof form.state, value);
    },
    [setField],
  );

  // Handler for type-specific section changes
  const handleTypeChange = useCallback(
    (field: string, value: string | boolean) => {
      setField(field as keyof typeof form.state, value as never);
    },
    [setField],
  );

  return (
    <>
      <Head>
        <title>{getPageTitle('Element Type Defaults')}</title>
      </Head>
      <SectionMain>
        <SectionTitleLineWithButton
          icon={mdiPaletteSwatch}
          title='Element Type Defaults'
          main
        >
          {''}
        </SectionTitleLineWithButton>

        <CardBox className='mb-4'>
          <div className='flex items-center justify-between gap-2'>
            <Link href='/element-type-defaults'>
              <BaseButton
                color='info'
                outline
                label='Back to Element Type Defaults'
              />
            </Link>
            <BaseButton
              color='info'
              icon={mdiContentSave}
              label={isSaving ? 'Saving...' : 'Save'}
              disabled={isLoading || isSaving || !item}
              onClick={handleSave}
            />
          </div>
        </CardBox>

        <CardBox>
          {isLoading ? (
            <p className='text-sm text-gray-500'>Loading...</p>
          ) : !item ? (
            <p className='text-sm text-gray-500'>
              Element type default not found.
            </p>
          ) : (
            <div className='space-y-4'>
              <FormField label='Element Type'>
                <input value={item.element_type} disabled />
              </FormField>

              <FormField label='Sort Order'>
                <input
                  type='number'
                  value={sortOrder}
                  onChange={(event) =>
                    setSortOrder(Number(event.target.value || 0))
                  }
                />
              </FormField>

              <FormField label='Active'>
                <label className='inline-flex items-center gap-2 text-sm'>
                  <input
                    type='checkbox'
                    checked={isActive}
                    onChange={(event) => setIsActive(event.target.checked)}
                  />
                  Use this element type in constructor
                </label>
              </FormField>

              {/* Tabs */}
              <ElementSettingsTabs
                activeTab={activeTab}
                onTabChange={setActiveTab}
                tabs={SETTINGS_TABS}
              />

              {/* General Settings Tab */}
              {activeTab === 'general' && (
                <>
                  <CommonSettingsSection
                    label={form.state.label}
                    xPercent={form.state.xPercent}
                    yPercent={form.state.yPercent}
                    appearDelaySec={form.state.appearDelaySec}
                    appearDurationSec={form.state.appearDurationSec}
                    onChange={handleCommonChange}
                    showLabel={false}
                  />

                  {/* Type-specific sections */}
                  {form.isNavigationType && (
                    <NavigationSettingsSection
                      iconUrl={form.state.iconUrl}
                      navLabel={form.state.navLabel}
                      navLabelFontFamily={form.state.navLabelFontFamily}
                      navType={form.state.navType}
                      navDisabled={form.state.navDisabled}
                      targetPageId={form.state.targetPageId}
                      targetPageSlug={form.state.targetPageSlug}
                      transitionVideoUrl={form.state.transitionVideoUrl}
                      transitionReverseMode={form.state.transitionReverseMode}
                      reverseVideoUrl={form.state.reverseVideoUrl}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}

                  {form.isTooltipType && (
                    <TooltipSettingsSection
                      iconUrl={form.state.iconUrl}
                      tooltipTitle={form.state.tooltipTitle}
                      tooltipText={form.state.tooltipText}
                      tooltipTitleFontFamily={form.state.tooltipTitleFontFamily}
                      tooltipTextFontFamily={form.state.tooltipTextFontFamily}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}

                  {form.isDescriptionType && (
                    <DescriptionSettingsSection
                      iconUrl={form.state.iconUrl}
                      descriptionTitle={form.state.descriptionTitle}
                      descriptionText={form.state.descriptionText}
                      descriptionTitleFontSize={
                        form.state.descriptionTitleFontSize
                      }
                      descriptionTextFontSize={
                        form.state.descriptionTextFontSize
                      }
                      descriptionTitleFontFamily={
                        form.state.descriptionTitleFontFamily
                      }
                      descriptionTextFontFamily={
                        form.state.descriptionTextFontFamily
                      }
                      descriptionTitleColor={form.state.descriptionTitleColor}
                      descriptionTextColor={form.state.descriptionTextColor}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}

                  {form.isGalleryType && (
                    <GallerySettingsSection
                      galleryCards={form.state.galleryCards}
                      galleryTitleFontFamily={form.state.galleryTitleFontFamily}
                      galleryTextFontFamily={form.state.galleryTextFontFamily}
                      onAddCard={form.addGalleryCard}
                      onRemoveCard={form.removeGalleryCard}
                      onUpdateCard={form.updateGalleryCard}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}

                  {form.isCarouselType && (
                    <CarouselSettingsSection
                      carouselPrevIconUrl={form.state.carouselPrevIconUrl}
                      carouselNextIconUrl={form.state.carouselNextIconUrl}
                      carouselCaptionFontFamily={form.state.carouselCaptionFontFamily}
                      carouselSlides={form.state.carouselSlides}
                      onAddSlide={form.addCarouselSlide}
                      onRemoveSlide={form.removeCarouselSlide}
                      onUpdateSlide={form.updateCarouselSlide}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}

                  {form.isMediaType && (
                    <MediaSettingsSection
                      elementType={
                        currentElementType as 'video_player' | 'audio_player'
                      }
                      mediaUrl={form.state.mediaUrl}
                      mediaAutoplay={form.state.mediaAutoplay}
                      mediaLoop={form.state.mediaLoop}
                      mediaMuted={form.state.mediaMuted}
                      onChange={handleTypeChange}
                      context='global'
                    />
                  )}
                </>
              )}

              {/* CSS Styles Tab */}
              {activeTab === 'css' && (
                <CardBox className='border border-gray-200 dark:border-dark-700'>
                  <StyleSettingsSection
                    values={form.getStyleValues()}
                    onChange={handleStyleChange}
                  />
                </CardBox>
              )}

              {/* Effects Tab */}
              {activeTab === 'effects' && (
                <CardBox className='border border-gray-200 dark:border-dark-700'>
                  <EffectsSettingsSection
                    values={form.getEffectValues()}
                    onChange={handleEffectChange}
                  />
                </CardBox>
              )}

              {errorMessage && (
                <p className='text-sm text-red-600'>{errorMessage}</p>
              )}
              {successMessage && (
                <p className='text-sm text-green-600'>{successMessage}</p>
              )}
            </div>
          )}
        </CardBox>
      </SectionMain>
    </>
  );
};

ElementTypeDefaultDetailsPage.getLayout = function getLayout(
  page: ReactElement,
) {
  return (
    <LayoutAuthenticated permission='UPDATE_PAGE_ELEMENTS'>
      {page}
    </LayoutAuthenticated>
  );
};

export default ElementTypeDefaultDetailsPage;
