import React from 'react';
import { useNavigate, useParams } from 'react-router-dom';
import { useTranslation } from 'react-i18next';
import { Image as ImageIcon, RefreshCcw, UploadCloud, Trash2, ChevronDown, Save, Droplets, Lock } from 'lucide-react';
import { YStack, XStack } from '@tamagui/stacks';
import { SizableText as Text } from '@tamagui/text';
import { Pressable } from '@tamagui/react-native-web-lite';
import { MobileShell, HeaderActionButton } from './components/MobileShell';
import { MobileCard, CTAButton, SkeletonCard } from './components/Primitives';
import { TenantEvent, getEvent, updateEvent, getTenantFonts, TenantFont, WatermarkSettings, trackOnboarding } from '../api';
import { isAuthError } from '../auth/tokens';
import { ApiError, getApiErrorMessage } from '../lib/apiError';
import { isBrandingAllowed } from '../lib/events';
import { MobileSheet } from './components/Sheet';
import toast from 'react-hot-toast';
import { adminPath } from '../constants';
import { useBackNavigation } from './hooks/useBackNavigation';
import { ADMIN_COLORS, ADMIN_GRADIENTS, useAdminTheme } from './theme';

type BrandingForm = {
  primary: string;
  accent: string;
  headingFont: string;
  bodyFont: string;
  logoDataUrl: string;
};

type WatermarkPosition =
  | 'top-left'
  | 'top-center'
  | 'top-right'
  | 'middle-left'
  | 'center'
  | 'middle-right'
  | 'bottom-left'
  | 'bottom-center'
  | 'bottom-right';

type WatermarkForm = {
  mode: 'base' | 'custom' | 'off';
  assetPath: string;
  assetDataUrl: string;
  position: WatermarkPosition;
  opacity: number;
  scale: number;
  padding: number;
  offsetX: number;
  offsetY: number;
};

type TabKey = 'branding' | 'watermark';

export default function MobileBrandingPage() {
  const { slug: slugParam } = useParams<{ slug?: string }>();
  const slug = slugParam ?? null;
  const navigate = useNavigate();
  const { t } = useTranslation('management');
  const { textStrong, muted, subtle, border, primary, accentSoft, danger, surfaceMuted, surface } = useAdminTheme();

  const [event, setEvent] = React.useState<TenantEvent | null>(null);
  const [form, setForm] = React.useState<BrandingForm>({
    primary: ADMIN_COLORS.primary,
    accent: ADMIN_COLORS.accent,
    headingFont: '',
    bodyFont: '',
    logoDataUrl: '',
  });
  const [watermarkForm, setWatermarkForm] = React.useState<WatermarkForm>({
    mode: 'base',
    assetPath: '',
    assetDataUrl: '',
    position: 'bottom-right',
    opacity: 0.25,
    scale: 0.2,
    padding: 16,
    offsetX: 0,
    offsetY: 0,
  });
  const [activeTab, setActiveTab] = React.useState<TabKey>('branding');
  const [loading, setLoading] = React.useState(true);
  const [saving, setSaving] = React.useState(false);
  const [error, setError] = React.useState<string | null>(null);
  const [showFontsSheet, setShowFontsSheet] = React.useState(false);
  const [fontField, setFontField] = React.useState<'heading' | 'body'>('heading');
  const back = useBackNavigation(slug ? adminPath(`/mobile/events/${slug}`) : adminPath('/mobile/events'));
  const [fonts, setFonts] = React.useState<TenantFont[]>([]);
  const [fontsLoading, setFontsLoading] = React.useState(false);
  const [fontsLoaded, setFontsLoaded] = React.useState(false);

  React.useEffect(() => {
    if (!slug) return;
    (async () => {
      setLoading(true);
      try {
        const data = await getEvent(slug);
        setEvent(data);
        setForm(extractBranding(data));
        setWatermarkForm(extractWatermark(data));
        setError(null);
      } catch (err) {
        if (!isAuthError(err)) {
          setError(getApiErrorMessage(err, t('events.errors.loadFailed', 'Branding konnte nicht geladen werden.')));
        }
      } finally {
        setLoading(false);
      }
    })();
  }, [slug, t]);

  React.useEffect(() => {
    if (!showFontsSheet || fontsLoaded) return;
    setFontsLoading(true);
    getTenantFonts()
      .then((data) => setFonts(data ?? []))
      .catch(() => undefined)
      .finally(() => {
        setFontsLoading(false);
        setFontsLoaded(true);
      });
  }, [showFontsSheet, fontsLoaded]);

  const previewTitle = event ? renderName(event.name) : t('events.placeholders.untitled', 'Unbenanntes Event');
  const previewHeadingFont = form.headingFont || 'Fraunces';
  const previewBodyFont = form.bodyFont || 'Manrope';
  const watermarkAllowed = event?.package?.watermark_allowed !== false;
  const brandingAllowed = isBrandingAllowed(event ?? null);
  const watermarkLocked = watermarkAllowed && !brandingAllowed;

  async function handleSave() {
    if (!event?.slug) return;
    const eventTypeId = event.event_type_id ?? event.event_type?.id ?? null;
    if (!eventTypeId) {
      const msg = t('events.errors.missingType', 'Event type fehlt. Speichere das Event erneut im Admin.');
      setError(msg);
      toast.error(msg);
      return;
    }
    setSaving(true);
    setError(null);
    try {
      if (watermarkAllowed && brandingAllowed && watermarkForm.mode === 'custom' && !watermarkForm.assetDataUrl && !watermarkForm.assetPath) {
        const msg = t('events.watermark.errors.noAsset', 'Bitte lade zuerst ein Wasserzeichen hoch.');
        setError(msg);
        setActiveTab('watermark');
        setSaving(false);
        return;
      }

      const payload = {
        name: typeof event.name === 'string' ? event.name : renderName(event.name),
        slug: event.slug,
        event_type_id: eventTypeId,
        event_date: event.event_date ?? undefined,
        status: event.status ?? 'draft',
        is_active: event.is_active ?? undefined,
      };
      const settings = { ...(event.settings ?? {}) };
      settings.branding = {
        ...(typeof settings.branding === 'object' ? (settings.branding as Record<string, unknown>) : {}),
        primary_color: form.primary,
        accent_color: form.accent,
        heading_font: form.headingFont,
        body_font: form.bodyFont,
        typography: {
          ...(typeof (settings.branding as Record<string, unknown> | undefined)?.typography === 'object'
            ? ((settings.branding as Record<string, unknown>).typography as Record<string, unknown>)
            : {}),
          heading: form.headingFont,
          body: form.bodyFont,
        },
        palette: {
          ...(typeof (settings.branding as Record<string, unknown> | undefined)?.palette === 'object'
            ? ((settings.branding as Record<string, unknown>).palette as Record<string, unknown>)
            : {}),
          primary: form.primary,
          secondary: form.accent,
        },
        logo_data_url: form.logoDataUrl || null,
        logo: form.logoDataUrl
          ? {
              mode: 'upload',
              value: form.logoDataUrl,
              position: 'center',
              size: 'm',
            }
          : null,
      };
      const watermarkPayload = buildWatermarkPayload(watermarkForm, watermarkAllowed, brandingAllowed);
      if (watermarkPayload) {
        settings.watermark = watermarkPayload;
      }
      const updated = await updateEvent(event.slug, {
        ...payload,
        settings,
      });
      setEvent(updated);
      void trackOnboarding('branding_configured', { event_id: updated.id });
      toast.success(t('events.branding.saveSuccess', 'Branding gespeichert'));
    } catch (err) {
      if (!isAuthError(err)) {
        let message = getApiErrorMessage(err, t('events.errors.saveFailed', 'Branding konnte nicht gespeichert werden.'));
        if (err instanceof ApiError && err.meta?.errors && typeof err.meta.errors === 'object') {
          const allErrors = Object.values(err.meta.errors as Record<string, unknown>)
            .flat()
            .filter((val): val is string => typeof val === 'string');
          if (allErrors.length) {
            message = allErrors.join('\n');
          }
        }
        setError(message);
        toast.error(message, { duration: 5000 });
      }
    } finally {
      setSaving(false);
    }
  }

  function handleReset() {
    if (event) {
      setForm(extractBranding(event));
      setWatermarkForm(extractWatermark(event));
    }
  }

  function renderWatermarkTab() {
    const policyLabel = watermarkAllowed ? 'basic' : 'none';
    const disabled = !watermarkAllowed;
    const controlsLocked = watermarkLocked || disabled;
    const mode = controlsLocked ? 'base' : watermarkForm.mode;

    return (
      <>
        <MobileCard space="$3">
          <Text fontSize="$sm" fontWeight="700" color={textStrong}>
            {t('events.watermark.previewTitle', 'Watermark Preview')}
          </Text>
          <WatermarkPreview
            position={watermarkForm.position}
            scale={watermarkForm.scale}
            opacity={watermarkForm.opacity}
            padding={watermarkForm.padding}
            offsetX={watermarkForm.offsetX}
            offsetY={watermarkForm.offsetY}
          />
        </MobileCard>

        {disabled ? (
          <InfoBadge
            icon={<Lock size={16} color={danger} />}
            text={t('events.watermark.lockedDisabled', 'Kein Wasserzeichen in diesem Paket.')}
            tone="danger"
          />
        ) : null}

        {watermarkLocked ? (
          <InfoBadge
            icon={<Lock size={16} color={textStrong} />}
            text={t('events.watermark.lockedBranding', 'Custom-Wasserzeichen ist im aktuellen Paket gesperrt. Standard wird genutzt.')}
          />
        ) : null}

        <MobileCard space="$3">
          <Text fontSize="$md" fontWeight="800" color={textStrong}>
            {t('events.watermark.title', 'Wasserzeichen')}
          </Text>

          <InputField
            label={t('events.watermark.mode', 'Modus')}
            value={mode}
            onChange={(value) => {
              if (controlsLocked) return;
              if (value === 'custom' || value === 'base' || value === 'off') {
                setWatermarkForm((prev) => ({ ...prev, mode: value as WatermarkForm['mode'] }));
              }
            }}
            onPicker={() => undefined}
          >
            <select
              value={mode}
              disabled={controlsLocked}
              onChange={(event) => setWatermarkForm((prev) => ({ ...prev, mode: event.target.value as WatermarkForm['mode'] }))}
              style={{ width: '100%', height: 40, border: 'none', outline: 'none', background: 'transparent' }}
            >
              <option value="base">{t('events.watermark.modeBase', 'Basis')}</option>
              <option value="custom" disabled={watermarkLocked}>
                {t('events.watermark.modeCustom', 'Eigenes Wasserzeichen')}
              </option>
              <option value="off" disabled={policyLabel === 'basic'}>
                {t('events.watermark.modeOff', 'Deaktiviert')}
              </option>
            </select>
          </InputField>

          {mode === 'custom' && !controlsLocked ? (
            <YStack space="$2">
              <Text fontSize="$sm" fontWeight="700" color={textStrong}>
                {t('events.watermark.upload', 'Wasserzeichen hochladen')}
              </Text>
              <Pressable onPress={() => document.getElementById('watermark-upload-input')?.click()}>
                <XStack
                  alignItems="center"
                  space="$2"
                  paddingHorizontal="$3.5"
                  paddingVertical="$2.5"
                  borderRadius={12}
                  borderWidth={1}
                  borderColor={border}
                  backgroundColor={surface}
                >
                  <UploadCloud size={18} color={primary} />
                  <Text fontSize="$sm" color={primary} fontWeight="700">
                    {watermarkForm.assetPath
                      ? t('events.watermark.replace', 'Wasserzeichen ersetzen')
                      : t('events.watermark.uploadCta', 'PNG/SVG/JPG (max. 3 MB)')}
                  </Text>
                </XStack>
              </Pressable>
              <input
                id="watermark-upload-input"
                type="file"
                accept="image/png,image/jpeg,image/webp,image/svg+xml"
                style={{ display: 'none' }}
                onChange={(event) => {
                  const file = event.target.files?.[0];
                  if (!file) return;
                  if (file.size > 3 * 1024 * 1024) {
                    setError(t('events.watermark.errors.fileTooLarge', 'Wasserzeichen muss kleiner als 3 MB sein.'));
                    return;
                  }
                  const reader = new FileReader();
                  reader.onload = () => {
                    const result = typeof reader.result === 'string' ? reader.result : '';
                    setWatermarkForm((prev) => ({ ...prev, assetDataUrl: result, assetPath: '' }));
                    setError(null);
                  };
                  reader.readAsDataURL(file);
                }}
              />
              <Text fontSize="$xs" color={muted}>
                {t('events.watermark.uploadHint', 'PNG mit transparenter Fläche empfohlen.')}
              </Text>
            </YStack>
          ) : null}
        </MobileCard>

        <MobileCard space="$3">
          <Text fontSize="$md" fontWeight="800" color={textStrong}>
            {t('events.watermark.placement', 'Position & Größe')}
          </Text>
          <PositionGrid
            value={watermarkForm.position}
            onChange={(next) => setWatermarkForm((prev) => ({ ...prev, position: next }))}
            disabled={controlsLocked}
          />
          <LabeledSlider
            label={t('events.watermark.size', 'Größe')}
            value={Math.round(watermarkForm.scale * 100)}
            min={5}
            max={60}
            step={1}
            onChange={(value) => setWatermarkForm((prev) => ({ ...prev, scale: value / 100 }))}
            disabled={controlsLocked}
          />
          <LabeledSlider
            label={t('events.watermark.opacity', 'Transparenz')}
            value={Math.round(watermarkForm.opacity * 100)}
            min={10}
            max={80}
            step={5}
            onChange={(value) => setWatermarkForm((prev) => ({ ...prev, opacity: value / 100 }))}
            disabled={controlsLocked}
          />
          <LabeledSlider
            label={t('events.watermark.padding', 'Abstand zum Rand')}
            value={watermarkForm.padding}
            min={0}
            max={80}
            step={2}
            onChange={(value) => setWatermarkForm((prev) => ({ ...prev, padding: value }))}
            disabled={controlsLocked}
          />
          <LabeledSlider
            label={t('events.watermark.offset', 'Feinjustierung')}
            value={watermarkForm.offsetX}
            min={-30}
            max={30}
            step={1}
            onChange={(value) => setWatermarkForm((prev) => ({ ...prev, offsetX: value }))}
            disabled={controlsLocked}
            suffix={t('events.watermark.offsetX', 'X-Achse')}
          />
          <LabeledSlider
            label={t('events.watermark.offsetY', 'Y-Achse')}
            value={watermarkForm.offsetY}
            min={-30}
            max={30}
            step={1}
            onChange={(value) => setWatermarkForm((prev) => ({ ...prev, offsetY: value }))}
            disabled={controlsLocked}
          />
        </MobileCard>
      </>
    );
  }

  return (
    <MobileShell
      activeTab="home"
      title={t('events.branding.titleShort', 'Branding')}
      onBack={back}
      headerActions={
        <HeaderActionButton onPress={() => handleSave()} ariaLabel={t('common.save', 'Save')}>
          <Save size={18} color={primary} />
        </HeaderActionButton>
      }
    >
      {error ? (
        <MobileCard>
          <Text fontWeight="700" color={danger}>
            {error}
          </Text>
        </MobileCard>
      ) : null}

      <MobileCard space="$2">
        <XStack space="$2">
          <TabButton label={t('events.branding.titleShort', 'Branding')} active={activeTab === 'branding'} onPress={() => setActiveTab('branding')} />
          <TabButton label={t('events.watermark.tab', 'Wasserzeichen')} active={activeTab === 'watermark'} onPress={() => setActiveTab('watermark')} />
        </XStack>
      </MobileCard>

      {activeTab === 'branding' ? (
        <>
          <MobileCard space="$3">
            <Text fontSize="$sm" fontWeight="700" color={textStrong}>
              {t('events.branding.previewTitle', 'Guest App Preview')}
            </Text>
            <YStack borderRadius={16} borderWidth={1} borderColor={border} backgroundColor={surfaceMuted} padding="$3" space="$2" alignItems="center">
              <YStack width="100%" borderRadius={12} backgroundColor={surface} borderWidth={1} borderColor={border} overflow="hidden">
                <YStack backgroundColor={form.primary} height={64} />
                <YStack padding="$3" space="$1.5">
                  <Text fontSize="$md" fontWeight="800" color={textStrong} style={{ fontFamily: previewHeadingFont }}>
                    {previewTitle}
                  </Text>
                  <Text fontSize="$sm" color={muted} style={{ fontFamily: previewBodyFont }}>
                    {t('events.branding.previewSubtitle', 'Aktuelle Farben & Schriften')}
                  </Text>
                  <XStack space="$2" marginTop="$1">
                    <ColorSwatch color={form.primary} label={t('events.branding.primary', 'Primary')} />
                    <ColorSwatch color={form.accent} label={t('events.branding.accent', 'Accent')} />
                  </XStack>
                </YStack>
              </YStack>
            </YStack>
          </MobileCard>

          <MobileCard space="$3">
            <Text fontSize="$md" fontWeight="800" color={textStrong}>
              {t('events.branding.colors', 'Colors')}
            </Text>
            <ColorField
              label={t('events.branding.primary', 'Primary Color')}
              value={form.primary}
              onChange={(value) => setForm((prev) => ({ ...prev, primary: value }))}
            />
            <ColorField
              label={t('events.branding.accent', 'Accent Color')}
              value={form.accent}
              onChange={(value) => setForm((prev) => ({ ...prev, accent: value }))}
            />
          </MobileCard>

          <MobileCard space="$3">
            <Text fontSize="$md" fontWeight="800" color={textStrong}>
              {t('events.branding.fonts', 'Fonts')}
            </Text>
            <InputField
              label={t('events.branding.headingFont', 'Headline Font')}
              value={form.headingFont}
              placeholder={t('events.branding.headingFontPlaceholder', 'SF Pro Display')}
              onChange={(value) => setForm((prev) => ({ ...prev, headingFont: value }))}
              onPicker={() => {
                setFontField('heading');
                setShowFontsSheet(true);
              }}
            />
            <InputField
              label={t('events.branding.bodyFont', 'Body Font')}
              value={form.bodyFont}
              placeholder={t('events.branding.bodyFontPlaceholder', 'SF Pro Text')}
              onChange={(value) => setForm((prev) => ({ ...prev, bodyFont: value }))}
              onPicker={() => {
                setFontField('body');
                setShowFontsSheet(true);
              }}
            />
          </MobileCard>

          <MobileCard space="$3">
            <Text fontSize="$md" fontWeight="800" color={textStrong}>
              {t('events.branding.logo', 'Logo')}
            </Text>
            <YStack
              borderRadius={14}
              borderWidth={1}
              borderColor={border}
              backgroundColor={surfaceMuted}
              padding="$3"
              alignItems="center"
              justifyContent="center"
              space="$2"
            >
              {form.logoDataUrl ? (
                <>
                  <img
                    src={form.logoDataUrl}
                    alt={t('events.branding.logoAlt', 'Logo')}
                    style={{ maxHeight: 80, maxWidth: '100%', objectFit: 'contain' }}
                  />
                  <XStack space="$2">
                    <CTAButton
                      label={t('events.branding.replaceLogo', 'Replace logo')}
                      onPress={() => document.getElementById('branding-logo-input')?.click()}
                    />
                    <Pressable onPress={() => setForm((prev) => ({ ...prev, logoDataUrl: '' }))}>
                      <XStack
                        alignItems="center"
                        space="$1.5"
                        paddingHorizontal="$3"
                        paddingVertical="$2"
                        borderRadius={12}
                        borderWidth={1}
                        borderColor={border}
                      >
                        <Trash2 size={16} color={danger} />
                        <Text fontSize="$sm" color={danger} fontWeight="700">
                          {t('events.branding.removeLogo', 'Remove')}
                        </Text>
                      </XStack>
                    </Pressable>
                  </XStack>
                </>
              ) : (
                <>
                  <ImageIcon size={28} color={subtle} />
                  <Text fontSize="$sm" color={muted} textAlign="center">
                    {t('events.branding.logoHint', 'Upload a logo to brand guest invites and QR posters.')}
                  </Text>
                  <Pressable onPress={() => document.getElementById('branding-logo-input')?.click()}>
                    <XStack
                      alignItems="center"
                      space="$2"
                      paddingHorizontal="$3.5"
                      paddingVertical="$2.5"
                      borderRadius={12}
                      borderWidth={1}
                      borderColor={border}
                      backgroundColor={surface}
                    >
                      <UploadCloud size={18} color={primary} />
                      <Text fontSize="$sm" color={primary} fontWeight="700">
                        {t('events.branding.uploadLogo', 'Upload logo (max. 1 MB)')}
                      </Text>
                    </XStack>
                  </Pressable>
                </>
              )}
              <input
                id="branding-logo-input"
                type="file"
                accept="image/*"
                style={{ display: 'none' }}
                onChange={(event) => {
                  const file = event.target.files?.[0];
                  if (!file) return;
                  if (file.size > 1024 * 1024) {
                    setError(t('events.branding.logoTooLarge', 'Logo must be under 1 MB.'));
                    return;
                  }
                  const reader = new FileReader();
                  reader.onload = () => {
                    const nextLogo =
                      typeof reader.result === 'string'
                        ? reader.result
                        : typeof reader.result === 'object' && reader.result !== null
                          ? String(reader.result)
                          : '';
                    setForm((prev) => ({ ...prev, logoDataUrl: nextLogo }));
                    setError(null);
                  };
                  reader.readAsDataURL(file);
                }}
              />
            </YStack>
          </MobileCard>
        </>
      ) : (
        renderWatermarkTab()
      )}

      <YStack space="$2">
        <CTAButton label={saving ? t('events.branding.saving', 'Saving...') : t('events.branding.save', 'Save Branding')} onPress={() => handleSave()} />
        <Pressable disabled={loading || saving} onPress={handleReset}>
          <XStack
            height={52}
            borderRadius={14}
            alignItems="center"
            justifyContent="center"
            backgroundColor={surface}
            borderWidth={1}
            borderColor={border}
            space="$2"
          >
            <RefreshCcw size={16} color={textStrong} />
            <Text fontSize="$sm" color={textStrong} fontWeight="700">
              {t('events.branding.reset', 'Reset to Defaults')}
            </Text>
          </XStack>
        </Pressable>
      </YStack>

      <MobileSheet
        open={showFontsSheet}
        onClose={() => setShowFontsSheet(false)}
        title={t('events.branding.fontPicker', 'Select font')}
        footer={null}
        bottomOffsetPx={120}
      >
        <YStack space="$2">
          {fontsLoading ? (
            Array.from({ length: 4 }).map((_, idx) => <SkeletonCard key={`font-sk-${idx}`} height={48} />)
          ) : fonts.length === 0 ? (
            <Text fontSize="$sm" color={muted}>
              {t('events.branding.noFonts', 'Keine Schriftarten gefunden.')}
            </Text>
          ) : (
            fonts.map((font) => (
              <Pressable
                key={font.family}
                onPress={() => {
                  setForm((prev) => ({
                    ...prev,
                    [fontField === 'heading' ? 'headingFont' : 'bodyFont']: font.family,
                  }));
                  setShowFontsSheet(false);
                }}
              >
                <XStack alignItems="center" justifyContent="space-between" paddingVertical="$2">
                  <YStack>
                    <Text fontSize="$sm" color={textStrong} style={{ fontFamily: font.family }}>
                      {font.family}
                    </Text>
                    {font.variants?.length ? (
                      <Text fontSize="$xs" color={muted} style={{ fontFamily: font.family }}>
                        {font.variants.map((v) => v.style ?? v.weight ?? '').filter(Boolean).join(', ')}
                      </Text>
                    ) : null}
                  </YStack>
                  {form[fontField === 'heading' ? 'headingFont' : 'bodyFont'] === font.family ? (
                    <Text fontSize="$xs" color={primary}>
                      {t('common.active', 'Active')}
                    </Text>
                  ) : null}
                </XStack>
              </Pressable>
            ))
          )}
        </YStack>
      </MobileSheet>
    </MobileShell>
  );
}

function extractBranding(event: TenantEvent): BrandingForm {
  const source = (event.settings as Record<string, unknown>) ?? {};
  const branding = (source.branding as Record<string, unknown>) ?? source;
  const readColor = (key: string, fallback: string) => {
    const value = branding[key];
    return typeof value === 'string' && value.startsWith('#') ? value : fallback;
  };
  const readText = (key: string) => {
    const value = branding[key];
    return typeof value === 'string' ? value : '';
  };
  return {
    primary: readColor('primary_color', ADMIN_COLORS.primary),
    accent: readColor('accent_color', ADMIN_COLORS.accent),
    headingFont: readText('heading_font'),
    bodyFont: readText('body_font'),
    logoDataUrl: readText('logo_data_url'),
  };
}

function extractWatermark(event: TenantEvent): WatermarkForm {
  const settings = (event.settings as Record<string, unknown>) ?? {};
  const wm = (settings.watermark as Record<string, unknown>) ?? {};
  const readNumber = (key: string, fallback: number) => {
    const value = wm[key];
    return typeof value === 'number' && !Number.isNaN(value) ? value : fallback;
  };
  const readString = (key: string, fallback: string) => {
    const value = wm[key];
    return typeof value === 'string' && value.trim() ? value : fallback;
  };

  const mode = (wm.mode === 'custom' || wm.mode === 'off') ? wm.mode : 'base';
  const position = readString('position', 'bottom-right') as WatermarkPosition;

  return {
    mode,
    assetPath: readString('asset', ''),
    assetDataUrl: '',
    position,
    opacity: readNumber('opacity', 0.25),
    scale: readNumber('scale', 0.2),
    padding: readNumber('padding', 16),
    offsetX: readNumber('offset_x', 0),
    offsetY: readNumber('offset_y', 0),
  };
}

function buildWatermarkPayload(
  form: WatermarkForm,
  watermarkAllowed: boolean,
  brandingAllowed: boolean
): WatermarkSettings | null {
  if (!watermarkAllowed) {
    return { mode: 'off' };
  }

  const policy = watermarkAllowed ? 'basic' : 'none';
  const desiredMode = brandingAllowed ? form.mode : 'base';
  const mode = desiredMode === 'off' && policy === 'basic' ? 'base' : desiredMode;

  const payload: WatermarkSettings = {
    mode,
    position: form.position,
    opacity: Math.min(1, Math.max(0, form.opacity)),
    scale: Math.min(1, Math.max(0.05, form.scale)),
    padding: Math.max(0, Math.round(form.padding)),
    offset_x: Math.max(-500, Math.min(500, Math.round(form.offsetX))),
    offset_y: Math.max(-500, Math.min(500, Math.round(form.offsetY))),
  };

  if (mode === 'custom' && brandingAllowed) {
    if (form.assetDataUrl) {
      payload.asset_data_url = form.assetDataUrl;
    }
    if (form.assetPath) {
      payload.asset = form.assetPath;
    }
  }

  return payload;
}

function renderName(name: TenantEvent['name']): string {
  if (typeof name === 'string') return name;
  if (name && typeof name === 'object') {
    return name.de ?? name.en ?? Object.values(name)[0] ?? '';
  }
  return '';
}

function ColorField({ label, value, onChange }: { label: string; value: string; onChange: (next: string) => void }) {
  const { textStrong, muted, border, surface } = useAdminTheme();
  return (
    <YStack space="$2">
      <Text fontSize="$sm" fontWeight="700" color={textStrong}>
        {label}
      </Text>
        <XStack alignItems="center" space="$2">
          <input
            type="color"
            value={value}
            onChange={(event) => onChange(event.target.value)}
            style={{ width: 52, height: 52, borderRadius: 12, border: `1px solid ${border}`, background: surface }}
          />
          <Text fontSize="$sm" color={muted}>
            {value}
          </Text>
        </XStack>
    </YStack>
  );
}

function ColorSwatch({ color, label }: { color: string; label: string }) {
  const { border, muted } = useAdminTheme();
  return (
    <YStack alignItems="center" space="$1">
      <YStack width={40} height={40} borderRadius={12} borderWidth={1} borderColor={border} backgroundColor={color} />
      <Text fontSize="$xs" color={muted}>
        {label}
      </Text>
    </YStack>
  );
}

function InputField({
  label,
  value,
  placeholder,
  onChange,
  onPicker,
  children,
}: {
  label: string;
  value: string;
  placeholder?: string;
  onChange: (next: string) => void;
  onPicker?: () => void;
  children?: React.ReactNode;
}) {
  const { textStrong, border, surface, primary } = useAdminTheme();
  return (
    <YStack space="$2">
      <Text fontSize="$sm" fontWeight="700" color={textStrong}>
        {label}
      </Text>
      <XStack
        alignItems="center"
        borderRadius={12}
        borderWidth={1}
        borderColor={border}
        paddingLeft="$3"
        paddingRight="$2"
        height={48}
        backgroundColor={surface}
        space="$2"
      >
        {children ?? (
          <input
            type="text"
            value={value}
            placeholder={placeholder}
            onChange={(event) => onChange(event.target.value)}
            style={{
              flex: 1,
              height: '100%',
              border: 'none',
              outline: 'none',
              fontSize: 14,
              background: 'transparent',
            }}
            onFocus={onPicker}
          />
        )}
        {onPicker ? (
          <Pressable onPress={onPicker}>
            <ChevronDown size={16} color={primary} />
          </Pressable>
        ) : null}
      </XStack>
    </YStack>
  );
}

function LabeledSlider({
  label,
  value,
  min,
  max,
  step,
  onChange,
  disabled,
  suffix,
}: {
  label: string;
  value: number;
  min: number;
  max: number;
  step: number;
  onChange: (value: number) => void;
  disabled?: boolean;
  suffix?: string;
}) {
  const { textStrong, muted } = useAdminTheme();
  return (
    <YStack space="$1.5">
      <XStack alignItems="center" justifyContent="space-between">
        <Text fontSize="$sm" fontWeight="700" color={textStrong}>
          {label}
        </Text>
        <Text fontSize="$xs" color={muted}>
          {value}
          {suffix ? ` ${suffix}` : ''}
        </Text>
      </XStack>
      <input
        type="range"
        min={min}
        max={max}
        step={step}
        value={value}
        disabled={disabled}
        onChange={(event) => onChange(Number(event.target.value))}
        style={{ width: '100%' }}
      />
    </YStack>
  );
}

function PositionGrid({
  value,
  onChange,
  disabled,
}: {
  value: WatermarkPosition;
  onChange: (value: WatermarkPosition) => void;
  disabled?: boolean;
}) {
  const { textStrong, primary, border, accentSoft, surface } = useAdminTheme();
  const positions: WatermarkPosition[] = [
    'top-left',
    'top-center',
    'top-right',
    'middle-left',
    'center',
    'middle-right',
    'bottom-left',
    'bottom-center',
    'bottom-right',
  ];

  return (
    <YStack space="$2">
      <Text fontSize="$sm" fontWeight="700" color={textStrong}>
        Position
      </Text>
      <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, minmax(0, 1fr))', gap: 8 }}>
        {positions.map((pos) => (
          <button
            key={pos}
            type="button"
            disabled={disabled}
            onClick={() => onChange(pos)}
            style={{
              height: 40,
              borderRadius: 10,
              border: value === pos ? `2px solid ${primary}` : `1px solid ${border}`,
              background: value === pos ? accentSoft : surface,
            }}
          >
            <Text fontSize="$xs" color={textStrong} textAlign="center">
              {pos.replace('-', ' ')}
            </Text>
          </button>
        ))}
      </div>
    </YStack>
  );
}

function WatermarkPreview({
  position,
  scale,
  opacity,
  padding,
  offsetX,
  offsetY,
}: {
  position: WatermarkPosition;
  scale: number;
  opacity: number;
  padding: number;
  offsetX: number;
  offsetY: number;
}) {
  const { border, muted, textStrong, overlay } = useAdminTheme();
  const width = 280;
  const height = 180;
  const wmWidth = Math.max(24, Math.round(width * Math.min(1, Math.max(0.05, scale))));
  const wmHeight = Math.round(wmWidth * 0.4);

  const baseX = (() => {
    switch (position) {
      case 'top-center':
      case 'center':
      case 'bottom-center':
        return (width - wmWidth) / 2;
      case 'top-right':
      case 'middle-right':
      case 'bottom-right':
        return width - wmWidth - padding;
      default:
        return padding;
    }
  })();

  const baseY = (() => {
    switch (position) {
      case 'middle-left':
      case 'center':
      case 'middle-right':
        return (height - wmHeight) / 2;
      case 'bottom-left':
      case 'bottom-center':
      case 'bottom-right':
        return height - wmHeight - padding;
      default:
        return padding;
    }
  })();

  const x = Math.max(0, Math.min(width - wmWidth, baseX + offsetX));
  const y = Math.max(0, Math.min(height - wmHeight, baseY + offsetY));

  return (
    <div style={{ position: 'relative', width: '100%', maxWidth: 320 }}>
      <div
        style={{
          width,
          height,
          borderRadius: 16,
          overflow: 'hidden',
          border: `1px solid ${border}`,
          background: ADMIN_GRADIENTS.softCard,
        }}
      >
        <div style={{ position: 'absolute', inset: 0, background: `linear-gradient(180deg, ${overlay}, transparent)` }} />
        <div
          style={{
            position: 'absolute',
            left: x,
            top: y,
            width: wmWidth,
            height: wmHeight,
            background: 'rgba(255,255,255,0.8)',
            borderRadius: 10,
            display: 'flex',
            alignItems: 'center',
            justifyContent: 'center',
            opacity: Math.min(1, Math.max(0, opacity)),
            border: `1px dashed ${muted}`,
          }}
        >
          <Droplets size={18} color={textStrong} />
        </div>
      </div>
    </div>
  );
}

function InfoBadge({ icon, text, tone = 'info' }: { icon?: React.ReactNode; text: string; tone?: 'info' | 'danger' }) {
  const { dangerBg, dangerText, surfaceMuted, textStrong, border } = useAdminTheme();
  const background = tone === 'danger' ? dangerBg : surfaceMuted;
  const color = tone === 'danger' ? dangerText : textStrong;

  return (
    <MobileCard space="$2" backgroundColor={background} borderColor={border}>
      <XStack space="$2" alignItems="center">
        {icon}
        <Text fontSize="$sm" color={color}>
          {text}
        </Text>
      </XStack>
    </MobileCard>
  );
}

function TabButton({ label, active, onPress }: { label: string; active: boolean; onPress: () => void }) {
  const { backdrop, surfaceMuted, border, surface } = useAdminTheme();
  return (
    <Pressable onPress={onPress} style={{ flex: 1 }}>
      <XStack
        alignItems="center"
        justifyContent="center"
        paddingVertical="$2.5"
        borderRadius={12}
        backgroundColor={active ? backdrop : surfaceMuted}
        borderWidth={1}
        borderColor={active ? backdrop : border}
      >
        <Text fontSize="$sm" color={active ? surface : backdrop} fontWeight="700">
          {label}
        </Text>
      </XStack>
    </Pressable>
  );
}
