Add Waste at Product Recipe
This commit is contained in:
parent
aa2946e627
commit
fab31f1540
@ -42,6 +42,7 @@ export interface ProductRecipe {
|
||||
variant_id: string | null
|
||||
ingredient_id: string
|
||||
quantity: number
|
||||
waste: number
|
||||
created_at: string
|
||||
updated_at: string
|
||||
product: Product
|
||||
@ -54,6 +55,7 @@ export interface ProductRecipeRequest {
|
||||
ingredient_id: string
|
||||
quantity: number
|
||||
outlet_id: string | null
|
||||
waste: number
|
||||
}
|
||||
|
||||
export interface IngredientUnit {
|
||||
|
||||
@ -11,8 +11,6 @@ import Typography from '@mui/material/Typography'
|
||||
// Third-party Imports
|
||||
import PerfectScrollbar from 'react-perfect-scrollbar'
|
||||
|
||||
// Type Imports
|
||||
|
||||
// Component Imports
|
||||
import CustomTextField from '@core/components/mui/TextField'
|
||||
import { Autocomplete } from '@mui/material'
|
||||
@ -25,6 +23,7 @@ import { useOutlets } from '../../../../../services/queries/outlets'
|
||||
import { Product } from '../../../../../types/services/product'
|
||||
import { ProductRecipeRequest } from '../../../../../types/services/productRecipe'
|
||||
import { resetProductVariant } from '../../../../../redux-store/slices/productRecipe'
|
||||
import { IngredientItem } from '@/types/services/ingredient'
|
||||
|
||||
type Props = {
|
||||
open: boolean
|
||||
@ -38,7 +37,8 @@ const initialData = {
|
||||
product_id: '',
|
||||
variant_id: '',
|
||||
ingredient_id: '',
|
||||
quantity: 0
|
||||
quantity: 0,
|
||||
waste: 0
|
||||
}
|
||||
|
||||
const AddRecipeDrawer = (props: Props) => {
|
||||
@ -55,23 +55,45 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
const [ingredientDebouncedInput] = useDebounce(ingredientInput, 500)
|
||||
const [formData, setFormData] = useState<ProductRecipeRequest>(initialData)
|
||||
|
||||
// Add state untuk menyimpan selected ingredient
|
||||
const [selectedIngredient, setSelectedIngredient] = useState<IngredientItem | null>(null)
|
||||
|
||||
const { data: outlets, isLoading: outletsLoading } = useOutlets({
|
||||
search: outletDebouncedInput
|
||||
})
|
||||
|
||||
// Modifikasi query ingredients dengan enabled condition
|
||||
const { data: ingredients, isLoading: ingredientsLoading } = useIngredients({
|
||||
search: ingredientDebouncedInput
|
||||
})
|
||||
|
||||
const outletOptions = useMemo(() => outlets?.outlets || [], [outlets])
|
||||
const ingredientOptions = useMemo(() => ingredients?.data || [], [ingredients])
|
||||
|
||||
// Perbaiki ingredient options untuk include selected ingredient
|
||||
const ingredientOptions = useMemo(() => {
|
||||
const options = ingredients?.data || []
|
||||
|
||||
// Jika ada selected ingredient dan tidak ada di current options, tambahkan
|
||||
if (selectedIngredient && !options.find(opt => opt.id === selectedIngredient.id)) {
|
||||
return [selectedIngredient, ...options]
|
||||
}
|
||||
|
||||
return options
|
||||
}, [ingredients, selectedIngredient])
|
||||
|
||||
const { createProductRecipe, updateProductRecipe } = useProductRecipesMutation()
|
||||
|
||||
useEffect(() => {
|
||||
if (currentProductRecipe.id) {
|
||||
setFormData(currentProductRecipe)
|
||||
|
||||
// Set selected ingredient dari current product recipe
|
||||
const currentIngredient = ingredients?.data?.find(ing => ing.id === currentProductRecipe.ingredient_id)
|
||||
if (currentIngredient) {
|
||||
setSelectedIngredient(currentIngredient)
|
||||
}
|
||||
}
|
||||
}, [currentProductRecipe])
|
||||
}, [currentProductRecipe, ingredients])
|
||||
|
||||
const handleSubmit = (e: any) => {
|
||||
e.preventDefault()
|
||||
@ -101,24 +123,16 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
handleClose()
|
||||
dispatch(resetProductVariant())
|
||||
setFormData(initialData)
|
||||
}
|
||||
|
||||
const handleInputChange = (e: any) => {
|
||||
setFormData({
|
||||
...formData,
|
||||
[e.target.name]: e.target.value
|
||||
})
|
||||
setSelectedIngredient(null) // Reset selected ingredient
|
||||
setIngredientInput('') // Reset input
|
||||
}
|
||||
|
||||
const setTitleDrawer = (recipe: any) => {
|
||||
const addOrEdit = currentProductRecipe.id ? 'Edit ' : 'Add '
|
||||
|
||||
let title = 'Original'
|
||||
|
||||
if (recipe?.name) {
|
||||
title = recipe?.name
|
||||
}
|
||||
|
||||
return addOrEdit + title
|
||||
}
|
||||
|
||||
@ -144,13 +158,14 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
<Typography color='text.primary' className='font-medium'>
|
||||
Basic Information
|
||||
</Typography>
|
||||
|
||||
<Autocomplete
|
||||
options={outletOptions}
|
||||
loading={outletsLoading}
|
||||
getOptionLabel={option => option.name}
|
||||
value={outletOptions.find(p => p.id === formData.outlet_id) || null}
|
||||
onInputChange={(event, newOutlettInput) => {
|
||||
setOutletInput(newOutlettInput)
|
||||
onInputChange={(event, newOutletInput) => {
|
||||
setOutletInput(newOutletInput)
|
||||
}}
|
||||
onChange={(event, newValue) => {
|
||||
setFormData({
|
||||
@ -161,7 +176,6 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
renderInput={params => (
|
||||
<CustomTextField
|
||||
{...params}
|
||||
className=''
|
||||
label='Outlet'
|
||||
fullWidth
|
||||
InputProps={{
|
||||
@ -171,24 +185,35 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
{/* Perbaiki Autocomplete untuk Ingredients */}
|
||||
<Autocomplete
|
||||
options={ingredientOptions || []}
|
||||
loading={ingredientsLoading}
|
||||
getOptionLabel={option => option.name}
|
||||
value={ingredientOptions?.find(p => p.id === formData.ingredient_id) || null}
|
||||
value={selectedIngredient}
|
||||
onInputChange={(event, newIngredientInput) => {
|
||||
setIngredientInput(newIngredientInput)
|
||||
}}
|
||||
onChange={(event, newValue) => {
|
||||
setSelectedIngredient(newValue) // Set selected ingredient
|
||||
setFormData({
|
||||
...formData,
|
||||
ingredient_id: newValue?.id || ''
|
||||
})
|
||||
|
||||
// Clear input search setelah selection
|
||||
if (newValue) {
|
||||
setIngredientInput('')
|
||||
}
|
||||
}}
|
||||
// Tambahkan props untuk mencegah clear on blur
|
||||
clearOnBlur={false}
|
||||
// Handle case ketika input kosong tapi ada selected value
|
||||
inputValue={selectedIngredient ? selectedIngredient.name : ingredientInput}
|
||||
renderInput={params => (
|
||||
<CustomTextField
|
||||
{...params}
|
||||
className=''
|
||||
label='Ingredient'
|
||||
fullWidth
|
||||
InputProps={{
|
||||
@ -198,6 +223,18 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
{/* Unit Field - Disabled, value from selected ingredient */}
|
||||
<CustomTextField
|
||||
label='Unit'
|
||||
fullWidth
|
||||
disabled
|
||||
value={selectedIngredient?.unit?.name || ''}
|
||||
InputProps={{
|
||||
readOnly: true
|
||||
}}
|
||||
/>
|
||||
|
||||
<CustomTextField
|
||||
type='number'
|
||||
label='Quantity'
|
||||
@ -205,6 +242,15 @@ const AddRecipeDrawer = (props: Props) => {
|
||||
value={formData.quantity}
|
||||
onChange={e => setFormData({ ...formData, quantity: Number(e.target.value) })}
|
||||
/>
|
||||
|
||||
<CustomTextField
|
||||
type='number'
|
||||
label='Waste'
|
||||
fullWidth
|
||||
value={formData.waste}
|
||||
onChange={e => setFormData({ ...formData, waste: Number(e.target.value) })}
|
||||
/>
|
||||
|
||||
<div className='flex items-center gap-4'>
|
||||
<Button
|
||||
variant='contained'
|
||||
|
||||
@ -161,7 +161,7 @@ const ProductDetail = () => {
|
||||
<TableCell className='font-semibold text-center'>
|
||||
<div className='flex items-center justify-center gap-2'>
|
||||
<i className='tabler-package text-blue-600' />
|
||||
Stock Available
|
||||
Waste
|
||||
</div>
|
||||
</TableCell>
|
||||
<TableCell className='font-semibold text-right'>
|
||||
@ -197,12 +197,7 @@ const ProductDetail = () => {
|
||||
</TableCell>
|
||||
<TableCell className='text-center'>{formatCurrency(item.ingredient.cost)}</TableCell>
|
||||
<TableCell className='text-center'>
|
||||
<Chip
|
||||
label={item.ingredient.stock}
|
||||
size='small'
|
||||
color={item.ingredient.stock > 5 ? 'success' : 'warning'}
|
||||
variant='outlined'
|
||||
/>
|
||||
<Chip label={item.waste ?? 0} size='small' color={'success'} variant='outlined' />
|
||||
</TableCell>
|
||||
<TableCell className='text-right font-medium'>
|
||||
{formatCurrency(item.ingredient.cost * item.quantity)}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user