import React, { useState, useMemo, useCallback } from 'react'; import * as Yup from 'yup'; import { useFormik } from 'formik'; import { FormGroup, MenuItem, Intent, InputGroup, HTMLSelect, Button, Classes, Checkbox, } from '@blueprintjs/core'; import { Row, Col } from 'react-grid-system'; import { FormattedMessage as T, useIntl } from 'react-intl'; import { Select } from '@blueprintjs/select'; import AppToaster from 'components/AppToaster'; import AccountsConnect from 'connectors/Accounts.connector'; import ItemsConnect from 'connectors/Items.connect'; import { compose } from 'utils'; import ErrorMessage from 'components/ErrorMessage'; import classNames from 'classnames'; import Icon from 'components/Icon'; import ItemCategoryConnect from 'connectors/ItemsCategory.connect'; import MoneyInputGroup from 'components/MoneyInputGroup'; import { useHistory } from 'react-router-dom'; import Dragzone from 'components/Dragzone'; import MediaConnect from 'connectors/Media.connect'; import useMedia from 'hooks/useMedia'; const ItemForm = ({ requestSubmitItem, accounts, categories, requestSubmitMedia, requestDeleteMedia, }) => { const [selectedAccounts, setSelectedAccounts] = useState({}); const history = useHistory(); const { formatMessage } = useIntl(); const { files, setFiles, saveMedia, deletedFiles, setDeletedFiles, deleteMedia, } = useMedia({ saveCallback: requestSubmitMedia, deleteCallback: requestDeleteMedia, }); const ItemTypeDisplay = useMemo( () => [ { value: null, label: formatMessage({id:'select_item_type'}) }, { value: 'service', label: formatMessage({id:'service'}) }, { value: 'inventory', label: formatMessage({id:'inventory'}) }, { value: 'non-inventory', label: formatMessage({id:'non_inventory'}) }, ], [] ); const validationSchema = Yup.object().shape({ active: Yup.boolean(), name: Yup.string().required().label(formatMessage({id:'item_name_'})), type: Yup.string().trim().required().label(formatMessage({id:'item_type_'})), sku: Yup.string().trim(), cost_price: Yup.number(), sell_price: Yup.number(), cost_account_id: Yup.number().required().label(formatMessage({id:'cost_account_id'})), sell_account_id: Yup.number().required().label(formatMessage({id:'sell_account_id'})), inventory_account_id: Yup.number().when('type', { is: (value) => value === 'inventory', then: Yup.number().required(), otherwise: Yup.number().nullable(), }), category_id: Yup.number().nullable(), stock: Yup.string() || Yup.boolean(), }); const initialValues = useMemo( () => ({ active: true, name: '', type: '', sku: '', cost_price: 0, sell_price: 0, cost_account_id: null, sell_account_id: null, inventory_account_id: null, category_id: null, note: '', }), [] ); const { getFieldProps, setFieldValue, values, touched, errors, handleSubmit, isSubmitting, } = useFormik({ enableReinitialize: true, validationSchema: validationSchema, initialValues: { ...initialValues, }, onSubmit: (values, { setSubmitting }) => { const saveItem = (mediaIds) => { const formValues = { ...values, media_ids: mediaIds }; return requestSubmitItem(formValues).then((response) => { AppToaster.show({ message: formatMessage({ id: 'service_has_been_successful_created', }, { name: values.name, service: formatMessage({ id: 'item' }), }), intent: Intent.SUCCESS, }); }); }; Promise.all([saveMedia(), deleteMedia()]).then( ([savedMediaResponses]) => { const mediaIds = savedMediaResponses.map((res) => res.data.media.id); return saveItem(mediaIds); } ); }, }); const accountItem = useCallback( (item, { handleClick }) => ( ), [] ); // Filter Account Items const filterAccounts = (query, account, _index, exactMatch) => { const normalizedTitle = account.name.toLowerCase(); const normalizedQuery = query.toLowerCase(); if (exactMatch) { return normalizedTitle === normalizedQuery; } else { return `${account.code} ${normalizedTitle}`.indexOf(normalizedQuery) >= 0; } }; const onItemAccountSelect = useCallback( (filedName) => { return (account) => { setSelectedAccounts({ ...selectedAccounts, [filedName]: account, }); setFieldValue(filedName, account.id); }; }, [setFieldValue, selectedAccounts] ); const categoryItem = useCallback( (item, { handleClick }) => ( ), [] ); const getSelectedAccountLabel = useCallback( (fieldName, defaultLabel) => { return typeof selectedAccounts[fieldName] !== 'undefined' ? selectedAccounts[fieldName].name : defaultLabel; }, [selectedAccounts] ); const requiredSpan = useMemo(() => *, []); const infoIcon = useMemo(() => , []); const handleMoneyInputChange = (fieldKey) => (e, value) => { setFieldValue(fieldKey, value); }; const initialAttachmentFiles = useMemo(() => { return []; }, []); const handleDropFiles = useCallback((_files) => { setFiles(_files.filter((file) => file.uploaded === false)); }, []); const handleDeleteFile = useCallback( (_deletedFiles) => { _deletedFiles.forEach((deletedFile) => { if (deletedFile.uploaded && deletedFile.metadata.id) { setDeletedFiles([...deletedFiles, deletedFile.metadata.id]); } }); }, [setDeletedFiles, deletedFiles] ); const handleCancelClickBtn = () => { history.goBack(); }; return (
} labelInfo={requiredSpan} className={'form-group--item-type'} intent={errors.type && touched.type && Intent.DANGER} helperText={ } inline={true} > } labelInfo={requiredSpan} className={'form-group--item-name'} intent={errors.name && touched.name && Intent.DANGER} helperText={ } inline={true} > } labelInfo={infoIcon} className={'form-group--item-sku'} intent={errors.sku && touched.sku && Intent.DANGER} helperText={ } inline={true} > } labelInfo={infoIcon} inline={true} intent={ errors.category_id && touched.category_id && Intent.DANGER } helperText={ } className={classNames( 'form-group--select-list', 'form-group--category', Classes.FILL )} > } defaultChecked={values.active} {...getFieldProps('active')} />

} className={'form-group--item-selling-price'} intent={ errors.selling_price && touched.selling_price && Intent.DANGER } helperText={ } inline={true} > } labelInfo={infoIcon} inline={true} intent={ errors.sell_account_id && touched.sell_account_id && Intent.DANGER } helperText={ } className={classNames( 'form-group--sell-account', 'form-group--select-list', Classes.FILL )} >

} className={'form-group--item-cost-price'} intent={errors.cost_price && touched.cost_price && Intent.DANGER} helperText={ } inline={true} > } labelInfo={infoIcon} inline={true} intent={ errors.cost_account_id && touched.cost_account_id && Intent.DANGER } helperText={ } className={classNames( 'form-group--cost-account', 'form-group--select-list', Classes.FILL )} >

} inline={true} intent={ errors.inventory_account_id && touched.inventory_account_id && Intent.DANGER } helperText={ } className={classNames( 'form-group--item-inventory_account', 'form-group--select-list', Classes.FILL )} > } className={'form-group--item-stock'} inline={true} >
); }; export default compose( AccountsConnect, ItemsConnect, ItemCategoryConnect, MediaConnect )(ItemForm);