import React, { forwardRef, useState, useEffect, useMemo } from 'react';
import { View, TouchableOpacity, Alert } from 'react-native';
import { Formik } from 'formik';
import * as Yup from 'yup';
import { MyTextInput, BottomDropdown, MyText, tw, ImageUploader } from 'common-ui';
import ProductsSelector from './ProductsSelector';
import { trpc } from '../src/trpc-client';
import usePickImage from 'common-ui/src/components/use-pick-image';
import { useUploadToObjectStorage } from '../hooks/useUploadToObjectStore';

export interface StoreFormData {
  name: string;
  description: string;
  imageUrl?: string;
  owner: number;
  products: number[];
}

export interface StoreFormRef {
  // Add methods if needed
}

interface StoreFormProps {
  mode: 'create' | 'edit';
  initialValues: StoreFormData;
  onSubmit: (values: StoreFormData) => void;
  isLoading: boolean;
  storeId?: number;
}

const validationSchema = Yup.object().shape({
  name: Yup.string().required('Name is required'),
  description: Yup.string(),
  imageUrl: Yup.string(),
  owner: Yup.number().required('Owner is required'),
  products: Yup.array().of(Yup.number()),
});

const StoreForm = forwardRef<StoreFormRef, StoreFormProps>((props, ref) => {
  const { mode, initialValues, onSubmit, isLoading, storeId } = props;
  const { data: staffData } = trpc.admin.staffUser.getStaff.useQuery();
  const { data: productsData } = trpc.admin.product.getProducts.useQuery();

  const [formInitialValues, setFormInitialValues] = useState<StoreFormData>(initialValues);
  const [selectedImages, setSelectedImages] = useState<{ blob: Blob; mimeType: string }[]>([]);
  const [displayImages, setDisplayImages] = useState<{ uri?: string }[]>([]);

  // For edit mode, pre-select products belonging to this store
  const initialSelectedProducts = useMemo(() => {
    if (mode !== 'edit' || !productsData?.products) return [];
    return productsData.products
      .filter(p => p.storeId === storeId)
      .map(p => p.id);
  }, [mode, productsData?.products, storeId]);

  useEffect(() => {
    setFormInitialValues({
      ...initialValues,
      products: initialSelectedProducts,
    });
  }, [initialValues, initialSelectedProducts]);

  const existingImageUrls = useMemo(
    () => (formInitialValues.imageUrl ? [formInitialValues.imageUrl] : []),
    [formInitialValues.imageUrl]
  )

  const staffOptions = staffData?.staff.map((staff: { id: number; name: string }) => ({
    label: staff.name,
    value: staff.id,
  })) || [];



  const { uploadSingle, isUploading } = useUploadToObjectStorage();

  const handleImagePick = usePickImage({
    setFile: async (assets: any) => {
      if (!assets || (Array.isArray(assets) && assets.length === 0)) {
        setSelectedImages([]);
        setDisplayImages([]);
        return;
      }

      const files = Array.isArray(assets) ? assets : [assets];
      const blobPromises = files.map(async (asset) => {
        const response = await fetch(asset.uri);
        const blob = await response.blob();
        return { blob, mimeType: asset.mimeType || 'image/jpeg' };
      });

      const blobArray = await Promise.all(blobPromises);
      setSelectedImages(blobArray);
      setDisplayImages(files.map(asset => ({ uri: asset.uri })));
    },
    multiple: false, // Single image for stores
  });

  const handleRemoveImage = (uri: string) => {
    const index = displayImages.findIndex(img => img.uri === uri);
    if (index !== -1) {
      const newDisplay = displayImages.filter((_, i) => i !== index);
      const newFiles = selectedImages.filter((_, i) => i !== index);
      setDisplayImages(newDisplay);
      setSelectedImages(newFiles);
    }
  };
  
  return (
    <Formik
      initialValues={formInitialValues}
      validationSchema={validationSchema}
      onSubmit={onSubmit}
      enableReinitialize
    >
      {({ handleChange, handleSubmit, values, setFieldValue, errors, touched }) => {
        const submit = async () => {
          try {
            let imageUrl: string | undefined;

            if (selectedImages.length > 0) {
              const { blob, mimeType } = selectedImages[0];
              const { presignedUrl } = await uploadSingle(blob, mimeType, 'store');
              imageUrl = presignedUrl;
            }

            onSubmit({ ...values, imageUrl });
          } catch (error) {
            console.error('Upload error:', error);
            Alert.alert('Error', 'Failed to upload image');
          }
        };

        return (
          <View>
            <MyTextInput
              topLabel="Store Name"
              placeholder="Enter store name"
              value={values.name}
              onChangeText={handleChange('name')}
              error={!!(touched.name && errors.name)}
              style={{ marginBottom: 16 }}
            />
            <MyTextInput
              topLabel="Description"
              placeholder="Enter store description"
              multiline
              numberOfLines={3}
              value={values.description}
              onChangeText={handleChange('description')}
              error={!!(touched.description && errors.description)}
              style={{ marginBottom: 16 }}
            />
            <BottomDropdown
              label="Owner"
              value={values.owner}
              options={staffOptions}
              onValueChange={(value) => setFieldValue('owner', value)}
              placeholder="Select owner"
              error={!!(touched.owner && errors.owner)}
              style={{ marginBottom: 16 }}
            />
            <ProductsSelector
              value={values.products || []}
              onChange={(value) => setFieldValue('products', value)}
              multiple={true}
              label="Products"
              placeholder="Select products"
              isDisabled={(product) => product.storeId !== null && product.storeId !== storeId}
              labelFormat={(product) => `${product.name} - ₹${product.price}`}
            />
            <View style={tw`mb-6`}>
              <MyText style={tw`text-sm font-bold text-gray-700 mb-3 uppercase tracking-wider`}>Store Image</MyText>
              <ImageUploader
                images={displayImages}
                existingImageUrls={existingImageUrls}
                onAddImage={handleImagePick}
                onRemoveImage={handleRemoveImage}
                onRemoveExistingImage={() =>
                  setFormInitialValues((prev) => ({
                    ...prev,
                    imageUrl: undefined,
                  }))
                }
                allowMultiple={false}
              />
            </View>
            <TouchableOpacity
              onPress={submit}
              disabled={isLoading || isUploading}
              style={tw`px-4 py-2 rounded-lg shadow-lg items-center mt-2 ${isLoading || isUploading ? 'bg-gray-400' : 'bg-blue-500'}`}
            >
              <MyText style={tw`text-white text-lg font-bold`}>
                {isUploading ? 'Uploading...' : isLoading ? (mode === 'create' ? 'Creating...' : 'Updating...') : (mode === 'create' ? 'Create Store' : 'Update Store')}
              </MyText>
            </TouchableOpacity>
          </View>
        );
      }}
    </Formik>
  );
});

StoreForm.displayName = 'StoreForm';

export default StoreForm;
