Untitled
unknown
plain_text
2 years ago
15 kB
7
Indexable
"use client"; import MainLayout from "@/app/components/Layouts/MainLayout"; import useRequiredFields from "@/app/hooks/useRequiredFields"; import { MantineReactTable, useMantineReactTable } from "mantine-react-table"; import Image from "next/image"; import { useEffect, useMemo, useRef, useState } from "react"; import toast from "react-hot-toast"; const Page = () => { const [charges, setCharges] = useState([]); const [formData, setFormData] = useState({ method: "", name: "", rate: 0, image: null, // New state for handling file upload }); const [editData, setEditData] = useState(null); const [confirmDeleteCharge, setConfirmDeleteCharge] = useState(null); const [loading, setLoading] = useState(true); // Add loading state const [btnLoading, setBtnLoading] = useState(false); const dropifyRef = useRef(); useEffect(() => { const loadDropify = async () => { await loadScript('https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js'); await loadScript('https://jeremyfagis.github.io/dropify/dist/js/dropify.min.js'); const defaultImageUrl = '../../../../default/image_uplode_empty.jpg'; // const defaultImageUrl = imageSet || '../../../../default/image_uplode_empty.jpg'; // Initialize Dropify after scripts are loaded $(dropifyRef.current).dropify({ showRemove: false, defaultFile: defaultImageUrl, }); }; loadDropify(); }, []); // dropify image uplode const loadScript = (src) => { return new Promise((resolve, reject) => { const script = document.createElement('script'); script.src = src; script.onload = resolve; script.onerror = reject; document.head.appendChild(script); }); }; useEffect(() => { fetchCharges(); }, []); const fetchCharges = () => { fetch(`${process.env.NEXT_PUBLIC_BACKEND_URL}/delivery-charges`) .then((response) => response.json()) .then((data) => setCharges(data)) .then((data) => setLoading(false)) .catch((error) => console.error("Error fetching delivery charges:", error) ); }; const handleInputChange = (e) => { const { name, value } = e.target; setFormData({ ...formData, [name]: value, }); }; const handleFileChange = (e) => { const file = e.target.files[0]; setFormData({ ...formData, image: file, }); }; useRequiredFields(loading); const handleSubmit = (e) => { e.preventDefault(); setBtnLoading(true); // Check for missing fields and display an alert if ( !formData.method || !formData.name || !formData.rate || !formData.image ) { toast.error("Please fill in all required fields."); setBtnLoading(false); return; } const formDataWithImage = new FormData(); formDataWithImage.append("method", formData.method); formDataWithImage.append("name", formData.name); formDataWithImage.append("rate", formData.rate); formDataWithImage.append("image", formData.image); fetch(`${process.env.NEXT_PUBLIC_BACKEND_URL}/delivery-charges`, { method: "POST", body: formDataWithImage, }) .then((response) => response.json()) .then((data) => { setCharges((prev) => [...prev, data]); setFormData({ method: "", name: "", rate: 0, image: null, }); const modal = document.getElementById("my_modal_2"); if (modal) { modal.close(); } setBtnLoading(false); toast.success("Delivery Charge Created Successfully"); }) .catch((error) => { console.error("Error adding delivery charge:", error); setBtnLoading(false); }); }; const handleEdit = (charge) => { const modal = document.getElementById("my_modal_2"); if (modal) { modal.showModal(); } setEditData(charge); setFormData({ method: charge.method, name: charge.name, rate: charge.rate, image: null, // Reset image when editing }); }; const handleEditSubmit = () => { setBtnLoading(true); const formDataWithImage = new FormData(); formDataWithImage.append("method", formData.method); formDataWithImage.append("name", formData.name); formDataWithImage.append("rate", formData.rate); formDataWithImage.append("image", formData.image); fetch( `${process.env.NEXT_PUBLIC_BACKEND_URL}/delivery-charges/${editData._id}`, { method: "PUT", body: formDataWithImage, } ) .then((response) => response.json()) // Add this line to parse the response .then((data) => { setCharges((prevChrg) => [...prevChrg, data]); setBtnLoading(false); toast.success("Delivery Charge Updated Successfully"); const modal = document.getElementById("my_modal_2"); if (modal) { modal.close(); } setEditData(null); }) .catch((error) => { console.error("Error updating delivery charge:", error); setBtnLoading(false); }); }; const handleDelete = (charge) => { setConfirmDeleteCharge(charge); const modal = document.getElementById("delete_modal"); if (modal) { modal.showModal(); } }; const handleConfirmDelete = () => { if (confirmDeleteCharge) { fetch( `${process.env.NEXT_PUBLIC_BACKEND_URL}/delivery-charges/${confirmDeleteCharge}`, { method: "DELETE", } ) .then((response) => { if (response.status === 200) { setCharges((prevChrg) => prevChrg.filter((item) => item._id !== confirmDeleteCharge) ); toast.success("Delivery Charge Deleted Successfully"); } const modal = document.getElementById("delete_modal"); if (modal) { modal.close(); } }) .catch((error) => { console.error("Error deleting delivery charge:", error); }); } }; const columns = useMemo( () => [ { accessorKey: "key", header: "#", columnDefType: "display", enableColumnOrdering: false, Cell: ({ row }) => <div className="text-center">{row.index + 1}</div>, mantineTableHeadCellProps: { align: "center", }, mantineTableBodyCellProps: { align: "center", }, size: 90, }, { accessorKey: "method", header: "Method", }, { accessorKey: "name", header: "Description", }, { accessorKey: "rate", header: "Rate", }, { accessorKey: "_id", header: "Action", mantineTableHeadCellProps: { align: "center", }, mantineTableBodyCellProps: { align: "center", }, Cell: ({ row }) => ( <div className="action-icons flex"> <span className="action-icon mr-4 cursor-pointer bg-success font-bold rounded px-2 py-1 text-white" onClick={() => handleEdit(row.original)} > <svg viewBox="0 0 1024 1024" fill="currentColor" height="2em" width="1.5em" aria-hidden="true" > <path d="M257.7 752c2 0 4-.2 6-.5L431.9 722c2-.4 3.9-1.3 5.3-2.8l423.9-423.9a9.96 9.96 0 000-14.1L694.9 114.9c-1.9-1.9-4.4-2.9-7.1-2.9s-5.2 1-7.1 2.9L256.8 538.8c-1.5 1.5-2.4 3.3-2.8 5.3l-29.5 168.2a33.5 33.5 0 009.4 29.8c6.6 6.4 14.9 9.9 23.8 9.9zm67.4-174.4L687.8 215l73.3 73.3-362.7 362.6-88.9 15.7 15.6-89zM880 836H144c-17.7 0-32 14.3-32 32v36c0 4.4 3.6 8 8 8h784c4.4 0 8-3.6 8-8v-36c0-17.7-14.3-32-32-32z" /> </svg> </span> {row.index >= 2 ? ( // Check if the row index is greater than or equal to 2 <span className="action-icon cursor-pointer bg-danger font-bold rounded px-2 py-1 text-white" onClick={() => handleDelete(row.original._id)} > <svg viewBox="0 0 24 24" fill="currentColor" height="2em" width="1.5em" aria-hidden="true" > <path d="M6 19a2 2 0 002 2h8a2 2 0 002-2V7H6v12M8 9h8v10H8V9m7.5-5l-1-1h-5l-1 1H5v2h14V4h-3.5z" /> </svg> </span> ) : null} </div> ), }, ], [] ); const table = useMantineReactTable({ columns, data: charges, state: { isLoading: loading }, }); return ( <MainLayout> <div> <div className="bg-white p-4"> <div className="flex justify-between"> <h1 className="text-xl font-bold">Delivery Charge Management</h1> <button className="btn bg-[#46ADFA] text-xs text-white hover:bg-[#BBE1FF] hover:text-black" onClick={() => { const modal = document.getElementById("my_modal_2"); if (modal) { modal.showModal(); } }} > Add Delivery Charges </button> </div> <div className="mt-2 overflow-x-auto rounded-t-lg"> <div className="px-1"> <MantineReactTable table={table} /> </div> </div> </div> <dialog id="my_modal_2" className="modal"> <div className="modal-box"> <form encType="multipart/form-data"> <div className="mb-4"> <label htmlFor="method" className="mb-2 block text-sm font-semibold text-gray-700" > Method: </label> <input type="text" id="method" name="method" value={formData.method} onChange={handleInputChange} className="input input-bordered w-full" required /> </div> <div className="mb-4"> <label htmlFor="name" className="mb-2 block text-sm font-semibold text-gray-700" > Description: </label> <textarea type="text" id="name" name="name" value={formData.name} onChange={handleInputChange} className="textarea textarea-bordered w-full" required /> </div> <div className="mb-4"> <label htmlFor="rate" className="mb-2 block text-sm font-semibold text-gray-700" > Rate: </label> <input type="number" id="rate" name="rate" value={formData.rate} onChange={handleInputChange} className="input input-bordered w-full" required /> </div> <div className="mb-4"> <label htmlFor="image" className="mb-2 block text-sm font-semibold text-gray-700" > Image: </label> <div className="h-52 imageUp"> <input type="file" id="image" name="image" onChange={(e) => handleFileChange(e)} className="file-input w-full dropify h-32" required ref={dropifyRef} /> </div> </div> {editData ? ( <button onClick={handleEditSubmit} className="btn btn-primary w-full" disabled={btnLoading} > {btnLoading ? ( <span className="flex items-center"> <span className="loading loading-sm mr-2"></span> Saving Changes </span> ) : ( "Save Changes" )} </button> ) : ( <button onClick={handleSubmit} className="btn btn-primary w-full" disabled={btnLoading} > {btnLoading ? ( <span className="flex items-center"> <span className="loading loading-sm mr-2"></span> Adding Delivery Charge </span> ) : ( "Add Delivery Charge" )} </button> )} </form> </div> <form method="dialog" className="modal-backdrop"> <button>close</button> </form> </dialog> <dialog id="edit_modal" className="modal"> </dialog> <dialog id="delete_modal" className="modal"> <div className="modal-box text-center flex flex-col justify-center items-center"> <Image src="/default/delete_sure.png" width={100} height={100} alt="Picture of the author" /> <p className="py-4 text-lg font-bold"> Would you like this Delivery Charge to be deleted? </p> <div className="modal-action"> <form method="dialog"> <button onClick={handleConfirmDelete} className="btn bg-success hover:bg-success hover:text-black btn-sm mr-2 transform-none text-white" > Yes, delete it! </button> <button className="btn btn-sm bg-error hover:bg-error hover:text-black text-white hover:bg-red " onClick={() => { const modal = document.getElementById("delete_modal"); if (modal) { modal.close(); } }}> Cancel </button> </form> </div> </div> </dialog> </div> </MainLayout> ); }; export default Page;
Editor is loading...
Leave a Comment