diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/DealInfoView.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/DealInfoView.tsx new file mode 100644 index 0000000..0e752c1 --- /dev/null +++ b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/DealInfoView.tsx @@ -0,0 +1,22 @@ +import { Flex, Stack } from "@mantine/core"; +import DealServicesTable from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/DealServicesTable"; +import ProductsActions from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/ProductsActions/ProductsActions"; +import TotalPriceLabel from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/TotalPriceLabel/TotalPriceLabel"; +import styles from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/FulfillmentBaseTab.module.css"; + +const DealInfoView = () => ( + + + + + + + +); + +export default DealInfoView; diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/DealServicesTable.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/DealServicesTable.tsx similarity index 78% rename from src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/DealServicesTable.tsx rename to src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/DealServicesTable.tsx index e19f7e8..190380a 100644 --- a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/DealServicesTable.tsx +++ b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/DealServicesTable.tsx @@ -1,10 +1,10 @@ import { FC } from "react"; import { Flex, ScrollArea } from "@mantine/core"; -import DealServiceRow from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/components/DealServiceRow"; -import DealServicesTitle from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/components/DealServicesTitle"; -import DealServicesTotalLabel from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/components/DealServicesTotalLabel"; -import ServicesActions from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/components/ServicesActions"; +import DealServicesTitle from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/components/DealServicesTitle"; +import DealServicesTotalLabel from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/components/DealServicesTotalLabel"; +import ServicesActions from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/components/DealServicesTable/components/ServicesActions"; import { useFulfillmentBaseContext } from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/contexts/FulfillmentBaseContext"; +import DealServiceRow from "./components/DealServiceRow"; const DealServicesTable: FC = () => { const { dealServicesList, dealServicesCrud } = useFulfillmentBaseContext(); @@ -15,7 +15,7 @@ const DealServicesTable: FC = () => { + h={"78vh"}> { + const { + dealServicesList: { dealServices }, + dealProductsList: { dealProducts }, + } = useFulfillmentBaseContext(); + + const totalPrice = useMemo(() => { + const productServicesPrice = dealProducts.reduce( + (acc, row) => + acc + + row.productServices.reduce( + (acc2, row2) => acc2 + row2.price * row.quantity, + 0 + ), + 0 + ); + const cardServicesPrice = dealServices.reduce( + (acc, row) => acc + row.price * row.quantity, + 0 + ); + return cardServicesPrice + productServicesPrice; + }, [dealServices, dealProducts]); + + return ( + + + Общая стоимость всех услуг: {totalPrice.toLocaleString("ru")}₽ + + + ); +}; + +export default TotalPriceLabel; diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/FulfillmentBaseTabBody/FulfillmentBaseTabBody.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/FulfillmentBaseTabBody/FulfillmentBaseTabBody.tsx index d54cc06..d19662f 100644 --- a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/FulfillmentBaseTabBody/FulfillmentBaseTabBody.tsx +++ b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/FulfillmentBaseTabBody/FulfillmentBaseTabBody.tsx @@ -1,9 +1,7 @@ import { Flex, ScrollArea, Stack } from "@mantine/core"; -import DealServicesTable from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealServicesTable/DealServicesTable"; -import ProductsActions from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/ProductsActions/ProductsActions"; +import DealInfoView from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/DealInfoView/DealInfoView"; import ProductView from "@/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/ProductView/ProductView"; import { useFulfillmentBaseContext } from "../../contexts/FulfillmentBaseContext"; -import styles from "../../FulfillmentBaseTab.module.css"; const FulfillmentBaseTabBody = () => { const { dealProductsList } = useFulfillmentBaseContext(); @@ -25,13 +23,7 @@ const FulfillmentBaseTabBody = () => { ))} - - - - + ); }; diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/GeneralDataForm/GeneralDataForm.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/GeneralDataForm/GeneralDataForm.tsx deleted file mode 100644 index 6e948b1..0000000 --- a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/GeneralDataForm/GeneralDataForm.tsx +++ /dev/null @@ -1,115 +0,0 @@ -import ShippingWarehouseAutocomplete - from "../../../../../../components/Selects/ShippingWarehouseAutocomplete/ShippingWarehouseAutocomplete.tsx"; -import { CardService, ShippingWarehouseSchema } from "../../../../../../client"; -import { useForm } from "@mantine/form"; -import { useCardPageContext } from "../../../../../../pages/CardsPage/contexts/CardPageContext.tsx"; -import { Button, Checkbox, Stack } from "@mantine/core"; -import { notifications } from "../../../../../../shared/lib/notifications.ts"; -import { useEffect, useState } from "react"; -import { isEqual } from "lodash"; -import { useSelector } from "react-redux"; -import { RootState } from "../../../../../../redux/store.ts"; - - -type GeneralDataFormType = { - shippingWarehouse?: ShippingWarehouseSchema | null | string; - isServicesProfitAccounted: boolean; -} - -const GeneralDataForm = () => { - const { selectedCard: card, refetchCard } = useCardPageContext(); - const { isDealsViewer } = useSelector((state: RootState) => state.auth); - if (!card) return <>; - - const [initialValues, setInitialValues] = useState(card); - - const form = useForm({ - initialValues, - }); - - useEffect(() => { - const data = card ?? {}; - setInitialValues(data); - form.setValues(data); - }, [card]); - - const isShippingWarehouse = ( - value: ShippingWarehouseSchema | string | null | undefined, - ): value is ShippingWarehouseSchema => { - return !!value && !["string"].includes(typeof value); - }; - - const onSubmit = (values: GeneralDataFormType) => { - if (!card) return; - - const shippingWarehouse = isShippingWarehouse(values.shippingWarehouse) - ? values.shippingWarehouse.name - : values.shippingWarehouse; - - CardService.updateProductsAndServicesGeneralInfo({ - requestBody: { - cardId: card.id, - data: { - ...values, - shippingWarehouse, - }, - }, - }) - .then(({ ok, message }) => { - if (!ok) { - notifications.error({ message }); - return; - } - - refetchCard(); - }) - .catch(err => console.log(err)); - }; - - return ( -
onSubmit(values))}> - - { - if (isShippingWarehouse(event)) { - form.getInputProps( - "shippingWarehouse", - ).onChange(event.name); - return; - } - form.getInputProps( - "shippingWarehouse", - ).onChange(event); - }} - readOnly={isDealsViewer} - /> - {!isDealsViewer && ( - <> - - - - )} - -
- ); -}; - -export default GeneralDataForm; diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PaymentLinkButton/PaymentLinkButton.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PaymentLinkButton/PaymentLinkButton.tsx deleted file mode 100644 index 87cec49..0000000 --- a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PaymentLinkButton/PaymentLinkButton.tsx +++ /dev/null @@ -1,68 +0,0 @@ -import { CardSchema } from "../../../../../../client"; -import ButtonCopy from "../../../../../../components/ButtonCopy/ButtonCopy.tsx"; -import { ButtonCopyControlled } from "../../../../../../components/ButtonCopyControlled/ButtonCopyControlled.tsx"; -import { getCurrentDateTimeForFilename } from "../../../../../../shared/lib/date.ts"; -import FileSaver from "file-saver"; -import { Button, Popover, Stack } from "@mantine/core"; - -type Props = { - card: CardSchema; -} - -const PaymentLinkButton = ({ card }: Props) => { - if ((!card.billRequests || card.billRequests.length === 0) && (!card?.group?.billRequests || card?.group?.billRequests.length === 0)) { - return ( - { - const date = - getCurrentDateTimeForFilename(); - FileSaver.saveAs( - `${import.meta.env.VITE_API_URL}/card/billing-document/${card.id}`, - `bill_${card.id}_${date}.pdf`, - ); - }} - copied={false} - onCopiedLabel={"Ссылка скопирована в буфер обмена"} - > - Ссылка на оплату (PDF) - - ); - } - - const requests = (card?.group ? card?.group?.billRequests : card.billRequests) ?? []; - const urls = requests.map(request => request.pdfUrl).filter(url => url !== null); - - if (urls.length === 1) { - return ( - - Ссылка на оплату - - ); - } - - return ( - - - - - - - {urls.map((url, i) => ( - - {`Ссылка на оплату (часть ${String(i + 1)})`} - - ))} - - - - ); -}; - -export default PaymentLinkButton; diff --git a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PrintDealBarcodesButton/PrintDealBarcodesButton.tsx b/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PrintDealBarcodesButton/PrintDealBarcodesButton.tsx deleted file mode 100644 index a465329..0000000 --- a/src/modules/dealModules/dealEditorTabs/FulfillmentBaseTab/components/PrintDealBarcodesButton/PrintDealBarcodesButton.tsx +++ /dev/null @@ -1,63 +0,0 @@ -import { ActionIcon, Group, Tooltip } from "@mantine/core"; -import styles from "../../../../../../pages/CardsPage/ui/CardsPage.module.css"; -import { CardSchema, CardService } from "../../../../../../client"; -import { base64ToBlob } from "../../../../../../shared/lib/utils.ts"; -import { notifications } from "../../../../../../shared/lib/notifications.ts"; -import { IconBarcode, IconPrinter } from "@tabler/icons-react"; - - -type Props = { - card: CardSchema; -} - -const PrintDealBarcodesButton = ({ card }: Props) => { - return ( - - - { - const response = - await CardService.getCardProductsBarcodesPdf({ - requestBody: { - cardId: card.id, - }, - }); - const pdfBlob = base64ToBlob( - response.base64String, - response.mimeType, - ); - const pdfUrl = URL.createObjectURL(pdfBlob); - const pdfWindow = window.open(pdfUrl); - if (!pdfWindow) { - notifications.error({ message: "Ошибка" }); - return; - } - pdfWindow.onload = () => { - pdfWindow.print(); - }; - }} - variant={"default"}> - - - - - { - const pdfWindow = window.open( - `${import.meta.env.VITE_API_URL}/card/tech-spec/${card.id}`, - ); - if (!pdfWindow) return; - pdfWindow.print(); - }} - variant={"default"}> - - - - - ); -}; - -export default PrintDealBarcodesButton;