import { BackHistoryButton, CancelButton, ErrorOverlay, LoadingOverlay, SubmitButton, } from "@/components"; import { calculateQuoteItemTotals, calculateQuoteTotals } from "@/lib/calc"; import { useUrlId } from "@/lib/hooks/useUrlId"; import { Badge, Button, Form, Tabs, TabsContent, TabsList, TabsTrigger } from "@/ui"; import { CurrencyData, IGetQuote_Response_DTO, Language } from "@shared/contexts"; import { t } from "i18next"; import { useEffect, useMemo, useState } from "react"; import { SubmitHandler, useForm } from "react-hook-form"; import { useNavigate } from "react-router-dom"; import { toast } from "react-toastify"; import { QuotePricesResume } from "./components"; import { QuoteDetailsCardEditor, QuoteGeneralCardEditor } from "./components/editors"; import { useQuotes } from "./hooks"; /*type QuoteDataForm = Omit & { items: IGetQuote_QuoteItem_Response_DTO; };*/ type QuoteDataForm = IGetQuote_Response_DTO; // eslint-disable-next-line @typescript-eslint/no-unused-vars export const QuoteEdit = () => { const navigate = useNavigate(); const quoteId = useUrlId(); const [activeTab, setActiveTab] = useState("general"); const [quoteCurrency, setQuoteCurrency] = useState( CurrencyData.createDefaultCode().object ); const [quoteLanguage, setQuoteLanguage] = useState(Language.createDefaultCode().object); /*const { data: userIdentity } = useGetIdentity(); console.log(userIdentity); const { flag } = useLocalization({ locale: userIdentity?.language ?? "es-es", }); console.log(flag);*/ const { useOne, useUpdate } = useQuotes(); const { data, status, error: queryError } = useOne(quoteId); const defaultValues = useMemo( () => ({ date: "", reference: "", customer_information: "", lang_code: "", currency_code: "", payment_method: "", notes: "", validity: "", subtotal_price: { amount: undefined, scale: 2, currency_code: data?.currency_code ?? quoteCurrency.code, }, discount: { amount: undefined, scale: 0, }, total_price: { amount: undefined, scale: 2, currency_code: data?.currency_code ?? quoteCurrency.code, }, items: [ { description: "", quantity: { amount: 1, scale: 0, }, unit_price: { amount: null, scale: 4, currency_code: data?.currency_code ?? quoteCurrency.code, }, subtotal_price: { amount: null, scale: 4, currency_code: data?.currency_code ?? quoteCurrency.code, }, discount: { amount: null, scale: 2, }, total_price: { amount: null, scale: 4, currency_code: data?.currency_code ?? quoteCurrency.code, }, }, ], }), [data, quoteCurrency] ); const { mutate } = useUpdate(String(quoteId)); const form = useForm({ mode: "onBlur", values: data, defaultValues, //shouldUnregister: true, }); const { watch, getValues, setValue, formState } = form; /*const { clear } = useFormPersist( "quote-edit", { watch, setValue, }, { storage: window.localStorage, // default window.sessionStorage //exclude: ['foo'] } );*/ const { isSubmitting } = formState; const onSubmit: SubmitHandler = async (data) => { // Transformación del form -> typo de request console.log(data); mutate(data, { onError: (error) => { console.debug(error); toast.error(error.message); //alert(error.message); }, //onSettled: () => {}, onSuccess: () => { toast("Guardado!"); //clear(); }, }); }; /* useEffect(() => { // eslint-disable-next-line @typescript-eslint/no-unused-vars const { unsubscribe } = watch((_, { name, type }) => { const value = getValues(); console.log(name); if (name) { if (name === "currency_code") { setQuoteCurrency( CurrencyData.createFromCode(value.currency_code ?? CurrencyData.DEFAULT_CURRENCY_CODE) .object ); } if (name === "lang_code") { setQuoteLanguage( Language.createFromCode(value.lang_code ?? Language.DEFAULT_LANGUAGE_CODE).object ); } if (name === "items") { console.log(">> Recalculo todas las líneas"); const { items } = value; let quoteSubtotal = MoneyValue.create({ amount: 0, scale: 4, }).object; // Recálculo líneas items && items.map((item, index) => { const itemTotals = calculateQuoteItemTotals(item); quoteSubtotal = quoteSubtotal.add(itemTotals.totalPrice); setValue(`items.${index}.subtotal_price`, itemTotals.subtotalPrice.toObject()); setValue(`items.${index}.total_price`, itemTotals.totalPrice.toObject()); }); // Recálculo completo setValue("subtotal_price", quoteSubtotal.convertScale(2).toObject()); } if (name.endsWith("quantity") || name.endsWith("unit_price") || name.endsWith("discount")) { console.group(">>>>>>>>>>>>>"); const { items } = value; const [, indexString, fieldName] = String(name).split("."); const index = parseInt(indexString); console.group(">> Voy a recalcular la línea ", index, items[index]); const itemTotals_1 = calculateQuoteItemTotals(items[index]); setValue(`items.${index}.subtotal_price`, itemTotals_1.subtotalPrice.toObject()); setValue(`items.${index}.total_price`, itemTotals_1.totalPrice.toObject()); console.log(">> Total de la línea -> ", index, itemTotals_1.subtotalPrice.toObject()); console.groupEnd(); // Recálculo completo let quoteSubtotal = MoneyValue.create({ amount: 0, scale: 4, }).object; console.group(">> Recalculo todas las líneas"); items && items.map((item, itemIndex) => { const itemTotals_2 = calculateQuoteItemTotals(item); console.log( ">> Recalculo la linea ", itemIndex, itemTotals_2.subtotalPrice.toObject() ); quoteSubtotal = quoteSubtotal.add(itemTotals_2.totalPrice); setValue(`items.${itemIndex}.subtotal_price`, itemTotals_2.subtotalPrice.toObject()); setValue(`items.${itemIndex}.total_price`, itemTotals_2.totalPrice.toObject()); }); console.log( ">> Gruardo el total en la cabecera ", quoteSubtotal.convertScale(2).toObject() ); // Recálculo completo setValue("subtotal_price", quoteSubtotal.convertScale(2).toObject()); console.groupEnd(); console.groupEnd(); } } }); return () => unsubscribe(); }, [watch, getValues, setValue]);*/ useEffect(() => { // eslint-disable-next-line @typescript-eslint/no-unused-vars const { unsubscribe } = watch((_, { name, type }) => { const quote = getValues(); if (name) { switch (true) { case name === "currency_code": setQuoteCurrency( CurrencyData.createFromCode(quote.currency_code ?? CurrencyData.DEFAULT_CURRENCY_CODE) .object ); break; case name === "lang_code": setQuoteLanguage( Language.createFromCode(quote.lang_code ?? Language.DEFAULT_LANGUAGE_CODE).object ); break; case name === "items": { quote.items && quote.items.map((item, index) => { const quoteItemTotals = calculateQuoteItemTotals(item); setValue(`items.${index}.subtotal_price`, quoteItemTotals.subtotalPrice.toObject()); setValue(`items.${index}.total_price`, quoteItemTotals.totalPrice.toObject()); }); const quoteTotals = calculateQuoteTotals(quote); setValue("subtotal_price", quoteTotals.subtotalPrice.toObject()); setValue("total_price", quoteTotals.totalPrice.toObject()); break; } case name.endsWith("quantity") || name.endsWith("unit_price") || name.endsWith("discount"): { const [, indexString] = String(name).split("."); const index = parseInt(indexString); const quoteItemTotals = calculateQuoteItemTotals(quote.items[index]); setValue(`items.${index}.subtotal_price`, quoteItemTotals.subtotalPrice.toObject()); setValue(`items.${index}.total_price`, quoteItemTotals.totalPrice.toObject()); // Cabecera const quoteTotals = calculateQuoteTotals(quote); setValue("subtotal_price", quoteTotals.subtotalPrice.toObject()); setValue("total_price", quoteTotals.totalPrice.toObject()); break; } default: break; } } }); return () => unsubscribe(); }, [watch, getValues, setValue]); if (isSubmitting) { return ; } if (status === "error") { return ; } if (status !== "success") { return ; } return (

{t("quotes.edit.title")}

{data.status}
navigate("/quotes")}> {t("common.cancel")} {t("common.save")}
{t("quotes.create.tabs.general")} {t("quotes.create.tabs.items")} {/* {t("quotes.create.tabs.history")}*/}
); };