10000
We read every piece of feedback, and take your input very seriously.
To see all available qualifiers, see our documentation.
There was an error while loading. Please reload this page.
-
How to trigger onChange when the field changes on FieldArrray Item? Array items can be added. So is there a way in formik if the quantity field changes on Array 2 element just trigger for that item?
Only adding the relevant code section
` const FormObserver = (index) => { //This approach works but I will need to do the calculation for all field array items as I won't know which one triggered this change const { values:{InvoiceDetails} } = useFormikContext(); React.useEffect(() => { console.log("FormObserver::values", InvoiceDetails); console.log(index); }, [InvoiceDetails]); return null; }; return ( <Formik initialValues={{ InvoiceNumber: '', InvoiceDate: Date.parse('2017-10-20'), ClientId: '', CompanyId: '', PaymentStatusId: '', PaymentTerms: '', Total: '', Notes: '', InvoiceDetails: [{ Id: '', Description: '', Quantity: '', Amount: '', VatPercentage: '20', VatAmount: '10', Total: '100' }] }} validationSchema={Yup.object().shape({ InvoiceNumber: Yup.string().required(), InvoiceDate: Yup.string().required(), ClientId: Yup.string().required(), CompanyId: Yup.string().required(), PaymentTerms: Yup.number().required().positive().integer().max(365), Notes: Yup.string().max(10), InvoiceDetails: Yup.array().of( Yup.object().shape({ Description: Yup.string().required("Description is a required field"), Quantity: twodecimalplaces("Quantity") .required("Quantity is a required field") .max(100000, "Maximum allowed Quantity is 100000"), Amount: twodecimalplaces("Amount") .required("Amount is a required field") .max(1000000, "Maximum allowed Amount is 1000000"), VatPercentage: Yup.number().positive().integer() .required("VatPercentage is a required field") .max(100, "Maximum allowed Percentage is 100"), VatAmount: Yup.number().required("VatAmount is a required field"), Total: Yup.number().required("Total is a required field") }) ) }) } => { alert(JSON.stringify(values)); }} > {({ props, values, setValues }) => ( <Container> <Form> {!invoicenumber && <h1 className="header text-center">Create new invoice</h1>} {invoicenumber && <h1 className="header text-center">Edit invoice</h1>} {!isAuthenticated && <Login></Login>} {error && <Alert variant="danger">{error}</Alert>} {success && <Alert variant="success">{success}</Alert>} <Row> {/* <Field name="InvoiceNumber" component={InvoiceNumberV3} /> */} <InvoiceNumberV4 name="InvoiceNumber" /> <FormControl.Label column="lg" lg={2}> Date </FormControl.Label> <Col md={4}> <MyDatePicker name="InvoiceDate" /> </Col> </Row> <Row> <FormControl.Label column="lg" lg={2}> Client </FormControl.Label> <Col> <FormSelect name="ClientId" options={clientItems.map((client) => ({ "value": client.Value, "key": client.Key }))} /> </Col> <FormControl.Label column="lg" lg={2}> Company </FormControl.Label> <Col> <FormSelect name="CompanyId" options={companyItems.map((company) => ({ "value": company.Value, "key": company.Key }))} /> </Col> </Row> <Row className="mt-2"> <FormControl.Label column="lg" lg={2}> Payment Terms </FormControl.Label> <Col> <DependentField name="PaymentTerms" type="text"></DependentField> </Col> <FormControl.Label column="lg" lg={2}> Notes </FormControl.Label> <Col> <FieldV1 name="Notes" as="textarea" rows="3" ></FieldV1> </Col> </Row> <FieldArray name="info"> {() => values.InvoiceDetails.map((invoicedetail, index) => { return ( <Card className="mt-2" key={`detail-${index}`}> <Card.Header as="h5" className="container-fluid"> Invoice details #{index + 1} {index > 0 && <Button type='button' variant="danger" size="sm" => removeInvoiceDetail(index, values, setValues)} > Remove-{index}</Button> } </Card.Header> <div className="mt-2 m-2"> {/* <FormObserver index={index} /> */} <Row key={index}> <FormControl.Label column="lg" lg={2}> Description </FormControl.Label> <Col md={10}> <FieldV1 name={`InvoiceDetails[${index}].Description`} ></FieldV1> </Col> <FormControl.Label column="lg" lg={2}> Quantity </FormControl.Label> <Col md={4}> <FieldV1 name={`InvoiceDetails[${index}].Quantity`} </Col> <FormControl.Label column="lg" lg={2}> Amount </FormControl.Label> <Col md={4}> <FieldV1 name={`InvoiceDetails[${index}].Amount`} ></FieldV1> </Col> <FormControl.Label column="lg" lg={2}> Vat% </FormControl.Label> <Col lg={4}> <FieldV1 name={`InvoiceDetails[${index}].VatPercentage`} ></FieldV1> </Col> <Row> <FormControl.Label column="lg" lg={2}> Vat Amount </FormControl.Label> <Col> <FieldV1 readOnly={true} name={`InvoiceDetails[${index}].VatAmount`}></FieldV1> </Col> <FormControl.Label column="lg" lg={2}> Total </FormControl.Label> <Col> <FieldV1 readOnly={true} name={`InvoiceDetails[${index}].Total`} ></FieldV1> </Col> </Row> </Row> </div> </Card> ) }) } </FieldArray> <div className="mt-4 mb-4 center-div"> <Button type="submit" variant="success" size="lg" disabled={busy}> {busy && ( <> <Spinner as="span" animation="border" size="sm" role="status" aria-hidden="true" /> <span className="visually-hidden">Loading...</span> </> )} Create Invoice </Button> <Button type="button" variant="secondary" size="lg" => addInvoiceDetail(values, setValues)} disabled={busy} className='margin-left-1rem btn-block' > Add detail </Button> <Link to="/"> <Button type="Button" variant="secondary" size="lg" disabled={busy} className='margin-left-1rem'> Back </Button> </Link> </div> </Form> </Container> )} </Formik>
Beta Was this translation helpful? Give feedback.
Hey,, Did you get the answer? i am also facing same issue and dont know how can i change array item value with onChange.
import React, { useState, useEffect, useRef } from "react"; import * as Yup from "yup"; import { Table, TableProps } from "antd"; import { Button, Modal } from "antd"; import img1 from "../assets/delete.png"; import "../../src/index.css"; import "../../src/App.scss"; import img from "../assets/images/logo.png"; import Login from "../login/Login"; import Accordian from "../accordian/Accordian"; import Header from "../component/Header"; import { Formik, Form, Field, ErrorMessage, FieldArray, useFormikContext } from "formik"; import { gwsPriceFormSchema } from "./Schema";
import GWSProductItemForm from "./GWSProductItemForm"; import { ProductPricelist, setProductPriceDetails, capitalizeFirstLetter } from "./ProductPriceList"; import { Link } from "react-router-dom";
export const subplans: any = { business: ["Starter", "Standard", "Plus"], enterprise: ["Starter", "Standard", "Plus"], frontline: ["Basic", "Plus"], };
export const populateSubplans = (productType: any) => { return subplans[productType] || []; };
const Newproposal = () => { const [isModalOpen, setIsModalOpen] = useState(false); const [editModalOpen, setIsModalOpen1] = useState(false); const [delModalOpen, setIsModalOpen2] = useState(false); const [activeKeys, setActiveKeys] = useState("1");
const [gwsPriceFormInitValues, setGwsPriceFormInitValues] = useState({ transationType: "new_business", contractPeriod: "1", priceGivenByGoogle: false, customerCompanyName: "", customerName: "", email: "", customerDomain: "", products: [] as any[], });
const [productPriceDetails1, setProductPriceDetails1] = useState(); const [productPriceDetails2, setProductPriceDetails2] = useState(); const [googleGivenPriceShow, setGoogleGivenPriceShow] = useState(false); const [isCalculated, setIsCalculated] = useState(false); const [isAccordionOpen, setIsAccordionOpen] = useState(false); const [forceUpdate, setForceUpdate] = useState(0); const productFormRef = useRef(null); const [isValid, setIsValid] = useState(false); const [priceVarifyPercentage, setPriceVarifyPercentage] = useState(11); const [allData, setAllData] = useState(null); const [invoiceData, setInvoiceData] = useState(null);
const handleButtonClick = () => { setIsAccordionOpen(true); setActiveKeys("0"); };
useEffect(() => { getProductPrice(); }, []);
const getProductPrice = () => { const { first_20_price, after_20_price } = setProductPriceDetails(ProductPricelist);
console.log("======================================="); console.log(first_20_price); console.log(after_20_price); console.log("======================================="); setProductPriceDetails1(first_20_price); setProductPriceDetails2(after_20_price); getInvoiceData();
};
const getInvoiceData = async () => { alert(sessionStorage.editInvoiceID);
if (sessionStorage.editInvoiceID) { try { const formdata = new FormData(); formdata.append("invoice_id", sessionStorage.editInvoiceID); const response = await fetch("https://api.gwscalculator.cloudnowtech.com/getInvoiceByID.php", { method: "POST", body: formdata }); const result = await response.json(); debugger; if (result && result.data && result.data[0]) { debugger; setInvoiceData(result.data[0]); setFormData(result.data[0]); } else { // triggerNotification("error", "Error", "Failed", "topRight", "pop-color"); } } catch (error) { // console.error(error); // setInvoiceHistoryList([]); // triggerNotification("error", "Error", "Failed", "topRight", "pop-color"); } }
const setFormData = (data: any) => { try { debugger; const invoiceData: any = JSON.parse(data.invoice_data); console.log(invoiceData); debugger; if (invoiceData) { const updatedData: any = changeKey(invoiceData.products);
if (productFormRef.current && updatedData) { productFormRef.current.setValues({ customerName: invoiceData.customerName, email: invoiceData.email, customerDomain: invoiceData.customerDomain, products: updatedData, transationType: invoiceData.transationType, contractPeriod: invoiceData.contractPeriod, priceGivenByGoogle: invoiceData.priceGivenByGoogle, customerCompanyName: invoiceData.customerCompanyName }); setTimeout(() => { document.getElementById('calculate')?.click(); }, 1000); setTimeout(() => { document.getElementById('handleAddressOpen')?.click(); }, 1200); } } debugger; } catch (error) { console.error("Failed to set form data:", error); }
}; const changeKey = (data: any[]) => { return data.map(item => { if (item.hasOwnProperty('subplan')) { item['subPlan'] = item['subplan']; delete item['subplan']; } return item; }); } const showModal = () => { setIsModalOpen(true); }; const handleOk = () => { setIsModalOpen(false); setIsModalOpen1(false); }; const handleCancel = () => { setIsModalOpen(false); setIsModalOpen1(false); setIsModalOpen2(false); }; const handleDel = () => { setIsModalOpen2(true); }; const handleedu = () => { setIsModalOpen1(true); };
const addProductItem = (values: any) => { debugger; let temp: any = productFormRef.current.values.products; const newProduct = { productType: values.productType, subPlan: values.subPlan, licenses: values.licenses, googlePrice: googleGivenPriceShow ? values.googlePrice : null, CustomerGivenPrice: values.customerPrice, }; if (!Array.isArray(temp)) { temp = []; } temp.push(newProduct); setGwsPriceFormInitValues({ ...productFormRef.current.values, products: temp, });
setForceUpdate((prev) => prev + 1); productFormRef.current.validateForm().then((errors: any) => { if (errors.products) { console.log("Form validation errors after adding product:", errors.products); } else { console.log("No form validation errors after adding product."); } });
const handlePriceGivenByGoogle = (name: any, value: any, setFieldValue: any, resetForm: any) => { setFieldValue(name, value); setGoogleGivenPriceShow(value); resetTable(resetForm); };
const handleTransationType = (value: any, name: any, setFieldValue: any, resetForm: any) => { setFieldValue("transationType", value); if (value === "renewal" || value === "transfer_business") { setFieldValue("priceGivenByGoogle", true); setGoogleGivenPriceShow(true); } if (value === "new_business") { setPriceVarifyPercentage(11); } if (value === "renewal") { setPriceVarifyPercentage(6); } if (value === "transfer_business") { setPriceVarifyPercentage(3); } };
const handleContractPeriodChange = (value: any, setFieldValue: any, resetForm: any) => { setFieldValue("contractPeriod", value); if (value === "3") { setFieldValue("priceGivenByGoogle", true); setGoogleGivenPriceShow(true); resetTable(resetForm); } };
const handleProductTypeChange = (index: any, value: any, setFieldValue: any) => { setFieldValue(products[${index}].productType, value); };
products[${index}].productType
const handleSubPlanChange = (index: any, value: any, setFieldValue: any) => { setFieldValue(products[${index}].subPlan, value); };
products[${index}].subPlan
const handleLicensesChange = (index: any, value: any, setFieldValue: any) => { const validValue = value === "" ? 0 : Number(value); setFieldValue(products[${index}].licenses, validValue); };
products[${index}].licenses
const handleGooglePriceChange = (index: any, value: any, setFieldValue: any) => { const validValue = value === "" ? 0 : Number(value); setFieldValue(products[${index}].googlePrice, validValue); };
products[${index}].googlePrice
const handleCustomerGivenPriceChange = (index: any, value: any, setFieldValue: any) => { const validValue = value === "" ? 0 : Number(value); setFieldValue(products[${index}].CustomerGivenPrice, validValue); };
products[${index}].CustomerGivenPrice
const proposalSubmit = async (values: any) => { console.log(values.products); debugger; if (values.priceGivenByGoogle) { let response = await comparePrice2(values); if (response) { const res = await calculate(); if (res) { let item = { ...values, ...res, }; setAllData(item); setIsAccordionOpen(true); setActiveKeys("0"); } } else { alert("Contact NK and Dinesh to get approvals for this price."); } } else { let response = await comparePrice1(values); if (response) { const res = await calculate(); if (res) { let item = { ...values, ...res, }; setAllData(item); setIsAccordionOpen(true); setActiveKeys("0"); } } else { alert("Contact NK and Dinesh to get approvals for this price."); } } };
const comparePrice1 = (values: any) => { let result = 0; let productsList = values.products; let mapErrorFlag = [];
productsList.map((object: any) => { let itemName = object.productType + "" + object.subPlan; if (itemName.toLocaleLowerCase() === "businessstarter" || itemName.toLocaleLowerCase() === "businessstandard") { let numberOfLicenses = parseInt(object.licenses); let checkRemainingLicenses = numberOfLicenses > 20 ? true : false; if (checkRemainingLicenses) { let CustomerGivenPrice: any = parseFloat(object.CustomerGivenPrice).toFixed(2); let total_OfCustomerGivenPrice = numberOfLicenses * CustomerGivenPrice; let countAfterTwantyLicenses = numberOfLicenses - 20; let basePrice1 = productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let basePrice2 = productPriceDetails2[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let margin1 = basePrice1 * (priceVarifyPercentage / 100); let margin2 = basePrice2 * (priceVarifyPercentage / 100); let firstTwantyLicensesAmt = 20 * basePrice1 + 20 * margin1; const afterTwantyLicensesAmt = countAfterTwantyLicenses * basePrice2 + countAfterTwantyLicenses * margin2; let preTotal = firstTwantyLicensesAmt + afterTwantyLicensesAmt; if (total_OfCustomerGivenPrice > preTotal) { mapErrorFlag.push(true); } else { mapErrorFlag.push(false); result = result + 1; } } else { let perLicensesAmount = productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let perLicensesWithMarginAmt = perLicensesAmount + calculateMarginAmount(perLicensesAmount); let CustomerGivenPrice = parseInt(object.CustomerGivenPrice); if (CustomerGivenPrice > perLicensesWithMarginAmt) { mapErrorFlag.push(true); } else { mapErrorFlag.push(false); result = result + 1; } } } else { let perLicensesAmount = productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let perLicensesWithMarginAmt = perLicensesAmount + calculateMarginAmount(perLicensesAmount); let CustomerGivenPrice = parseInt(object.CustomerGivenPrice); if (CustomerGivenPrice > perLicensesWithMarginAmt) { mapErrorFlag.push(true); } else { mapErrorFlag.push(false); result = result + 1; } } }); return result == 0 ? true : false;
const calculateMarginAmount = (perLicensesAmount: any) => { return perLicensesAmount * (priceVarifyPercentage / 100); };
const comparePrice2 = (values: any) => { let result = 0; let productsList = values.products; let packagePrice = productsList.map((object: any) => { let googlePriceNum = parseFloat(object.googlePrice); let customerPriceNum = parseFloat(object.CustomerGivenPrice); let difference = customerPriceNum - googlePriceNum; let percentageOfGooglePrice = googlePriceNum * (priceVarifyPercentage / 100); if (difference >= percentageOfGooglePrice) { } else { result += 1; } }); return result == 0 ? true : false; };
const calculate = () => { debugger;
let skuNameList: any = []; let qtyList: any = []; let customerPrice: any = []; let costToGoogle: any = []; let tempProductList = productFormRef.current.values.products; if (productFormRef.current.values.priceGivenByGoogle) { debugger; let result = 0; let packagePrice = tempProductList.map((object: any) => { let difference = object.CustomerGivenPrice - object.googlePrice; let percentageOfGooglePrice = object.googlePrice * (priceVarifyPercentage / 100); if (difference >= percentageOfGooglePrice) { } else { result += 1; } skuNameList.push({ sku: capitalizeFirstLetter(object.productType) + "-" + capitalizeFirstLetter(object.subPlan), }); qtyList.push({ qty: object.licenses }); customerPrice.push({ customerPrice: object.CustomerGivenPrice }); costToGoogle.push({ googlePrice: object.googlePrice }); }); } else { debugger; let result = 0; let packagePrice = tempProductList.map((object: any) => { let numberOfLicenses = parseInt(object.licenses); let nameType = (object.productType + "" + object.subPlan).toLocaleLowerCase(); if (nameType === "businessstarter" || nameType === "businessstandard") { let checkRemainingLicenses = numberOfLicenses > 20 ? true : false; if (checkRemainingLicenses) { let _tempSkuNameList = []; let _tempQtyList = []; let _tempCostToGoogle = []; let _tempCustomerPrice = []; let CustomerGivenPrice: any = parseFloat(object.CustomerGivenPrice).toFixed(2); let total_OfCustomerGivenPrice = numberOfLicenses * CustomerGivenPrice; let basePrice1 = productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let basePrice2 = productPriceDetails2[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let margin1 = basePrice1 * (priceVarifyPercentage / 100); let margin2 = basePrice2 * (priceVarifyPercentage / 100); let countAfterTwantyLicenses = numberOfLicenses - 20; let firstTwantyLicensesAmt = 20 * basePrice1 + 20 * margin1; _tempSkuNameList.push(capitalizeFirstLetter(object.productType) + "-" + capitalizeFirstLetter(object.subPlan)); _tempQtyList.push(20); _tempCostToGoogle.push(productPriceDetails1[object.productType][object.subPlan]); _tempCustomerPrice.push(object.CustomerGivenPrice); const afterTwantyLicensesAmt = countAfterTwantyLicenses * basePrice2 + countAfterTwantyLicenses * margin2; _tempSkuNameList.push(capitalizeFirstLetter(object.productType) + "-" + capitalizeFirstLetter(object.subPlan)); _tempQtyList.push(countAfterTwantyLicenses); _tempCostToGoogle.push(productPriceDetails2[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]); _tempCustomerPrice.push(object.CustomerGivenPrice); skuNameList.push({ sku: _tempSkuNameList }); qtyList.push({ qty: _tempQtyList }); costToGoogle.push({ googlePrice: _tempCostToGoogle }); customerPrice.push({ customerPrice: _tempCustomerPrice }); let preTotal = firstTwantyLicensesAmt + afterTwantyLicensesAmt; if (total_OfCustomerGivenPrice > preTotal) { } else { result += 1; } debugger; } else { skuNameList.push({ sku: capitalizeFirstLetter(object.productType) + "-" + capitalizeFirstLetter(object.subPlan), }); qtyList.push({ qty: numberOfLicenses }); costToGoogle.push({ googlePrice: productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()] }); customerPrice.push({ customerPrice: object.CustomerGivenPrice }); let perLicensesAmount = productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()]; let perLicensesWithMarginAmt = perLicensesAmount + calculateMarginAmount(perLicensesAmount); let CustomerGivenPrice = parseInt(object.CustomerGivenPrice); if (CustomerGivenPrice > perLicensesWithMarginAmt) { } else { result += 1; } debugger; } } else { qtyList.push({ qty: numberOfLicenses }); skuNameList.push({ sku: capitalizeFirstLetter(object.productType) + "-" + capitalizeFirstLetter(object.subPlan) }); customerPrice.push({ customerPrice: object.CustomerGivenPrice }); costToGoogle.push({ googlePrice: productPriceDetails1[object.productType.toLocaleLowerCase()][object.subPlan.toLocaleLowerCase()] }); let perLicensesAmount = productPriceDetails1[object.productType][object.subPlan]; let perLicensesWithMarginAmt = perLicensesAmount + calculateMarginAmount(perLicensesAmount); let CustomerGivenPrice = parseInt(object.CustomerGivenPrice); if (CustomerGivenPrice > perLicensesWithMarginAmt) { } else { result += 1; } } }); } debugger; return { skuNameList: skuNameList, qtyList: qtyList, customerPrice: customerPrice, costToGoogle: costToGoogle, };
const resetTable = (resetForm: any) => { setAllData(null); setActiveKeys("1"); setIsAccordionOpen(false); setTimeout(() => { resetForm({ values: { ...productFormRef.current.values, products: [], }, }); }, 1000); };
return (
<div className="mx-auto accordian-screen w-90 mt-[120px]"> <button className="flex bck"> <Link to="/invoice_logs" className="flex"> <span className="material-symbols-outlined pr-1 pt-[2px]">keyboard_backspace</span>Back </Link> </button> <div className="grid grid-cols-12 gap-4"> <div className="col-span-4 bg-gy1 p-4"> <Formik initialValues={gwsPriceFormInitValues} validationSchema={gwsPriceFormSchema} innerRef={productFormRef}> {({ isSubmitting, setFieldValue, values, handleSubmit, handleChange, errors, resetForm }) => ( <Form name="outerform" id="outerform"> <h3>GWS Price Calculator</h3> <h4>Transaction Details:</h4> <div className="grid grid-cols-2 gap-6 align-center mb-5 frm1"> <div className=""> <label className="block mb-2">Select Transaction Type</label> <select id="tran" className="p-2.5 w-full" name="transationType" value={values.transationType} => handleTransationType(e.target.value, "transationType", setFieldValue, resetForm)} > <option value="new_business">New Business</option> <option value="renewal">Renewal</option> <option value="transfer_business">Transfer Business</option> </select> <ErrorMessage name="transationType" component="div" className="error" /> </div> <div className=""> <label className="block mb-2">Contract period</label> <select id="peri" className="w-full p-2.5" name="contractPeriod" value={values.contractPeriod} => handleContractPeriodChange(e.target.value, setFieldValue, resetForm)} > <option value="1">One Year</option> <option value="3">Three Year</option> </select> <ErrorMessage name="contractPeriod" component="div" className="error" /> </div> </div> <div className="flex items-center"> <label className="flex items-center" style={{ position: "unset" }}> <input id="checked-checkbox" type="checkbox" className="w-5 h-5" name="priceGivenByGoogle" checked={values.priceGivenByGoogle} => handlePriceGivenByGoogle("priceGivenByGoogle", e.target.checked, setFieldValue, resetForm)} /> <p className="ms-2 text-sm font-medium">Price Given By Google</p> </label> </div> <ErrorMessage name="priceGivenByGoogle" component="div" className="error" /> <h4>Customer Details:</h4> <div className="grid grid-cols-2 gap-6 align-center mb-5 frm1"> <div className=""> <label className="block mb-2">Company Name</label> <input type="text" id="" className="block w-full p-2.5 bg-[#F7F7F7]" placeholder="" name="customerCompanyName" value={values.customerCompanyName} => setFieldValue("customerCompanyName", e.target.value)} /> <ErrorMessage name="customerCompanyName" component="div" className="error" /> </div> <div className=""> <label className="block mb-2">Customer Name</label> <input type="text" id="" className="block w-full p-2.5" name="customerName" value={values.customerName} => setFieldValue("customerName", e.target.value)} /> <ErrorMessage name="customerName" component="div" className="error" /> </div> </div> <div className="grid grid-cols-2 gap-6 align-center mb-5 frm1"> <div className=""> <label className="block mb-2">Customer Email</label> <input type="text" id="" className="block w-full p-2.5" placeholder="" name="email" value={values.email} => setFieldValue("email", e.target.value)} /> <ErrorMessage name="email" component="div" className="error" /> </div> <div className=""> <label className="block mb-2">Customer Domain</label> <input type="text" id="" className="block w-full p-2.5" placeholder="" name="customerDomain" value={values.customerDomain} => setFieldValue("customerDomain", e.target.value)} /> <ErrorMessage name="customerDomain" component="div" className="error" /> </div> </div> <h4>Product Details:</h4> <GWSProductItemForm addProductItem={addProductItem} googleGivenPriceShow={googleGivenPriceShow} productPriceDetails1={productPriceDetails1} productPriceDetails2={productPriceDetails2} /> <div className="seleted-product-list"> <FieldArray name="products"> {({ push, remove }) => values.products.map((product, index) => ( <div className="list" key={index}> <div className="grid grid-cols-5 gap-3 align-center selected"> <div className="col-span-2"> <label className="block mb-2">Product Type</label> <Field as="select" id={`products[${index}].productType`} name={`products[${index}].productType`} className="p-2.5 w-full peri-selected" any) => handleProductTypeChange(index, e.target.value, setFieldValue)} > <option value="business">Business</option> <option value="enterprise">Enterprise</option> <option value="frontline">Frontline</option> </Field> <ErrorMessage name={`products[${index}].productType`} component="div" className="error" /> </div> <div className="col-span-2"> <label className="block mb-2">Sub Plan</label> {/* <Field as="select" id={`products[${index}].subPlan`} name={`products[${index}].subPlan`} className="p-2.5 w-full peri-selected" any) => handleSubPlanChange(index, e.target.value, setFieldValue)} > {product.productType && populateSubplans(product.productType).map((subPlan: any, subindex: any) => ( <option key={subindex} value={subPlan}> {subPlan} </option> ))} </Field> */} { product.productType && <> <Field as="select" id={`products[${index}].subPlan`} name={`products[${index}].subPlan`} className="p-2.5 w-full peri-selected" value={values.products[index].subPlan || ""} any) => handleSubPlanChange(index, e.target.value, setFieldValue)} > {product.productType === "business" && ( <> <option value="starter">Starter</option> <option value="standard">Standard</option> <option value="plus">Plus</option> </> )} {product.productType === "enterprise" && ( <> <option value="starter">Starter</option> <option value="standard">Standard</option> <option value="plus">Plus</option> </> )} {product.productType === "frontline" && ( <> <option value="basic">Basic</option> <option value="plus">Plus</option> </> )} </Field> <ErrorMessage name={`products[${index}].subPlan`} component="div" className="error" /> </> } </div> <div className="col-span-1"> <label className="block mb-2">Licenses</label> <Field type="number" value={values.products[index].licenses || ""} id={`products[${index}].licenses`} name={`products[${index}].licenses`} className="block w-full p-2.5" /> {product?.licenses === "" && <p className="error">Licenses are required</p>} <ErrorMessage name={`products[${index}].licenses`} component="div" className="error" /> </div> </div> <div className="grid grid-cols-5 gap-3 align-center mb-5 selected2"> {googleGivenPriceShow ? ( <div className="col-span-2"> <label className="block mb-2">Google price</label> <Field type="number" value={values.products[index].googlePrice || ""} id={`products[${index}].googlePrice`} name={`products[${index}].googlePrice`} className="block w-full p-2.5" /> {product?.googlePrice === "" && <p className="error">Google Price is required</p>} </div> ) : null} <div className="col-span-2"> <label className="block mb-2">Customer price</label> <Field type="number" value={values.products[index].CustomerGivenPrice || ""} id={`product[${index}].CustomerGivenPrice`} name={`product[${index}].CustomerGivenPrice`} className="block w-full p-2.5" any) => handleCustomerGivenPriceChange(index, e.target.value, setFieldValue)} /> {product?.CustomerGivenPrice === "" && <p className="error">Customer Given Price is required</p>} </div> <div className="col-span-1"> <div className="flex"> <button className="n-user2" type="button" => remove(index)}> Remove </button> </div> </div> </div> </div> )) } </FieldArray> {/* {gwsPriceFormInitValues.products.length === 0 || errors.products ? ( <> <ErrorMessage name="products" component="div" className="error" /> {errors.products ? ( <span className="error" style={{ fontSize: 12 }}> Please click above add button </span> ) : null} </> ) : null} */} </div> <pre>{JSON.stringify(errors, undefined, 2)}</pre> <div className="flex justify-center mt-7"> <button type="submit" className="n-user flex align-center" id="calculate" name="calculate"> Calculate </button> </div> </Form> )} </Formik> </div> <div className="col-span-8 p-4"> <div className="accordian"> <Accordian allData={allData} isAccordionOpen={isAccordionOpen} activeKeys={activeKeys} invoiceData={invoiceData} /> </div> </div> </div> </div> </div>
); };
export default Newproposal;