From 82c1dc4b8e9fafb882114e730c156629e1cedc27 Mon Sep 17 00:00:00 2001 From: "pramod.mahajan" Date: Wed, 26 Nov 2025 12:29:40 +0530 Subject: [PATCH] created purchase form --- public/assets/css/core-extend.css | 12 + .../common/Forms/SelectFieldServerSide.jsx | 12 +- src/components/common/InputSuggestion.jsx | 1 - src/components/purchase/ManagePurchase.jsx | 138 ++++++---- .../purchase/PurchasePartyDetails.jsx | 241 ++++++++++++++++-- .../purchase/PurchasePaymentDetails.jsx | 148 ++++++++++- src/components/purchase/PurchaseSchema.jsx | 105 ++++---- .../purchase/PurchaseTansportDetails.jsx | 11 - .../purchase/PurchaseTransportDetails.jsx | 131 ++++++++++ 9 files changed, 659 insertions(+), 140 deletions(-) delete mode 100644 src/components/purchase/PurchaseTansportDetails.jsx create mode 100644 src/components/purchase/PurchaseTransportDetails.jsx diff --git a/public/assets/css/core-extend.css b/public/assets/css/core-extend.css index b05f71c1..127de638 100644 --- a/public/assets/css/core-extend.css +++ b/public/assets/css/core-extend.css @@ -11,6 +11,18 @@ top: var(--sticky-top, 0px) !important; z-index: 1025; } +.form-control-md { + min-height: calc(1.6em + 0.65rem + calc(var(--bs-border-width) * 2)); + padding: 0.18rem 0.60rem; + font-size: 0.875rem; /* ~14px */ + border-radius: var(--bs-border-radius); +} + +.form-control-md::file-selector-button { + padding: 0.32rem 0.75rem; + margin: -0.32rem -0.75rem; + margin-inline-end: 0.75rem; +} /* ===========================% Background_Colors %========================================================== */ diff --git a/src/components/common/Forms/SelectFieldServerSide.jsx b/src/components/common/Forms/SelectFieldServerSide.jsx index 47b1d5ad..d60be88b 100644 --- a/src/components/common/Forms/SelectFieldServerSide.jsx +++ b/src/components/common/Forms/SelectFieldServerSide.jsx @@ -200,7 +200,9 @@ export const SelectProjectField = ({ isFullObject = false, isMultiple = false, isAllProject = false, - disabled + disabled, + className, + errors }) => { const [searchText, setSearchText] = useState(""); const debounce = useDebounce(searchText, 300); @@ -302,6 +304,10 @@ export const SelectProjectField = ({ {displayText} + + {errors?.projectId && ( +
{errors.projectId.message}
+ )} {/* DROPDOWN */} {open && ( @@ -377,6 +383,7 @@ export const SelectFieldSearch = ({ isMultiple = false, hookParams, useFetchHook, + errors=null, }) => { const [searchText, setSearchText] = useState(""); const debounce = useDebounce(searchText, 300); @@ -512,6 +519,9 @@ export const SelectFieldSearch = ({ {displayText} + {errors && ( +
{errors.message}
+ )} {/* DROPDOWN */} {open && ( diff --git a/src/components/common/InputSuggestion.jsx b/src/components/common/InputSuggestion.jsx index 0a79fa35..b586abe1 100644 --- a/src/components/common/InputSuggestion.jsx +++ b/src/components/common/InputSuggestion.jsx @@ -50,7 +50,6 @@ const InputSuggestions = ({ {filteredList.map((org) => (
  • { const [activeTab, setActiveTab] = useState(0); const [completedTabs, setCompletedTabs] = useState([]); - const newTenantConfig = [ + const stepsConfig = [ { name: "Contact Info", icon: "bx bx-user bx-md", @@ -24,29 +25,29 @@ const ManagePurchase = () => { name: "Organization", icon: "bx bx-buildings bx-md", subtitle: "Organization Details", - component:
    Invoice & Transport Details
    , + component: , }, { - name: "SubScription", + name: "Subscription", icon: "bx bx-star bx-md", - component:
    Payment & Financials
    , + subtitle: "Payment & Financials", + component: , }, ]; + const purchaseOrder = useAppForm({ resolver: zodResolver(PurchaseSchema), - defaultJobValue: defaultPurchaseValue, + defaultValues: defaultPurchaseValue, + mode: "onChange", }); - const getCurrentTrigger = () => - activeTab === 2 ? subscriptionForm.trigger : tenantForm.trigger; const handleNext = async () => { const currentStepFields = getStepFields(activeTab); - const trigger = getCurrentTrigger(); - const valid = await trigger(currentStepFields); + const valid = await purchaseOrder.trigger(currentStepFields); if (valid) { setCompletedTabs((prev) => [...new Set([...prev, activeTab])]); - setActiveTab((prev) => Math.min(prev + 1, newTenantConfig.length - 1)); + setActiveTab((prev) => Math.min(prev + 1, stepsConfig.length - 1)); } }; @@ -54,59 +55,84 @@ const ManagePurchase = () => { setActiveTab((prev) => Math.max(prev - 1, 0)); }; - const onsubmit = (formData) => {}; + const onSubmit = (formData) => { + console.log("PURCHASE DATA:", formData); + }; + return (
    - {/* New Parchase */} -
    - {newTenantConfig - .filter((step) => step.name.toLowerCase() !== "congratulation") - .map((step, index) => { - const isActive = activeTab === index; - const isCompleted = completedTabs.includes(index); + {/* Header */} +
    + {stepsConfig.map((step, index) => { + const isActive = activeTab === index; + const isCompleted = completedTabs.includes(index); - return ( - -
    - -
    - {index < newTenantConfig.length - 1 && ( -
    - )} -
    - ); - })} + + +
    + + {index < stepsConfig.length - 1 && ( +
    + )} + + ); + })}
    + + {/* Content */}
    - -
    - {newTenantConfig[activeTab].component} + + + {stepsConfig[activeTab].component} + +
    + + + {activeTab < stepsConfig.length - 1 ? ( + + ) : ( + + )} +
    diff --git a/src/components/purchase/PurchasePartyDetails.jsx b/src/components/purchase/PurchasePartyDetails.jsx index d7b63533..4870d38a 100644 --- a/src/components/purchase/PurchasePartyDetails.jsx +++ b/src/components/purchase/PurchasePartyDetails.jsx @@ -1,31 +1,232 @@ import React from "react"; -import { useAppFormContext } from "../../hooks/appHooks/useAppForm"; +import { AppFormController, useAppFormContext } from "../../hooks/appHooks/useAppForm"; +import Label from "../common/Label"; +import DatePicker from "../common/DatePicker"; +import { + SelectFieldSearch, + SelectProjectField, +} from "../common/Forms/SelectFieldServerSide"; +import { useOrganization, useOrganizationsList } from "../../hooks/useOrganization"; +import { ITEMS_PER_PAGE } from "../../utils/constants"; -const PurchasePartyDetails = ({ onNext }) => { +const PurchasePartyDetails = () => { const { register, control, - trigger, + setValue, + watch, formState: { errors }, } = useAppFormContext(); - const handleNext = async () => { - const valid = await trigger([ - "title", - "projectId", - "organizationId", - "supplier", - "billingAddress", - "shippingAddress", - "purchaseOrderNumber", - "purchaseOrderDate", - "porformaInvoiceNo", - ]); - if (valid) { - onNext(); - } - }; - return
    ; + + return ( +
    + {/* Title */} +
    + + + + + {errors?.title && ( +
    {errors.title.message}
    + )} +
    + + {/* Project ID */} +
    + + setValue("projectId", val, { + shouldDirty: true, + shouldValidate: true, + }) + } + errors={errors} + /> +
    + + {/* Organization */} +
    + + {/* */} + ( + + )} + /> + +
    + + {/* Supplier */} +
    + + + + + {errors?.supplierId && ( +
    {errors.supplierId.message}
    + )} +
    + + {/* Billing Address */} +
    + + +