tca-admin/components/gallery/CreateEventGalleryForm.tsx
2025-08-12 10:25:18 +05:30

142 lines
4.9 KiB
TypeScript

'use client';
import React, { useState, ChangeEvent, FormEvent } from 'react';
import IconTrashLines from '../icon/icon-trash-lines';
import axios from 'axios';
import { useRouter } from 'next/navigation';
interface FormErrors {
[key: string]: string;
}
interface EditEventFormProps {
eventId: string | null;
}
const CreateEventGalleryForm: React.FC<EditEventFormProps> = ({ eventId }) => {
const router = useRouter();
const [selectedImages, setSelectedImages] = useState<File[]>([]);
const [previewUrls, setPreviewUrls] = useState<string[]>([]);
const [errors, setErrors] = useState<FormErrors>({});
const handleFileChange = (e: ChangeEvent<HTMLInputElement>) => {
const files = Array.from(e.target.files || []);
const validImages: File[] = [];
const previews: string[] = [];
files.forEach((file) => {
if (file.type.startsWith('image/')) {
validImages.push(file);
previews.push(URL.createObjectURL(file));
}
});
setSelectedImages(prev => [...prev, ...validImages]);
setPreviewUrls(prev => [...prev, ...previews]);
};
const handleImageDelete = (index: number) => {
setSelectedImages(prev => prev.filter((_, i) => i !== index));
setPreviewUrls(prev => prev.filter((_, i) => i !== index));
};
const validateForm = (): boolean => {
const newErrors: FormErrors = {};
if (selectedImages.length === 0) {
newErrors.images = 'Please upload at least one image';
}
setErrors(newErrors);
return Object.keys(newErrors).length === 0;
};
const handleSubmit = async (e: FormEvent) => {
e.preventDefault();
if (!validateForm()) return;
try {
const formData = new FormData();
selectedImages.forEach((file, index) => {
formData.append(`files`, file);
});
const uploadRes = await axios.post(`https://api.tamilculturewaterloo.org/api/upload/multiple`, formData)
console.log("uploadres", uploadRes)
const uploadedUrls = uploadRes?.data?.data?.map((image: any) => image?.fullUrl) || [];
// Step 2: Prepare correct body for bulk save
const body = {
eventid: Number(eventId), // ensure number
imageurl: uploadedUrls // API may expect 'imageurls' not 'imageurl'
};
console.log("Sending body:", body);
// Step 3: Call bulk API
await axios.post(
`https://api.tamilculturewaterloo.org/api/event-images/bulk`,
body
);
router.push(`/event-gallery?eventid=${eventId}`);
} catch (error) {
console.error('Upload failed:', error);
}
};
return (
<form onSubmit={handleSubmit} className="max-w-4xl mx-auto p-6 bg-white rounded shadow-md">
<h2 className="text-xl font-bold mb-4">Upload Gallery Images</h2>
{/* File Input */}
<div className="mb-4">
<label htmlFor="gallery" className="block font-medium">Select Images</label>
<input
type="file"
id="gallery"
accept="image/*"
multiple
onChange={handleFileChange}
className="w-full border rounded px-3 py-2"
/>
{errors.images && <p className="text-red-500 text-sm">{errors.images}</p>}
</div>
{/* Previews */}
{previewUrls.length > 0 && (
<div className="grid grid-cols-2 md:grid-cols-4 gap-4 mb-6">
{previewUrls.map((url, index) => (
<div key={index} className="relative border rounded shadow overflow-hidden">
<img
src={url}
alt={`Preview ${index + 1}`}
className="w-full h-40 object-cover"
/>
<button
type="button"
onClick={() => handleImageDelete(index)}
className="absolute top-1 right-1 bg-red-600 text-white rounded-full p-1 hover:bg-red-700"
>
<IconTrashLines className="w-4 h-4" />
</button>
</div>
))}
</div>
)}
{/* Submit */}
<div className="mt-6">
<button
type="submit"
className="bg-blue-600 text-white px-6 py-2 rounded hover:bg-blue-700"
>
Submit
</button>
</div>
</form>
);
};
export default CreateEventGalleryForm;