Android_Retail/src/Pages/BookingScreen/Components/BSItemCards/BsBookingitemCard.jsx

6611 lines
248 KiB
JavaScript
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import React, { useCallback, useEffect, useRef, useState } from 'react';
import { shallowEqual, useDispatch, useSelector } from 'react-redux';
import { Badge, DatePicker, Modal, Tooltip, message } from 'antd';
import { ExclamationCircleOutlined, PlusOutlined } from '@ant-design/icons';
import defaultimage from '../../../../Images/defaultItemImg.png';
import FormHeader from '../../../PageComponents/FormHeader';
import {
SelectedGlobalCardColorDetail,
SelectedGlobalCardFont,
StoredSessionData,
getTemplateData,
} from '../../../../Features/ThemeChange/ThemeChange';
import {
GlobalProductSubCategorie,
GlobalItemCard,
getLayoutproductCard,
GlobalOrderCardDetails,
changeOrderCardDetails,
changeSearchedData,
ChangeAllItemData,
GlobalAllItemData,
GlobalCardAccess,
getSelectedFavItems,
GlobalSelectedDatas,
GlobalEditfavItems,
getEditFavItems,
GlobalAccessForOthers,
GlobalAlldat,
Globalothersdata,
GlobalProductCategorie,
getCardDataWithoutSub,
changeothersdata,
ChangeNewQrProduct,
GlobalWSProduct,
GlobalNewQrProduct,
GlobalBookingType,
GlobalSearchData,
getCardDataWithoutSubmodule,
changePreviousOrderLength,
changeHoldOrderDtl,
GlobalReorderHoldDetails,
GlobalUnpaidData,
GlobalWeightScalePort,
GlobalWeightScaleWeight,
changeWeightScaleWeight,
GlobalExpDateforHeight,
GlobalBookingTypeBoth,
GlobalOrderType,
GlobalReorderProductDetails,
getConfigType,
GlobalPayementloader,
GlobalPaymentTransactionNumber,
GlobalSelOption,
PreferenceData,
changeCardData,
GlobaldraggingComponent,
GlobalisAlphabeticFormat,
GlobalBtoBQuickProductTransfer,
changeBtoBQuickProductTransfer,
GlobalRetailWSSalesType,
GlobalisFavClicked,
PostBlockSlots,
GlobalPreviousOrderLength,
GlobalSummeryTotalAmount,
slotTimeStatus,
changeAddBookingDetailsTrigger,
GlobalAddBookingDetailsTrigger,
GlobalGetmultipleSearchDatas,
getmultipleSearch,
GlobalAllBookingType,
} from '../../../../Features/BookingScreen/BookingData/BookingData';
import {
GlobalPreOrderAdditem,
GlobalPreOrderList,
GlobalpreOrderOpen,
changepreOrderList,
} from '../../../../Features/BookingScreen/PreOrder/PreOrder';
import { DefaultModal } from '../../../../Components/Modal/DefaultModal';
import { Messages } from '../../../../Components/Notifications/Messages';
import '../../../../Styles/BookingScreen/Components/BSItemCards/BSItemCard.scss';
import WebFont from 'webfontloader';
import FeaturesFunctionalities from '../BookingFunctionality/FeaturesFunctionalities';
import { isMobile } from 'react-device-detect';
import {
Global_OrderOfferDetail,
Global_PromoCodeOffers,
} from '../../../../Features/Offer/Offer';
import {
DndContext,
useSensor,
useSensors,
PointerSensor,
TouchSensor,
closestCenter,
} from '@dnd-kit/core';
import {
SortableContext,
arrayMove,
rectSortingStrategy,
} from '@dnd-kit/sortable';
import { v4 as uuidv4 } from 'uuid';
// import './styles.css'; // Your styles if any
// Dummy SortableCard component
import { useSortable } from '@dnd-kit/sortable';
import { CSS } from '@dnd-kit/utilities';
import VoiceToTextItemCard from '../../../VoiceToText/VoiceToTextItemCard.jsx';
import { ExtractDateFormate } from '../../../../Services/Others.js';
import {
changeFullOfferAppliedProducts,
changeOfferAppliedProductsForMembership,
GlobalOfferAppliedProducts,
} from '../../../../Features/Offer/Offernew/BookingOffernew.js';
import { useSaleswiseOfferWatcher } from './SalesWiseOffer.jsx';
import { ApplicationPreferences } from '../../../../Features/BrachLogin/BranchLogin.js';
import { useDateStore } from '../../../../Features/BookingScreen/BookingData/DateStore.js';
import { onReceiveNotification } from '../../../../Features/SignalR/signalRClient.js';
import { IoClose } from 'react-icons/io5';
import { MdBlock } from 'react-icons/md';
import dayjs from 'dayjs';
import BSCustomerSelect from '../UtillComponents/BSSelectCustomer.jsx';
import BSNavBarAddUser from '../UtillComponents/BSNavBarAddUser.jsx';
import { FaAngleLeft, FaAngleRight } from 'react-icons/fa';
import useRemoveFromCart from './RemoveFromCartFunction.jsx';
import { LuMinus } from 'react-icons/lu';
import BranchName from '../../Template/BranchName.jsx';
import { FiPlus } from 'react-icons/fi';
export function SortableCard({ id, children, item }) {
const {
attributes,
listeners,
setNodeRef,
transform,
transition,
isDragging,
} = useSortable({ id });
const style = {
transform: CSS.Transform.toString(transform),
transition,
opacity: isDragging ? 0.5 : 1,
// Add mobile-specific styling for better touch interaction
// touchAction: 'none', // Prevents default touch behaviors
userSelect: 'none', // Prevents text selection during drag
// Add mobile-specific cursor and visual feedback
cursor: isMobile ? 'grab' : 'default',
// Add a subtle shadow for mobile to indicate draggability
boxShadow: isMobile && !isDragging ? '0 2px 4px rgba(0,0,0,0.1)' : 'none',
};
const draggingComponent = useSelector(GlobaldraggingComponent);
const allowDrag = draggingComponent === 'card';
return (
<div
ref={setNodeRef}
style={style}
{...(allowDrag ? attributes : {})}
{...(allowDrag ? listeners : {})}
>
{children}
</div>
);
}
const BsBookingitemCard = (props) => {
const voiceTriggerRef = useRef(null);
const unsubscribeRef = useRef(null);
const AllBookingType = useSelector(GlobalAllBookingType);
const { removeFromCart, clearAllItems, decline } = useRemoveFromCart();
const handleRemoveFromCart = async (item) => {
await removeFromCart(item, setPreviousdataLength);
};
const handleDecline = async (item) => {
await decline(item, setPreviousdataLength);
};
const cardFunction = props?.cardFunctionality;
// const applyOffer = useApplyOfferto_CardDetail();
const preferenceDatas = useSelector(PreferenceData, shallowEqual);
const { selectedDate, setSelectedDate, isBulk } = useDateStore();
const preferenceOffer =
preferenceDatas?.[0]?.['SettingDtlDetails']?.find(
(item) => item.SettingIdName === 'Offer'
)?.SettingValue === 'Y';
// const AddCustomerDetails = useSelector(
// GlobalAddCustomerDetails,
// shallowEqual
// );
const offerAppliedProducts = useSelector(
GlobalOfferAppliedProducts,
shallowEqual
);
// const SelectedCust = useSelector(GlobalSelOption, shallowEqual);
const GetmultipleSearchDatas = useSelector(
GlobalGetmultipleSearchDatas,
shallowEqual
);
const RetailWSSalesType = useSelector(GlobalRetailWSSalesType, shallowEqual);
// const CustDetails = SelectedCust ? SelectedCust : AddCustomerDetails?.[0];
const BookingTypeBoth = useSelector(GlobalBookingTypeBoth);
const GPreOrderList = useSelector(GlobalPreOrderList, shallowEqual);
const [modelQty, setModelQty] = useState(false);
const [modelstock, setModelstock] = useState(false);
const [ModalVarient, setModalVarient] = useState(false);
const [QtyIndex, setQtyIndex] = useState(0);
const [VarientIndex, setVarientIndex] = useState(0);
const [expModel, setexpModel] = useState(false);
const [prodexpir, setProdexpir] = useState(false);
const [expVarModel, setexpVarModel] = useState(false);
const [expStockModel, setexpStockModel] = useState(false);
const [initialRun, setInitialRun] = useState(false);
const [Item, setItem] = useState();
const [VarItem, setVarItem] = useState(0);
const [StockItem, setStockItem] = useState();
const [noSubcatCardData, setNoSubcatCardData] = useState();
const [qtydata, setQtydata] = useState();
const PreOrderAdditem = useSelector(GlobalPreOrderAdditem, shallowEqual);
const OrderType = useSelector(GlobalOrderType, shallowEqual);
const ProdSubCat = useSelector(GlobalProductSubCategorie);
const ItemCard = useSelector(GlobalItemCard, shallowEqual);
const selOption = useSelector(GlobalSelOption);
const globaldata = useSelector(GlobalAlldat, shallowEqual);
const TotalAmount = useSelector(GlobalSummeryTotalAmount, shallowEqual);
const { action: quickBranchtoBranchTransfer, selectedProducts } = useSelector(
GlobalBtoBQuickProductTransfer
);
const preOrder = useSelector(GlobalpreOrderOpen, shallowEqual);
const templateData = useSelector(getTemplateData, shallowEqual);
const temp5 = templateData?.BookingLayout?.[0] === 'Layout5';
const OfferCheckedInSetup = templateData?.BookingNavbar?.[1].some(
(item) => item?.OptionName == 'Offer'
);
const globalAllItemdata = useSelector(GlobalAllItemData);
const EditfavItems = useSelector(GlobalEditfavItems);
const BookingType = useSelector(GlobalBookingType);
const ProductSearch = useSelector(GlobalSearchData);
const Discount = useSelector(GlobalOverAllOfferAmt);
const [SelectedProdNames, setSelectedProdNames] = useState(EditfavItems);
const [PreOrderSelectedProdNames, setPreOrderSelectedProdNames] = useState(
[]
);
const PreviousOrderLength = useSelector(GlobalPreviousOrderLength);
const [PreviousdataLength, setPreviousdataLength] =
useState(PreviousOrderLength);
const CardAccess = useSelector(GlobalCardAccess, shallowEqual);
const globalAccessForOthers = useSelector(
GlobalAccessForOthers,
shallowEqual
);
const SelectedCardColor = useSelector(
SelectedGlobalCardColorDetail,
shallowEqual
);
const SelectedCardFont = useSelector(SelectedGlobalCardFont, shallowEqual);
const CartOrderDetails = useSelector(GlobalOrderCardDetails, shallowEqual);
const SelectedDatas = useSelector(GlobalSelectedDatas, shallowEqual);
const otherscarddata = useSelector(Globalothersdata, shallowEqual);
const WSProductdata = useSelector(GlobalWSProduct, shallowEqual);
const NewQrProductData = useSelector(GlobalNewQrProduct, shallowEqual);
const ReportholdData = useSelector(GlobalReorderHoldDetails, shallowEqual);
const ReorderProductData = useSelector(
GlobalReorderProductDetails,
shallowEqual
);
const WeightScalePort = useSelector(GlobalWeightScalePort, shallowEqual);
const WeightScaleWeight = useSelector(GlobalWeightScaleWeight, shallowEqual);
const PaymentTransactionNumber = useSelector(
GlobalPaymentTransactionNumber,
shallowEqual
);
const OverAllproductBasedOfferDatas = useSelector(
(state) => state?.BookingOFferNew?.OverAllProductBasedProducts,
shallowEqual
);
const PromoCodeOffersDatas = useSelector(
Global_PromoCodeOffers,
shallowEqual
);
const allowDecimal = preferenceDatas?.[0]?.SettingDtlDetails?.find(
(setting) =>
setting?.SettingIdName?.toLowerCase() === 'decimal' &&
setting?.SettingValue === 'Y'
);
const [messageType, setMessageType] = useState(null);
const [messageData, setMessageData] = useState(null);
const [repeatedModel, setRepeatedModel] = useState(false);
const [StockPreferenceDetail, setStockPreferenceDetail] = useState();
const [QuickAdd, setQuickAdd] = useState(true);
const [onePeiceFlow, setOnePeiceFlow] = useState(false);
const [BillOrderPre, setBillOrderPre] = useState();
const [expQtyModel, setExpQtyModel] = useState(false);
const [qtyExpData, setQtyExpData] = useState();
const OrderOfferDetail = useSelector(Global_OrderOfferDetail);
const [freeProductsOffers, setfreeProductsOffers] = useState([]);
const [screenWidth, setScreenWidth] = useState(window.innerWidth);
const [screenHeight, setScreenHeight] = useState(window.innerHeight);
const ProdCat = useSelector(GlobalProductCategorie, shallowEqual);
const AddBookingDetailsTrigger = useSelector(GlobalAddBookingDetailsTrigger);
const paymentloader = useSelector(GlobalPayementloader, shallowEqual);
const SessionData = useSelector(StoredSessionData, shallowEqual);
const AppId = SessionData?.AppId;
const CompId = SessionData?.CompId;
const BranchId = SessionData?.BranchId;
const UserId = SessionData?.UserId;
const [TempCartData, setTempCartData] = useState(CartOrderDetails || []);
const dispatch = useDispatch();
const scrollContainerRef = useRef(null);
const isDragging = useRef(false);
const startX = useRef(0);
const scrollLeft = useRef(0);
const itemListScrollRef = useRef(null);
const [selectedBrand, setSelectedBrand] = useState('Others');
const [showLeftButton, setShowLeftButton] = useState(false);
const [showRightButton, setShowRightButton] = useState(false);
const [ExpiredProduct, setExpiredProduct] = useState();
const [ConfigDataList, setConfigDataList] = useState([]);
const alphabeticFormat = useSelector(GlobalisAlphabeticFormat);
// const PricingAppPricingName = useSelector(GlobalPricingAppPricingName);
const favouriteCat = useSelector(GlobalisFavClicked, shallowEqual);
const appPreferences = useSelector(ApplicationPreferences);
const [draggableCardData, setDraggableCardData] = useState([]);
const [refreshKey, setRefreshKey] = useState(0);
const [dateRange, setDateRange] = useState([]);
const [activeMode, setActiveMode] = useState('slot');
const [currentSlotIndex, setCurrentSlotIndex] = useState(0);
const slotItems = [
'Slot 1',
'Slot 2',
'Slot 3',
'Slot 4',
'Slot 5',
'Slot 6',
];
const visibleSlots = 2;
const maxIndex = Math.max(0, draggableCardData.length - visibleSlots);
const currentActiveOffer = getCurrentMembership(selOption?.MembershipDetail);
const handleSlotPrev = () => {
setCurrentSlotIndex((prev) => Math.max(0, prev - 2));
};
const handleSlotNext = () => {
setCurrentSlotIndex((prev) => Math.min(maxIndex, prev + 2));
};
// Add these states to your component
const [selectionMode, setSelectionMode] = useState(false);
const [selectedSlots, setSelectedSlots] = useState([]);
const [bookedDetails, setBookedDetails] = useState(false);
const [selectedSlotDetails, setSelectedSlotDetails] = useState(null);
const [showAllBookingsModal, setShowAllBookingsModal] = useState(false);
const [selectedCustomerBookings, setSelectedCustomerBookings] =
useState(null);
const [loadingSlotAction, setLoadingSlotAction] = useState({});
useEffect(() => {
if (activeMode == 'individual') {
setOnePeiceFlow(true);
} else {
setOnePeiceFlow(false);
}
}, [activeMode]);
// Handler for checkbox selection
const handleSlotSelection = (e, data) => {
if (e.target.checked) {
setSelectedSlots((prev) => [...prev, data]);
} else {
setSelectedSlots((prev) =>
prev.filter(
(slot) =>
!(
slot.ProdId === data.ProdId &&
slot.InwardDtlId === data.InwardDtlId &&
slot.VariantAvailableFrom === data.VariantAvailableFrom &&
slot.VariantAvailableTo === data.VariantAvailableTo &&
slot.BookedDate === data.BookedDate
)
)
);
}
};
const handleBookedDetails = (slot) => {
setSelectedSlotDetails(slot);
setBookedDetails(true);
};
const handleSlotTimeUpdate = async (slot, bookingDate, type) => {
const key = `${slot?.SalesId}-${type}`;
if (loadingSlotAction[key]) return;
let data = {
SalesId: [slot?.SalesId],
BookingDate: bookingDate,
UpdatedBy: UserId,
};
if (type === 'start') {
if (slot?.StartTime) {
message?.error('Play already started for this slot');
return;
}
data.Type = 'S';
} else if (type === 'end') {
if (slot?.EndTime) {
message?.error('Play already ended for this slot');
return;
}
data.Type = 'E';
}
setLoadingSlotAction((prev) => ({ ...prev, [key]: true }));
try {
const res = await dispatch(slotTimeStatus(data))?.unwrap();
if (res?.data?.statusCode === 1) {
message?.success(
`Play ${type === 'start' ? 'started' : 'ended'} successfully`
);
// dispatch(triggerSlotTime());
if (favouriteCat) {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
await dispatch(getSelectedFavItems(data)).unwrap();
} else {
await productCardList();
}
} else {
message?.error(res?.data?.response);
}
} finally {
setLoadingSlotAction((prev) => ({ ...prev, [key]: false }));
}
};
const handleShowAllBookings = (customer) => {
setSelectedCustomerBookings(customer);
setShowAllBookingsModal(true);
};
// Handler for button click in selection mode
const handleSlotButtonClick = async (
newdata,
product,
onePeiceFlow,
ispast
) => {
if (!ispast) {
return;
}
const [productIndex, detailIndex, variantIndex] = newdata?.key?.split('-');
// await dataTransfer(product, detailIndex, variantIndex,0,onePeiceFlow);
let data = {
...newdata,
SinglePc: onePeiceFlow ? 'Y' : 'N',
Product: product,
BookingTypeName: 'TakeAway',
};
const isSelected = CartOrderDetails?.some(
(selected) =>
selected.ProdId === data.ProdId &&
selected.InwardDtlId === data.InwardDtlId &&
selected.VariantAvailableFrom === data.VariantAvailableFrom &&
selected.VariantAvailableTo === data.VariantAvailableTo &&
selected.BookedDate === data.BookedDate
);
if (isSelected) {
// let data = await dataTransfer(product, detailIndex, variantIndex, 0, onePeiceFlow);
const { detail, variant, stock } = extractProductDetails(
product,
detailIndex,
variantIndex,
0
);
const price = onePeiceFlow
? stock?.OnePcsPrice
: RetailWSSalesType === 'W'
? stock?.WhSalePrice || stock?.SellPrice
: stock?.SellPrice;
const size = onePeiceFlow ? '1' : detail?.Size;
const removedata = buildOrderData(
product,
detail,
variant,
stock,
size,
price,
onePeiceFlow
);
handleRemoveFromCart(removedata);
} else {
// setSelectedSlots((prev) => [...prev, data]);
await dataTransfer(product, detailIndex, variantIndex, 0, onePeiceFlow);
}
};
const handleSingleSlotIncrease = async (newdata, product, onePeiceFlow) => {
const [productIndex, detailIndex, variantIndex] = newdata?.key?.split('-');
// await dataTransfer(product, detailIndex, variantIndex,0,onePeiceFlow);
let data = {
...newdata,
SinglePc: onePeiceFlow ? 'Y' : 'N',
Product: product,
BookingTypeName: 'TakeAway',
};
const isSelected = CartOrderDetails?.some(
(selected) =>
selected.ProdId === data.ProdId &&
selected.InwardDtlId === data.InwardDtlId &&
selected.VariantAvailableFrom === data.VariantAvailableFrom &&
selected.VariantAvailableTo === data.VariantAvailableTo &&
selected.BookedDate === data.BookedDate
);
if (isSelected) {
await dataTransfer(product, detailIndex, variantIndex, 0, onePeiceFlow);
} else {
// setSelectedSlots((prev) => [...prev, data]);
await dataTransfer(product, detailIndex, variantIndex, 0, onePeiceFlow);
}
};
const handleRemoveSingle = async (newdata, product, onePeiceFlow) => {
const [productIndex, detailIndex, variantIndex] = newdata?.key?.split('-');
// await dataTransfer(product, detailIndex, variantIndex,0,onePeiceFlow);
let data = {
...newdata,
SinglePc: onePeiceFlow ? 'Y' : 'N',
Product: product,
BookingTypeName: 'TakeAway',
};
const isSelected = CartOrderDetails?.some(
(selected) =>
selected.ProdId === data.ProdId &&
selected.InwardDtlId === data.InwardDtlId &&
selected.VariantAvailableFrom === data.VariantAvailableFrom &&
selected.VariantAvailableTo === data.VariantAvailableTo &&
selected.BookedDate === data.BookedDate
);
if (isSelected) {
const { detail, variant, stock } = extractProductDetails(
product,
detailIndex,
variantIndex,
0
);
const price = onePeiceFlow
? stock?.OnePcsPrice
: RetailWSSalesType === 'W'
? stock?.WhSalePrice || stock?.SellPrice
: stock?.SellPrice;
const size = onePeiceFlow ? '1' : detail?.Size;
const removedata = buildOrderData(
product,
detail,
variant,
stock,
size,
price,
onePeiceFlow
);
const removetemdata = { ...removedata, OrderQty: 1 };
handleDecline(removetemdata);
} else {
// setSelectedSlots((prev) => [...prev, data]);
await dataTransfer(product, detailIndex, variantIndex, 0, onePeiceFlow);
}
};
// Handler for submitting selected slots with PostBlockSlots
const handleSubmitSelectedSlots = async () => {
if (TotalAmount > 0) {
setModalVarient(false);
// alert('Total Amount greater than 0, proceed to payment');
// const AddBooking = new CustomEvent('MembershipZeroPayment');
// window.dispatchEvent(AddBooking);
} else {
dispatch(changeAddBookingDetailsTrigger(true));
// triggerBooking({ value: 'TakeAway', pay: true });
// const AddBooking = new CustomEvent('MembershipZeroPayment');
// window.dispatchEvent(AddBooking);
}
};
const handleSubmitBlockSlots = async () => {
try {
// Validate inputs
if (!selectedSlots?.length) {
setMessageType('error');
setMessageData('No slots selected');
return;
}
if (!CompId || !BranchId || !AppId || !UserId) {
setMessageType('error');
setMessageData('Missing session data');
return;
}
const selectedCount = selectedSlots.length; // Store count before reset
let prodList = [];
for (const slot of selectedSlots) {
let slotStatus = slot?.SlotStatus?.toLowerCase();
let isBooked = slotStatus === 'booked';
const isPartiallyBooked =
slotStatus === 'partially booked' ||
CartOrderDetails?.some(
(item) =>
item?.SinglePc === 'Y' &&
item?.VariantAvailableFrom === slot?.VariantAvailableFrom &&
item?.VariantAvailableTo === slot?.VariantAvailableTo
);
const qty =
Number(slot?.TotalSlotQty || 0) - Number(slot?.BookedQty || 0);
if (!isBooked) {
prodList.push({
ProdId: slot?.ProdId || qtydata?.ProductDetail?.[QtyIndex]?.ProdId,
InwardDtlId: slot?.InwardDtlId,
SinglePc:
onePeiceFlow || (isPartiallyBooked && !onePeiceFlow) ? 'Y' : 'N',
Qty: isPartiallyBooked && !onePeiceFlow ? qty : 1,
Date: slot?.BookedDate,
});
}
}
if (!prodList.length) {
setMessageType('error');
setMessageData('No valid slots to book');
return;
}
const BlockPostdata = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
Status: 'Block',
CreatedBy: UserId,
ProductList: prodList,
};
const res = await dispatch(PostBlockSlots(BlockPostdata)).unwrap();
if (res?.data?.statusCode === 1) {
setSelectedSlots([]);
setSelectionMode(false);
setMessageType('success');
setMessageData(`${selectedCount} slots booked successfully`);
if (favouriteCat) {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
await dispatch(getSelectedFavItems(data)).unwrap();
} else {
await productCardList();
}
} else {
throw new Error('Failed to book slots');
}
} catch (error) {
console.error('Error submitting slots:', error);
setMessageType('error');
setMessageData('Error booking slots');
}
};
// Reset selection when modal closes
useEffect(() => {
if (!ModalVarient) {
setSelectionMode(false);
setSelectedSlots([]);
}
}, [ModalVarient]);
useEffect(() => {
if (!AddBookingDetailsTrigger) {
ModalVarient && setModalVarient(false);
}
}, [AddBookingDetailsTrigger]);
useEffect(() => {
if (!ItemCard?.length || !qtydata?.ProdId) return;
const sourceArray = favouriteCat ? SelectedDatas : ItemCard;
const filteredItem = sourceArray?.find(
(item) => item.ProdId === qtydata?.ProdId
);
if (filteredItem) {
setQtydata(filteredItem);
}
}, [ItemCard, SelectedDatas, qtydata?.ProdId, favouriteCat]);
const salespagefields = appPreferences?.find(
(pref) => pref?.PreferredCatName === 'Sales Page Fields'
)?.PreferenceCatDetails;
const AvailableDate = salespagefields?.find(
(type) =>
type?.PreferredSubCatName?.toLowerCase() === 'available date' &&
type?.PreferredStatus === 'Y'
);
const SingleMember = salespagefields?.find(
(type) =>
type?.PreferredSubCatName?.toLowerCase() === 'single member' &&
type?.PreferredStatus === 'Y'
);
useSaleswiseOfferWatcher();
useEffect(() => {
itemListScrollRef.current?.scrollTo(0, 0);
}, [ProdCat, ProdSubCat, favouriteCat]);
useEffect(() => {
if (ConfigDataList?.length === 0) {
getBookingTypeId();
}
}, []);
const prodCatRef = useRef(ProdCat);
const prodSubCatRef = useRef(ProdSubCat);
const selectedDateRef = useRef(selectedDate);
useEffect(() => {
selectedDateRef.current = selectedDate;
}, [selectedDate]);
useEffect(() => {
prodCatRef.current = ProdCat;
prodSubCatRef.current = ProdSubCat;
}, [ProdCat, ProdSubCat]);
useEffect(() => {
const subscribeToNotification = async () => {
const unsubscribeFn = await onReceiveNotification(async (title, msg) => {
console.log('📢 Notification:', title, msg);
const currentProdCat = prodCatRef.current;
const currentProdSubCat = prodSubCatRef.current;
if (favouriteCat) {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
await dispatch(getSelectedFavItems(data)).unwrap();
} else if (currentProdCat && !isNaN(currentProdSubCat)) {
console.log(
currentProdCat,
currentProdSubCat,
'ProdSubCatProdSubCatProdSubCatProdSubCatProdSubCat'
);
productCardList();
} else {
console.log(
currentProdCat,
currentProdSubCat,
'ProdSubCatProdSubCatProdSubCatProdSubCatProdSubCat'
);
}
});
unsubscribeRef.current = unsubscribeFn;
};
subscribeToNotification();
return () => {
if (unsubscribeRef.current) {
unsubscribeRef.current();
console.log('🔌 Unsubscribed from notifications');
}
};
}, []);
useEffect(() => {
if (CartOrderDetails?.length > 0 && selOption) {
if (selOption?.MembershipDetail?.length == 0) {
dispatch(changeFullOfferAppliedProducts([]));
return;
}
const currentActiveOffer = getCurrentMembership(
selOption?.MembershipDetail
);
const calculateTotalHours = (cartData) => {
let totalHours = 0;
let totalAmt = 0;
const itemsWithHours = []; // Track individual items with their hours and amounts
cartData.forEach((item, index) => {
const timeFrom = item?.VariantAvailableFrom;
const timeTo = item?.VariantAvailableTo;
if (timeFrom && timeTo) {
const [hoursFrom, minutesFrom] = timeFrom.split(':').map(Number);
const [hoursTo, minutesTo] = timeTo.split(':').map(Number);
const totalMinutesFrom = hoursFrom * 60 + minutesFrom;
const totalMinutesTo = hoursTo * 60 + minutesTo;
const hrs = (totalMinutesTo - totalMinutesFrom) / 60;
const itemHours = hrs * item?.Size * item?.OrderQty;
totalHours += itemHours;
// Store item details for prioritization
itemsWithHours.push({
index: index, // Track original index
hours: itemHours,
amount: item?.TotalAmt,
amountPerHour: item?.TotalAmt / itemHours,
item: item,
});
}
totalAmt += item?.TotalAmt;
});
return { totalHours, totalAmt, itemsWithHours };
};
const { totalHours, totalAmt, itemsWithHours } =
calculateTotalHours(CartOrderDetails);
const needsUpdate = (newOffers) => {
return CartOrderDetails.some((item, index) => {
const newOffer = newOffers[index] || 0;
const currentOffer = item?.Offer || 0;
return Math.abs(newOffer - currentOffer) > 0.01; // Use small threshold for floating point comparison
});
};
if (currentActiveOffer) {
if (currentActiveOffer?.RemainingSessionHrs > 0) {
if (totalHours <= currentActiveOffer?.RemainingSessionHrs) {
// All hours can be covered
const offer = [
{
OfferId: currentActiveOffer?.MembershipId,
OfferAmount: totalAmt,
OfferValue: totalAmt,
TableName: 'MemberShip',
TableUniqueName: 'MemberShip',
OfferType: 'M',
OfferMode: 'M',
Detail: [{ MembershipName: currentActiveOffer?.MemberName }],
CustId: selOption?.CustId,
Usedhours: totalHours,
PlanId: currentActiveOffer?.PlanId,
},
];
dispatch(changeOfferAppliedProductsForMembership(offer));
} else if (totalHours > currentActiveOffer?.RemainingSessionHrs) {
// Prioritize items with higher amount per hour
const sortedItems = [...itemsWithHours].sort(
(a, b) => b.amountPerHour - a.amountPerHour
);
let remainingHours = currentActiveOffer?.RemainingSessionHrs;
let offerAmount = 0;
const offerByIndex = {};
for (const item of sortedItems) {
if (remainingHours <= 0) break;
if (item.hours <= remainingHours) {
offerByIndex[item.index] = item.amount;
offerAmount += item.amount;
remainingHours -= item.hours;
} else {
const partialOffer =
(remainingHours / item.hours) * item.amount;
offerByIndex[item.index] = partialOffer;
offerAmount += partialOffer;
remainingHours = 0;
}
}
const newOffers = CartOrderDetails.map(
(item, index) => offerByIndex[index] || 0
);
if (needsUpdate(newOffers)) {
const updatedCartDetails = CartOrderDetails.map(
(item, index) => ({
...item,
Offer: newOffers[index],
})
);
dispatch(changeOrderCardDetails(updatedCartDetails));
}
const offer = [
{
OfferId: currentActiveOffer?.MembershipId,
OfferAmount: offerAmount,
OfferValue: offerAmount,
TableName: 'MemberShip',
TableUniqueName: 'MemberShip',
OfferType: 'M',
OfferMode: 'M',
Detail: [{ MembershipName: currentActiveOffer?.MemberName }],
CustId: selOption?.CustId,
Usedhours: currentActiveOffer?.RemainingSessionHrs,
PlanId: currentActiveOffer?.PlanId,
},
];
dispatch(changeOfferAppliedProductsForMembership(offer));
}
} else if (currentActiveOffer?.RemainingDays > 0) {
const offerValue =
currentActiveOffer?.DiscountType === 'F'
? currentActiveOffer?.Discount || 0
: totalAmt * ((currentActiveOffer?.Discount || 0) / 100);
const offer = [
{
OfferId: currentActiveOffer?.MembershipId,
OfferAmount: offerValue,
OfferValue: offerValue,
TableName: 'MemberShip',
TableUniqueName: 'MemberShip',
OfferType: 'M',
OfferMode: 'M',
Detail: [{ MembershipName: currentActiveOffer?.MemberName }],
CustId: selOption?.CustId,
Usedhours: 0,
PlanId: currentActiveOffer?.PlanId,
},
];
dispatch(changeOfferAppliedProductsForMembership(offer));
} else {
dispatch(
changeFullOfferAppliedProducts(
offerAppliedProducts?.filter((off) => off?.OfferMode !== 'M')
)
);
}
}
}
if (CartOrderDetails?.length == 0) {
dispatch(changeFullOfferAppliedProducts([]));
}
console.log('Membership Offer Applied', selOption);
if (!selOption) {
dispatch(changeFullOfferAppliedProducts([]));
}
}, [CartOrderDetails, selOption]);
useEffect(() => {
const filteredOffers = OrderOfferDetail?.filter(
({ TableName, TableUniqueName, OfferCode, Type, FreeProductsList }) => {
if (
(TableName === 'LoyaltyPoints' &&
TableUniqueName === 'UniqueId' &&
Type === 'A') ||
((TableName === 'CustomerPromo' ||
TableName === 'CustomerCoupon' ||
TableName === 'OfferCode') &&
OfferCode != null &&
TableUniqueName === 'UniqueId')
) {
return FreeProductsList?.ExistingList?.length > 0;
}
if (TableName === 'BuyXGetXOffers') return true;
}
);
setfreeProductsOffers(filteredOffers);
}, [OrderOfferDetail]);
useEffect(() => {
if (SelectedCardFont) {
WebFont.load({
google: {
families: [SelectedCardFont], // Load the selected font
},
});
}
}, [SelectedCardFont]);
// const cardData = !globalAccessForOthers
// ? CardAccess
// ? SelectedDatas
// : ItemCard?.length == 0 ? noSubcatCardData : ItemCard
// : "";
//mohan 18-04-2025
const cardData = !globalAccessForOthers
? CardAccess
? SelectedDatas?.length > 1
? SelectedDatas
: SelectedDatas?.[0]?.AppId === 0 && SelectedDatas?.[0]?.CompId === 0
? []
: SelectedDatas
: ItemCard?.length == 0 ||
(ItemCard?.[0]?.AppId === 0 && ItemCard?.[0]?.CompId === 0)
? noSubcatCardData
: ItemCard
: '';
const cardDataForNewPrd = !globalAccessForOthers
? CardAccess
? SelectedDatas
: ItemCard?.length == 0
? noSubcatCardData
: ItemCard
: '';
//
function safeRound(amountStr) {
if (amountStr == null) return allowDecimal ? '0.00' : '0';
const cleaned = String(amountStr).replace(/[^0-9.-]+/g, '');
const num = Number(cleaned);
if (isNaN(num)) return allowDecimal ? '0.00' : '0';
return allowDecimal ? num.toFixed(2) : Math.round(num).toString();
}
useEffect(() => {
if (bookedDetails) {
const itemCardData = ItemCard?.find((item) =>
item?.ProductDetail?.[0]?.ProdVariantDetails?.some((variant) =>
variant?.StockDetails?.some(
(stock) => stock?.InwardDtlId === selectedSlotDetails?.InwardDtlId
)
)
);
const filteredVariant =
itemCardData?.ProductDetail?.[0]?.ProdVariantDetails?.find((variant) =>
variant?.StockDetails?.some(
(stock) => stock?.InwardDtlId === selectedSlotDetails?.InwardDtlId
)
);
const filteredStock = filteredVariant?.StockDetails?.find(
(stock) => stock?.InwardDtlId === selectedSlotDetails?.InwardDtlId
);
const updatedSelectedSlotDetails = {
...filteredStock,
ProdName: itemCardData?.ProductDetail?.[0]?.ProdName,
ProdSubCatName: itemCardData?.ProdSubCatName,
BookedDate: filteredVariant?.TempDate,
AvailableFrom: filteredVariant?.AvailableFrom,
AvailableTo: filteredVariant?.AvailableTo,
};
setSelectedSlotDetails(updatedSelectedSlotDetails);
if (showAllBookingsModal) {
const selectedCustomer = filteredStock?.CustomerDetails?.find(
(cust) => cust?.CustId === selectedCustomerBookings?.CustId
);
setSelectedCustomerBookings(selectedCustomer);
}
}
}, [ItemCard]);
useEffect(() => {
// fetchedit();
getPreferenceStock();
// dispatch(changepreOrder(false)); Commented to Add Normal Produts After Adding the Combo Pack !!!!!! Dont Touch Without Shifayath Permission
}, [preferenceDatas]);
useEffect(() => {
if (AppId && CompId && BranchId) {
fetchedit();
GetmultipleSearchData();
}
// dispatch(changepreOrder(false)); Commented to Add Normal Produts After Adding the Combo Pack !!!!!! Dont Touch Without Shifayath Permission
}, [AppId, CompId, BranchId]);
const GetmultipleSearchData = async () => {
const data = {
AppId,
CompId,
BranchId,
};
try {
const response = await dispatch(getmultipleSearch(data));
} catch (error) {
console.error('Get Search Terms Error:', error);
}
};
useEffect(() => {
setPreOrderSelectedProdNames([]);
// dispatch(changePreOrderAdditem(null));
}, [preOrder]);
useEffect(() => {
if (ProdCat && ProdSubCat !== NaN && ProdSubCat !== 'NaN' && ProdSubCat) {
// if (ProdCat && !isNaN(ProdSubCat)) {
productCardList();
}
}, [ProdSubCat]);
useEffect(() => {
if (favouriteCat) {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
dispatch(getSelectedFavItems(data)).unwrap();
} else {
productCardList();
}
}, [selectedDate]);
useEffect(() => {
if (noSubcatCardData) {
setNoSubcatCardData();
}
if (
ProductSearch?.length > 5 &&
GetmultipleSearchDatas.some((e) => e.toLowerCase() === 'qrcode')
) {
setQuickAdd(true);
}
}, [ProductSearch, GetmultipleSearchDatas]);
useEffect(() => {
if (
!initialRun &&
(!ProdSubCat || ProdSubCat != NaN || ProdSubCat === 'NaN') &&
ProdCat &&
templateData?.BookingCategory?.[0] != 'Category5'
) {
// if (!initialRun && (!ProdSubCat || !isNaN(ProdSubCat)) && ProdCat) {
setInitialRun(true);
productCardList();
}
}, [ProdCat, initialRun]);
// const formatDateFromRange = (date) => {
// if (!date) return null;
// if (date?.format) {
// return date.format('YYYY-MM-DD');
// }
// if (dayjs(date).isValid()) {
// return dayjs(date).format('YYYY-MM-DD');
// }
// return date;
// };
const productCardList = async () => {
//condition
const currentProdCat = prodCatRef.current;
const currentProdSubCat = prodSubCatRef.current;
const currentDateRef = selectedDateRef.current;
if (
(templateData?.BookingLayout?.[1]?.some(
(item) => item?.OptionName === 'SubCategory'
) ||
templateData?.BookingCategory?.[0] == 'Category5') &&
currentProdSubCat &&
currentProdCat
) {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
ProdSubCat: currentProdSubCat,
...(AvailableDate && currentDateRef
? {
fromDate: currentDateRef?.[0],
toDate: currentDateRef?.[1],
}
: {}),
};
//mohan
let response = await dispatch(getLayoutproductCard(data)).unwrap();
if (response?.data?.statusCode == 1) {
setNoSubcatCardData(response?.data?.data);
}
} else if (
!templateData?.BookingLayout?.[1]?.some(
(item) => item?.OptionName === 'SubCategory'
) &&
currentProdCat
) {
let data = {
compId: CompId,
branchId: BranchId,
appId: AppId,
prodCat: currentProdCat,
...(AvailableDate && currentDateRef
? {
fromDate: currentDateRef?.[0],
toDate: currentDateRef?.[1],
}
: {}),
};
let response = await dispatch(getCardDataWithoutSubmodule(data)).unwrap();
if (response?.data?.statusCode == 1) {
setNoSubcatCardData(response?.data?.data);
}
} else if (
templateData?.BookingLayout?.[1]?.some(
(item) => item?.OptionName === 'SubCategory'
) &&
!currentProdSubCat &&
currentProdCat &&
currentProdSubCat != 'NaN'
) {
let data = {
compId: CompId,
branchId: BranchId,
appId: AppId,
prodCat: currentProdCat,
...(AvailableDate && currentDateRef
? {
fromDate: currentDateRef?.[0],
toDate: currentDateRef?.[1],
}
: {}),
};
let response = await dispatch(getCardDataWithoutSub(data)).unwrap();
if (response?.data?.statusCode == 1) {
setNoSubcatCardData(response?.data?.data);
}
}
};
const getBookingTypeId = async () => {
setConfigDataList(AllBookingType);
let configdata = AllBookingType;
let checkName = BookingTypeBoth ? 'DineIn,TakeAway' : BookingType;
let filterconfigdata = configdata?.find((a) => a?.ConfigName === checkName);
// setSelectedBookingType(filterconfigdata?.ConfigId);
};
function getCurrentMembership(memberships) {
if (!memberships?.length) return null;
// ✅ Clone the array to avoid mutating read-only data
const sorted = [...memberships].sort(
(a, b) => new Date(a.CreatedDate) - new Date(b.CreatedDate)
);
// Step 1: find active plan
const active = sorted.find(
(m) => m.RemainingDays > 0 || m.RemainingSessionHrs > 0
);
if (active) return active;
// Step 2: if no active plan, find the next upcoming (based on CreatedDate)
const now = new Date();
const next = sorted.find((m) => new Date(m.CreatedDate) > now);
return next || null;
}
const fetchedit = async () => {
let data = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
let res = await dispatch(getEditFavItems(data)).unwrap();
if (res?.data?.statusCode == 1) {
setSelectedProdNames(res?.data?.data);
} else {
setSelectedProdNames([]);
}
};
useEffect(() => {
DispatchData();
}, [SelectedProdNames]);
const DispatchData = async () => {
await dispatch(ChangeAllItemData(SelectedProdNames));
};
useEffect(() => {
if (Object.keys(WSProductdata)?.length > 0) {
AddOrderDetails(WSProductdata);
}
}, [WSProductdata]);
useEffect(() => {
if (ItemCard?.[0]?.QrBasedSearch === 'Y') {
if (ItemCard?.[0]?.OverAllExpStatus == 'Y' && ExpiredProduct) {
setexpModel(true);
setItem(ItemCard?.[0]);
} else {
setQtydata(ItemCard?.[0]);
SingleQuantity(ItemCard?.[0], false);
}
} else if (ItemCard?.[0]?.OnePcQRBased === 'Y') {
if (ItemCard?.[0]?.OverAllExpStatus == 'Y' && ExpiredProduct) {
setexpModel(true);
setItem(ItemCard?.[0]);
setOnePeiceFlow(true);
} else {
setQtydata(ItemCard?.[0]);
SingleQuantity(ItemCard?.[0], true);
}
}
}, [ItemCard]);
useEffect(() => {
// let data = otherscarddata
if (Object.keys(otherscarddata)?.length > 0) {
let data = {
Type: otherscarddata?.Type ? otherscarddata?.Type : 'P',
OverallQuantity: otherscarddata?.OverAllQty,
ActiveStatus: otherscarddata?.ActiveStatus,
AvailableFrom: otherscarddata?.AvailableFrom,
AvailableTo: otherscarddata?.AvailableTo,
Cess: otherscarddata?.Cess,
ExpDate: otherscarddata?.ExpDate,
HSNCode: otherscarddata?.HSNCode,
ManufDate: otherscarddata?.ManufDate,
OpeningQty: otherscarddata?.OpeningQty,
ProdType: otherscarddata?.ProdType,
PartNumber: otherscarddata?.PartNumber,
ProdId: otherscarddata?.ProdId,
ProdLogo: otherscarddata?.ProdLogo,
ProdName: otherscarddata?.ProdName,
QRCode: otherscarddata?.QRCode,
QtyBasedPrice: otherscarddata?.QtyBasedPrice,
Rack: otherscarddata?.Rack,
Size: otherscarddata?.Size,
StockAvailable: otherscarddata?.StockAvailable,
TaxId: otherscarddata?.TaxId,
TaxPercentage: otherscarddata?.TaxPercentage,
TaxName: otherscarddata?.TaxIdName,
UniqueId: otherscarddata?.UniqueId,
UomName: otherscarddata?.UomName,
ProdVariantName: otherscarddata?.ProdVariantName, //sri
BalanceQty: otherscarddata?.BalanceQty,
BatchRef: otherscarddata?.BatchRef,
ModelNumber: otherscarddata?.ModelNumber, //sri
FullProductIdentifierDtls: otherscarddata?.FullProductIdentifierDtls, //sri
InwardDate: otherscarddata?.InwardDate,
InwardDtlId: otherscarddata?.InwardDtlId,
InwardId: otherscarddata?.InwardId,
MRP: otherscarddata?.MRP,
Offer: otherscarddata?.OfferPrice,
OrderRate: otherscarddata?.SellPrice,
SellingPrice: otherscarddata?.SellPrice, // edit srii
SuppId: otherscarddata?.SuppId,
SuppName: otherscarddata?.SuppName,
OrderQty: otherscarddata?.Quantity,
OtherProduct: otherscarddata?.OtherProduct,
// 'ProdVariantName': otherscarddata?.ProdVariantName,
BookingTypeName: BookingType,
CounterName: '', //sri
};
AddOrderDetails(data);
}
// data["OrderRate"] = otherscarddata?.SellPrice
}, [otherscarddata]);
useEffect(() => {
if (Object.keys(NewQrProductData)?.length > 0) {
let addQrProductData = { ...NewQrProductData };
addQrProductData['OrderRate'] = addQrProductData['SellPrice'];
addQrProductData['OrderQty'] = addQrProductData['Quantity'];
addQrProductData['SellingPrice'] = addQrProductData['SellPrice'];
addQrProductData['BookingTypeName'] = BookingType;
AddOrderDetails(addQrProductData);
}
}, [NewQrProductData]);
const getPreferenceStock = async () => {
const PreferenceStckDtl = preferenceDatas?.[0]?.SettingDtlDetails;
const StockPreference = PreferenceStckDtl?.find(
(item) => item.SettingIdName === 'StockSelection'
);
setStockPreferenceDetail(StockPreference);
const BillOrder = PreferenceStckDtl?.find(
(item) => item.SettingIdName === 'BillItemsOrder'
);
setBillOrderPre(BillOrder?.SettingValue);
const expiredDate =
PreferenceStckDtl?.find(
(item) => item.SettingIdName === 'ExpiredSelection'
)?.SettingValue === 'Y';
setExpiredProduct(expiredDate);
};
const to12Hour = (timeStr) => {
if (!timeStr) return '';
let [h, m] = timeStr.split(':');
h = parseInt(h, 10);
const suffix = h >= 12 ? 'PM' : 'AM';
h = h % 12 || 12;
return `${h}:${m}${suffix}`;
};
const CloseModal = () => {
setModelQty(false);
setRepeatedModel(false);
setProdexpir(false);
setOnePeiceFlow(false);
setSelectedBrand('Others');
};
const CloseModal1 = () => {
setModelstock(false);
setRepeatedModel(false);
setProdexpir(false);
setOnePeiceFlow(false);
};
const CloseVarientModal = () => {
setModalVarient(false);
setRepeatedModel(false);
setProdexpir(false);
setOnePeiceFlow(false);
};
const Quantity = () => {
setModelQty(true);
};
const SingleQuantity = (item, onePcs) => {
// if (count > 1) {
setModalVarient(true);
setActiveMode('slot');
// } else {
// setVarientIndex(0);
// SingleStockfun(item, onePcs);
// }
};
const Stockfun = async (index, onePeiceFlow) => {
let CartUpdateData = [];
setVarientIndex(index.key);
const variantDetails =
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[index.key] || {};
const overallExpStatus = variantDetails.OverAllExpStatus;
const count = variantDetails.StockDetails?.length || 0;
if (
StockPreferenceDetail?.SettingValue === 'Y' &&
qtydata?.ProductDetail?.[QtyIndex]?.StockAvailable == 'Y'
) {
if (count > 1) {
if (
overallExpStatus === 'N' ||
(overallExpStatus === 'Y' && prodexpir)
) {
setModalVarient(false);
setModelstock(true);
setVarItem(index.key);
if (overallExpStatus === 'Y' && prodexpir) {
setRepeatedModel(true);
}
} else if (overallExpStatus === 'Y' && ExpiredProduct) {
setVarItem(index.key);
setexpVarModel(true);
}
} else {
if (
overallExpStatus === 'N' ||
(overallExpStatus === 'Y' && prodexpir)
) {
let Isincart = CartOrderDetails?.find(
(cartItem) =>
cartItem?.ProdId === qtydata?.ProductDetail?.[QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.InwardDtlId &&
cartItem?.OrderRate ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.SellPrice &&
!cartItem?.SalesId
);
if (onePeiceFlow) {
let Isincartonepc = CartOrderDetails?.filter(
(cartItem) =>
cartItem?.ProdId ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.InwardDtlId &&
// (cartItem?.OrderRate === item?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[VarientIndex]?.StockDetails?.[0]?.SellPrice)
!cartItem?.SalesId
);
let totalOrderQty = Isincartonepc?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * (card.NoOfPcs ? card.NoOfPcs : 1)
: card.OrderQty
: 0
)
);
}, 0);
if (Isincartonepc && Isincartonepc?.[0]?.StockAvailable === 'Y') {
if (Isincartonepc?.[0]?.OverAllPcs > totalOrderQty) {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
1,
onePeiceFlow
);
}
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
}
} else {
if (Isincart && Isincart?.StockAvailable === 'Y') {
if (Isincart?.BalanceQty > Isincart?.OrderQty) {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
1,
onePeiceFlow
);
}
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
}
}
setModelQty(false);
setSelectedBrand('Others');
setVarItem(index.key);
if (overallExpStatus === 'Y' && prodexpir) {
setProdexpir(false);
setRepeatedModel(true);
return;
}
} else if (overallExpStatus === 'Y' && ExpiredProduct) {
setVarItem(index.key);
setexpVarModel(true);
return;
}
}
} else {
if (overallExpStatus === 'N' || (overallExpStatus === 'Y' && prodexpir)) {
let Isincart = CartOrderDetails?.find(
(cartItem) =>
cartItem?.ProdId === qtydata?.ProductDetail?.[QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.InwardDtlId &&
cartItem?.OrderRate ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.SellPrice &&
!cartItem?.SalesId
);
if (onePeiceFlow) {
let Isincartonepc = CartOrderDetails?.filter(
(cartItem) =>
cartItem?.ProdId === qtydata?.ProductDetail?.[QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
index.key
]?.StockDetails?.[0]?.InwardDtlId &&
// (cartItem?.OrderRate === item?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[VarientIndex]?.StockDetails?.[0]?.SellPrice)
!cartItem?.SalesId
);
let totalOrderQty = Isincartonepc?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * (card.NoOfPcs ? card.NoOfPcs : 1)
: card.OrderQty
: 0
)
);
}, 0);
if (Isincartonepc && Isincartonepc?.[0]?.StockAvailable === 'Y') {
if (Isincartonepc?.[0]?.OverAllPcs > totalOrderQty) {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
1,
onePeiceFlow
);
}
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
}
} else {
if (Isincart && Isincart?.StockAvailable === 'Y') {
if (Isincart?.BalanceQty > Isincart?.OrderQty) {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
1,
onePeiceFlow
);
}
} else {
CartUpdateData = await dataTransfer(
qtydata,
QtyIndex,
index.key,
0,
onePeiceFlow
);
}
}
setModelQty(false);
setSelectedBrand('Others');
setVarItem(index.key);
if (overallExpStatus === 'Y' && prodexpir) {
setProdexpir(false);
setRepeatedModel(true);
return;
}
} else if (overallExpStatus === 'Y' && ExpiredProduct) {
setVarItem(index.key);
setexpVarModel(true);
return;
}
setModelQty(false);
setSelectedBrand('Others');
}
return CartUpdateData;
};
const VarientFun = (index) => {
const QtyExpire = index?.ProdVariantDetails.every(
(item) => item.OverAllExpStatus === 'Y'
);
if (QtyExpire && ExpiredProduct) {
setExpQtyModel(true);
setQtyExpData(index);
} else {
const selectedProIndex = qtydata?.ProductDetail?.findIndex(
(item) =>
item?.ProdId === index?.ProdId &&
item?.Size === index?.Size &&
item?.UomName === index?.UomName &&
item?.Brand === index?.Brand
);
if (selectedProIndex !== -1) {
const count =
qtydata?.ProductDetail[selectedProIndex]?.ProdVariantDetails
?.length || 0;
if (count > 1) {
setModelQty(false);
setSelectedBrand('Others');
setModalVarient(true);
} else {
const item = { QtyIndex: selectedProIndex, VarientIndex: 0 };
singleVarient(item);
setModelQty(false);
setSelectedBrand('Others');
}
}
setQtyIndex(selectedProIndex);
setVarientIndex(0);
setRepeatedModel(false);
}
};
const singleVarient = (item) => {
let count =
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.length;
if (
StockPreferenceDetail?.SettingValue === 'Y' &&
qtydata?.ProductDetail?.[item?.QtyIndex]?.StockAvailable == 'Y'
) {
if (count > 1) {
setModalVarient(false);
setModelstock(true);
// setVarientIndex(index.key)
} else {
let Isincart = CartOrderDetails?.find(
(cartItem) =>
cartItem?.ProdId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.InwardDtlId &&
cartItem?.OrderRate ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.SellPrice &&
!cartItem?.SalesId
);
if (onePeiceFlow) {
let Isincartonepc = CartOrderDetails?.filter(
(cartItem) =>
cartItem?.ProdId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.InwardDtlId &&
// (cartItem?.OrderRate === item?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[VarientIndex]?.StockDetails?.[0]?.SellPrice)
!cartItem?.SalesId
);
let totalOrderQty = Isincartonepc?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
}, 0);
if (Isincartonepc && Isincartonepc?.[0]?.StockAvailable === 'Y') {
if (Isincartonepc?.[0]?.OverAllPcs > totalOrderQty) {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
1,
onePeiceFlow
);
}
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
}
} else {
if (Isincart && Isincart?.StockAvailable === 'Y') {
if (Isincart?.BalanceQty > Isincart?.OrderQty) {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
1,
onePeiceFlow
);
}
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
}
}
setModelQty(false);
setSelectedBrand('Others');
}
} else {
let Isincart = CartOrderDetails?.find(
(cartItem) =>
cartItem?.ProdId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.InwardDtlId &&
cartItem?.OrderRate ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.SellPrice &&
!cartItem?.SalesId
);
if (onePeiceFlow) {
let Isincartonepc = CartOrderDetails?.filter(
(cartItem) =>
cartItem?.ProdId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdId &&
cartItem?.InwardDtlId ===
qtydata?.ProductDetail?.[item?.QtyIndex]?.ProdVariantDetails?.[
item?.VarientIndex
]?.StockDetails?.[0]?.InwardDtlId &&
// (cartItem?.OrderRate === item?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[VarientIndex]?.StockDetails?.[0]?.SellPrice)
!cartItem?.SalesId
);
let totalOrderQty = Isincartonepc?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
}, 0);
if (Isincartonepc && Isincartonepc?.[0]?.StockAvailable === 'Y') {
if (Isincartonepc?.[0]?.OverAllPcs > totalOrderQty) {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
1,
onePeiceFlow
);
}
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
}
} else {
if (Isincart && Isincart?.StockAvailable === 'Y') {
if (Isincart?.BalanceQty > Isincart?.OrderQty) {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
1,
onePeiceFlow
);
}
} else {
dataTransfer(
qtydata,
item?.QtyIndex,
item?.VarientIndex,
0,
onePeiceFlow
);
}
}
setModelQty(false);
setSelectedBrand('Others');
}
};
const StockSelected = (item) => {
const stockDetails =
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[VarientIndex]
?.StockDetails?.[item.key] || {};
const overallExpStatus = stockDetails?.OverAllExpStatus;
if (overallExpStatus === 'N' || overallExpStatus === 'Y') {
const firstStockDetails =
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[0]
?.StockDetails?.[item.key] || {};
const firstOverallExpStatus = firstStockDetails.OverAllExpStatus;
if (
overallExpStatus === 'N' ||
(firstOverallExpStatus === 'Y' && prodexpir)
) {
dataTransfer(qtydata, QtyIndex, VarientIndex, item.key, onePeiceFlow);
} else if (overallExpStatus === 'Y' && repeatedModel) {
dataTransfer(qtydata, QtyIndex, VarientIndex, item.key, onePeiceFlow);
} else {
setexpStockModel(true);
setStockItem(item.key);
}
}
setProdexpir(false);
setRepeatedModel(false);
};
const CardOnclick = async (item, index, Parameter) => {
console.log(item, index, 'setCurrentSlotIndex');
setCurrentSlotIndex(index);
setOnePeiceFlow(Parameter === 'OnePeiceProduct');
const transformedItem = {
...item,
ProductDetail: item.ProductDetail
// .filter((detail) => detail.OnePcsAvailable === "Y")
.map(({ ProdId, ProdName, ProdVariantDetails, ...rest }) => ({
ProdId,
ProdName,
ProdVariantDetails,
...rest,
})),
};
const modiffiedData =
Parameter === 'OnePeiceProduct' ? transformedItem : item;
setQtydata(modiffiedData);
if (modiffiedData.OverAllExpStatus === 'Y' && ExpiredProduct) {
setexpModel(true);
setItem(modiffiedData);
} else if (modiffiedData) {
setQtydata(modiffiedData);
let count = modiffiedData?.ProductDetail?.length;
if (count > 1) {
Quantity(modiffiedData);
} else {
setQtyIndex(0);
SingleQuantity(modiffiedData, Parameter === 'OnePeiceProduct');
}
}
};
const AddOrderDetails = async (item) => {
if (preOrder) {
await handlePreOrder(item);
} else {
let data = await handleRegularOrder(item);
return data;
}
};
const handlePreOrder = async (item) => {
let Response = await dispatch(
getConfigType({ TypeName: 'Booking Type' })
).unwrap();
let BookingTypeID;
if (Response?.data?.statusCode == 1) {
BookingTypeID = Response?.data?.data?.find(
(item) => item?.ConfigName === 'Dine In'
)?.ConfigId;
}
let Condition = PreOrderSelectedProdNames?.some(
(obj) =>
obj?.InwardDtlId === item?.InwardDtlId &&
obj?.SinglePc === item?.SinglePc
);
if (PreOrderAdditem !== 'AddItems') {
setMessageData('Have To choose Add Item Before select Any Item ');
setMessageType('error');
return;
}
if (Condition) {
setMessageData('Duplicate Data');
setMessageType('error');
return;
}
const calculateWithoutTaxRate = (qty, rate, taxPercentage) => {
const totalAmount = qty * rate;
const taxAmount = (
(totalAmount * taxPercentage) /
(100 + taxPercentage)
).toFixed(2);
const withoutTaxRate = (totalAmount - taxAmount).toFixed(2);
return parseFloat(withoutTaxRate);
};
const SelectedProduct = {
ProdId: item?.ProdId,
InwardDtlId: item?.InwardDtlId,
ProdNameQty: item?.ProdName + ' ' + item?.Size + ' ' + item?.UomName,
ProdName: item?.ProdName,
Size: item?.Size,
UomName: item?.UomName,
OrderQty: 1,
OrderRate: item?.OrderRate,
TotalAmt: item?.OrderRate,
Image: null,
Description: null,
Type: item?.Type,
TaxAmt: 0,
RefundQty: 0,
TaxId: item?.TaxId,
OrderStatus: 'O',
OrderType: 'PRE',
SinglePc: item?.SinglePc,
BookingType: BookingTypeID,
WithoutTaxRate: calculateWithoutTaxRate(
1,
item?.OrderRate,
item?.TaxPercentage
),
StockAvailable: item?.StockAvailable,
};
const Data =
PreOrderSelectedProdNames?.length > 0
? [SelectedProduct, ...PreOrderSelectedProdNames]
: [SelectedProduct];
await setPreOrderSelectedProdNames(Data);
await dispatch(changepreOrderList(Data));
};
const handleRegularOrder = async (item) => {
const isHoldOrder = OrderType === 'Hold';
const addFirst = BillOrderPre === 'Y';
const hasOffer = OfferCheckedInSetup && preferenceOffer;
const calculateTaxAmounts = (qty, rate, taxPercentage) => {
const totalAmount = qty * rate;
const taxAmount = (
(totalAmount * taxPercentage) /
(100 + taxPercentage)
).toFixed(2);
const withoutTaxRate = (totalAmount - taxAmount).toFixed(2);
return {
TotalAmt: totalAmount,
TaxAmt: parseFloat(taxAmount),
WithoutTaxRate: parseFloat(withoutTaxRate),
};
};
// Helper function to create updated cart item
const createUpdatedCartItem = (cartItem, newQty = null) => {
const quantity = newQty || cartItem.OrderQty + 1;
const taxAmounts = calculateTaxAmounts(
quantity,
cartItem.OrderRate,
cartItem.TaxPercentage
);
return {
...cartItem,
OrderQty: quantity,
...taxAmounts,
};
};
// Helper function to create new item for cart
const createNewCartItem = (item, quantity = 1) => {
const taxAmounts = calculateTaxAmounts(
quantity,
item.OrderRate,
item.TaxPercentage
);
return {
...item,
localId: uuidv4(),
OrderQty: quantity,
...taxAmounts,
};
};
dispatch(changeHoldOrderDtl(false));
dispatch(changePreviousOrderLength(CartOrderDetails?.length));
const itemMatchCondition = (cartItem) =>
cartItem.ProdId === item.ProdId &&
cartItem.InwardDtlId === item.InwardDtlId &&
cartItem.OrderRate === item.OrderRate &&
cartItem.BookingTypeName === item.BookingTypeName &&
// console.log(new Date(cartItem.BookedDate).toDateString() , item,"mohandate")
// if both sides have date info, check match too
cartItem.BookedDate &&
item.BookedDate &&
cartItem.BookedDate === item.BookedDate;
const isItemInCart = CartOrderDetails?.find(
(cartItem) => itemMatchCondition(cartItem) && !cartItem.SalesId
);
const isItemInCartHold = CartOrderDetails?.find((cartItem) =>
itemMatchCondition(cartItem)
);
// Filter cart items
const otherOrderDataForNormal = CartOrderDetails?.filter(
(cartItem) => !(itemMatchCondition(cartItem) && !cartItem.SalesId)
);
const otherOrderDataForNormalWithoutSalesId = CartOrderDetails?.filter(
(cartItem) => !itemMatchCondition(cartItem)
);
try {
// CASE 1: Item exists in cart, not Dine In, not Hold order
if (isItemInCart && !isHoldOrder) {
const updatedCartItem = createUpdatedCartItem(isItemInCart);
const updatedData = addFirst
? [updatedCartItem, ...otherOrderDataForNormal]
: [...otherOrderDataForNormal, updatedCartItem];
dispatch(changeOrderCardDetails(updatedData));
UpdateBlockSlot(updatedCartItem);
}
// CASE 2: Item exists in cart (hold), is Hold order
else if (isItemInCartHold && isHoldOrder) {
const updatedCartItem = createUpdatedCartItem(isItemInCartHold);
const updatedData = addFirst
? [updatedCartItem, ...otherOrderDataForNormalWithoutSalesId]
: [...otherOrderDataForNormalWithoutSalesId, updatedCartItem];
dispatch(changeOrderCardDetails(updatedData));
UpdateBlockSlot(updatedCartItem);
}
// CASE 3: New item - not in cart
else {
if (item.OtherProduct === 'Others') {
const newCartItem = createNewCartItem(item, item.OrderQty);
const updatedData = addFirst
? [newCartItem, ...CartOrderDetails]
: [...CartOrderDetails, newCartItem];
dispatch(changeOrderCardDetails(updatedData));
UpdateBlockSlot(newCartItem);
} else {
const newCartItem = createNewCartItem(item, 1);
const updatedData = addFirst
? [newCartItem, ...CartOrderDetails]
: [...CartOrderDetails, newCartItem];
dispatch(changeOrderCardDetails(updatedData));
UpdateBlockSlot(newCartItem);
return newCartItem;
}
}
} catch (error) {
console.error('Error updating order details:', error);
} finally {
// Clean up dispatch calls
dispatch(changeothersdata({}));
dispatch(ChangeNewQrProduct({}));
}
};
const UpdateBlockSlot = async (newCartItem) => {
let BlockPostdata = {
CompId: CompId,
BranchId: BranchId,
AppId: AppId,
Status: 'Block',
CreatedBy: UserId,
ProductList: [
{
ProdId: newCartItem?.ProdId,
InwardDtlId: newCartItem?.InwardDtlId,
SinglePc: newCartItem?.SinglePc,
Qty: 1,
Date: newCartItem?.BookedDate,
},
],
};
await dispatch(PostBlockSlots(BlockPostdata)).unwrap();
};
const returnCount = (ProdName, currentQty, orderDetails, overallpcs) => {
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdName === ProdName
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
},
0
);
// Include combo consumption from ReorderProductData (SetCount == 0)
try {
const reorderComboLines = (ReorderProductData || []).filter(
(a) => a?.Type === 'C'
);
if (reorderComboLines?.length > 0) {
const reorderComboConsumed = reorderComboLines.reduce(
(sum, comboLine) => {
const setZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!setZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((inner, d) => {
const nameMatches =
d?.ProdName === ProdName || d?.ProductName === ProdName;
if (nameMatches && d?.StockAvailable === 'Y') {
const compQty = parseInt(d?.ProductQty ?? 1);
return inner + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return inner;
}, 0);
return sum + consumed;
},
0
);
totalSelectedProductQty =
parseInt(totalSelectedProductQty || 0) +
parseInt(reorderComboConsumed || 0);
}
} catch (_) {}
let getCurrentProdDtl = orderDetails?.filter(
(a) => a?.ProdName === ProdName
);
let ComboProdDtl = orderDetails?.filter((a) => a?.Type === 'C');
if (overallpcs === 'Y' && ComboProdDtl?.length > 0) {
getCurrentProdDtl = getCurrentProdDtl?.filter((a) => a?.Type !== 'C');
}
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
}, 0);
// Combo adjustment:
// If combos (Type === 'C') include this product and that component has SetCount == 0
// and StockAvailable === 'Y', treat each occurrence as consuming one unit.
if (Array.isArray(ComboProdDtl) && ComboProdDtl.length > 0) {
try {
const comboExtraQty = ComboProdDtl.reduce((sum, comboLine) => {
// Use combo-level SetCount when detail-level SetCount is absent
const comboSetCountZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!comboSetCountZero) return sum;
const details = comboLine?.ProdDetail;
if (!Array.isArray(details)) return sum;
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((innerSum, d) => {
const nameMatches =
d?.ProdName === ProdName || d?.ProductName === ProdName;
const stockYes = d?.StockAvailable === 'Y';
if (nameMatches && stockYes) {
const compQty = parseInt(d?.ProductQty ?? 1);
return innerSum + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return innerSum;
}, 0);
return sum + consumed;
}, 0);
totalOrderQty =
parseInt(totalOrderQty || 0) + parseInt(comboExtraQty || 0);
} catch (e) {
// ignore structure mismatches
}
}
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(currentQty) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(currentQty) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
};
const returnOnepcCount = (ProdName, currentQty, orderDetails, overallpcs) => {
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdName === ProdName
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
},
0
);
let getCurrentProdDtl = orderDetails?.filter(
(a) => a?.ProdName === ProdName
);
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
}, 0);
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(currentQty) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(currentQty) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
};
const returnQtyCount = (ProdId, item, orderDetails) => {
if (onePeiceFlow) {
let ItemQuantity = item?.ProdVariantDetails?.reduce(
(accumulator, card) => {
return accumulator + parseInt(card.OverAllPcs || 0);
},
0
);
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdId === ProdId
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
},
0
);
// Include combo consumption from ReorderProductData (pieces flow)
try {
const reorderComboLines = (ReorderProductData || []).filter(
(a) => a?.Type === 'C'
);
if (reorderComboLines?.length > 0) {
const reorderComboConsumed = reorderComboLines.reduce(
(sum, comboLine) => {
const setZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!setZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((inner, d) => {
if (d?.ProdId === ProdId && d?.StockAvailable === 'Y') {
const compQty = parseInt(d?.ProductQty ?? 1);
return inner + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return inner;
}, 0);
return sum + consumed;
},
0
);
totalSelectedProductQty =
parseInt(totalSelectedProductQty || 0) +
parseInt(reorderComboConsumed || 0);
}
} catch (_) {}
let getCurrentProdDtl = orderDetails?.filter((a) => a?.ProdId === ProdId);
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
}, 0);
// Include combo consumption for pieces flow
try {
const comboLines = orderDetails?.filter((a) => a?.Type === 'C') || [];
const comboConsumed = comboLines.reduce((sum, comboLine) => {
const comboSetZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!comboSetZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumedForThisCombo = details.reduce((inner, d) => {
if (d?.ProdId === ProdId && d?.StockAvailable === 'Y') {
const compQty = parseInt(d?.ProductQty ?? 1);
return inner + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return inner;
}, 0);
return sum + consumedForThisCombo;
}, 0);
totalOrderQty =
parseInt(totalOrderQty || 0) + parseInt(comboConsumed || 0);
} catch (_) {}
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(ItemQuantity) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(ItemQuantity) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
} else {
let ItemQuantity = item?.ProdVariantDetails?.reduce(
(accumulator, card) => {
return accumulator + parseInt(card.OverAllQty || 0);
},
0
);
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdId === ProdId
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
},
0
);
// Include combo consumption from ReorderProductData (quantity flow)
try {
const reorderComboLines = (ReorderProductData || []).filter(
(a) => a?.Type === 'C'
);
if (reorderComboLines?.length > 0) {
const reorderComboConsumed = reorderComboLines.reduce(
(sum, comboLine) => {
const setZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!setZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((inner, d) => {
if (d?.ProdId === ProdId && d?.StockAvailable === 'Y') {
return inner + orderQty;
}
return inner;
}, 0);
return sum + consumed;
},
0
);
totalSelectedProductQty =
parseInt(totalSelectedProductQty || 0) +
parseInt(reorderComboConsumed || 0);
}
} catch (_) {}
let getCurrentProdDtl = orderDetails?.filter((a) => a?.ProdId === ProdId);
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
}, 0);
// Include combo consumption for quantity flow
try {
const comboLines = orderDetails?.filter((a) => a?.Type === 'C') || [];
const comboConsumed = comboLines.reduce((sum, comboLine) => {
const comboSetZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!comboSetZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumedForThisCombo = details.reduce((inner, d) => {
if (d?.ProdId === ProdId && d?.StockAvailable === 'Y') {
return inner + orderQty;
}
return inner;
}, 0);
return sum + consumedForThisCombo;
}, 0);
totalOrderQty =
parseInt(totalOrderQty || 0) + parseInt(comboConsumed || 0);
} catch (_) {}
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(ItemQuantity) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(ItemQuantity) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
}
};
const returnCountStock = (
ProdId,
currentQty,
orderDetails,
InwardDtlId,
onepcavailable,
overallpcs
) => {
if (onepcavailable === 'Y') {
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdId === ProdId && a?.InwardDtlId === InwardDtlId
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
},
0
);
// Include combo consumption from ReorderProductData (pieces + batch)
try {
const reorderComboLines = (ReorderProductData || []).filter(
(a) => a?.Type === 'C'
);
if (reorderComboLines?.length > 0) {
const reorderComboConsumed = reorderComboLines.reduce(
(sum, comboLine) => {
const setZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!setZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((inner, d) => {
if (
d?.ProdId === ProdId &&
d?.InwardDtlId === InwardDtlId &&
d?.StockAvailable === 'Y'
) {
const compQty = parseInt(d?.ProductQty ?? 1);
return inner + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return inner;
}, 0);
return sum + consumed;
},
0
);
totalSelectedProductQty =
parseInt(totalSelectedProductQty || 0) +
parseInt(reorderComboConsumed || 0);
}
} catch (_) {}
let getCurrentProdDtl = orderDetails?.filter(
(a) => a?.ProdId === ProdId && a?.InwardDtlId === InwardDtlId
);
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty * card.NoOfPcs
: card.OrderQty
: 0
)
);
}, 0);
// Include combo consumption (no one-piece logic for combos)
try {
const comboLines = orderDetails?.filter((a) => a?.Type === 'C') || [];
const comboConsumed = comboLines.reduce((sum, comboLine) => {
const comboSetZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!comboSetZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumedForThisCombo = details.reduce((inner, d) => {
if (
d?.ProdId === ProdId &&
d?.InwardDtlId === InwardDtlId &&
d?.StockAvailable === 'Y'
) {
const compQty = parseInt(d?.ProductQty ?? 1);
return inner + orderQty * (isNaN(compQty) ? 1 : compQty);
}
return inner;
}, 0);
return sum + consumedForThisCombo;
}, 0);
totalOrderQty =
parseInt(totalOrderQty || 0) + parseInt(comboConsumed || 0);
} catch (_) {}
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(currentQty) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(currentQty) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
} else {
let SelectedProduct = ReorderProductData?.filter(
(a) => a?.ProdId === ProdId && a?.InwardDtlId === InwardDtlId
);
let totalSelectedProductQty = SelectedProduct?.reduce(
(accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
},
0
);
// Include combo consumption from ReorderProductData (quantity + batch)
try {
const reorderComboLines = (ReorderProductData || []).filter(
(a) => a?.Type === 'C'
);
if (reorderComboLines?.length > 0) {
const reorderComboConsumed = reorderComboLines.reduce(
(sum, comboLine) => {
const setZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!setZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumed = details.reduce((inner, d) => {
if (
d?.ProdId === ProdId &&
d?.InwardDtlId === InwardDtlId &&
d?.StockAvailable === 'Y'
) {
return inner + orderQty;
}
return inner;
}, 0);
return sum + consumed;
},
0
);
totalSelectedProductQty =
parseInt(totalSelectedProductQty || 0) +
parseInt(reorderComboConsumed || 0);
}
} catch (_) {}
let getCurrentProdDtl = orderDetails?.filter(
(a) => a?.ProdId === ProdId && a?.InwardDtlId === InwardDtlId
);
let totalOrderQty = getCurrentProdDtl?.reduce((accumulator, card) => {
return (
accumulator +
parseInt(
card?.StockAvailable === 'Y'
? card.SinglePc !== 'Y'
? card.OrderQty
: card.OverAllPcs % card.NoOfPcs >= card.OrderQty
? 0
: card.OrderQty % card.NoOfPcs === 0
? Math.floor(card.OrderQty / card.NoOfPcs)
: Math.floor(card.OrderQty / card.NoOfPcs) + 1
: 0
)
);
}, 0);
// Include combo consumption for quantity flow
try {
const comboLines = orderDetails?.filter((a) => a?.Type === 'C') || [];
const comboConsumed = comboLines.reduce((sum, comboLine) => {
const comboSetZero =
comboLine?.SetCount === 0 || comboLine?.SetCount === '0';
if (!comboSetZero) return sum;
const details = Array.isArray(comboLine?.ProdDetail)
? comboLine?.ProdDetail
: [];
const orderQty = parseInt(comboLine?.OrderQty || 1);
const consumedForThisCombo = details.reduce((inner, d) => {
if (
d?.ProdId === ProdId &&
d?.InwardDtlId === InwardDtlId &&
d?.StockAvailable === 'Y'
) {
return inner + orderQty;
}
return inner;
}, 0);
return sum + consumedForThisCombo;
}, 0);
totalOrderQty =
parseInt(totalOrderQty || 0) + parseInt(comboConsumed || 0);
} catch (_) {}
let OverallProdQty = totalOrderQty - totalSelectedProductQty;
if (
parseInt(currentQty) >
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
)
) {
let count =
parseInt(currentQty) -
parseInt(
Object.keys(ReportholdData)?.length > 0 && totalOrderQty
? OverallProdQty
: getCurrentProdDtl
? totalOrderQty
: 0
);
return parseInt(count);
} else {
let count = 0;
return count;
}
}
};
const returnVariantStock = (data, CartOrderDetails) => {
const baseAvailable =
parseInt(data?.TotalSlotQty || 0) - parseInt(data?.BookedQty || 0);
// Calculate total single piece order qty from cart
const inCartQty = CartOrderDetails?.reduce((acc, item) => {
const same =
item?.InwardDtlId === data?.InwardDtlId &&
item?.ProdVariantName?.toLowerCase() ===
data?.VarientName?.toLowerCase() &&
item?.VariantAvailableFrom === data?.VariantAvailableFrom &&
item?.VariantAvailableTo === data?.VariantAvailableTo &&
item?.BookedDate &&
data?.BookedDate &&
item?.BookedDate?.split('T')[0] === data?.BookedDate?.split('T')[0];
if (same && item?.SinglePc === 'Y') {
return acc + (parseInt(item?.OrderQty) || 0);
}
return acc;
}, 0);
return Math.max(baseAvailable, 0);
};
const varientcolumns = [
{
title: 'Variant Name',
dataIndex: 'VarientName',
key: 'VarientName',
align: 'left',
render: (_, record, index) => (
<span
style={
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record.VarientName}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
) {
Stockfun(record);
}
},
};
},
},
{
title: 'Stock Count',
dataIndex: 'StockCount',
key: 'StockCount',
align: 'Right',
render: (_, record, index) => (
<span
style={
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record.StockCount}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
) {
Stockfun(record);
}
},
};
},
},
{
title: 'Amount',
dataIndex: 'Amount',
key: 'Amount',
align: 'right',
render: (_, record, index) => (
<span
style={
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record.Amount}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (
record.StockCount > 0 ||
record.StockCount === 'Stock Not Maintained'
) {
Stockfun(record);
}
},
};
},
},
];
const stockcolumns = [
{
title: 'Batch No',
dataIndex: 'Batch No',
key: 'Batch No',
align: 'center',
render: (text, record, index) => (
<span
style={
record.StockCount > 0
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record?.['Batch No']}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (record.StockCount > 0) {
StockSelected(record);
}
},
};
},
},
{
title: 'Stock Count',
dataIndex: 'StockCount',
key: 'StockCount',
align: 'center',
render: (_, record, index) => (
<span
style={
record.StockCount > 0
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record.StockCount}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (record.StockCount > 0) {
StockSelected(record);
}
},
};
},
},
{
title: 'Stock Date',
dataIndex: 'Stock Date',
key: 'Stock Date',
align: 'center',
render: (_, record, index) => (
<span
style={
record.StockCount > 0
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record?.['Stock Date']}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (record.StockCount > 0) {
StockSelected(record);
}
},
};
},
},
{
title: 'Exp Date',
dataIndex: 'ExpDate',
key: 'ExpDate',
align: 'center',
render: (_, record, index) => (
<span
style={
record.StockCount > 0
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{record.ExpDate}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (record.StockCount > 0) {
StockSelected(record);
}
},
};
},
},
{
title: 'Price',
dataIndex: 'Price',
key: 'Price',
align: 'center',
render: (_, record, index) => (
<span
style={
record.StockCount > 0
? { color: '#000', cursor: 'pointer' }
: { color: '#f49898', cursor: 'not-allowed' }
}
>
{safeRound(record.Price)}
</span>
),
onCell: (record) => {
return {
onClick: () => {
if (record.StockCount > 0) {
StockSelected(record);
}
},
};
},
},
];
const qtydataSource = [];
qtydata?.ProductDetail?.map((item, index) => {
qtydataSource.push({
key: index,
Quantity: item?.Size + ' ' + item?.UomName,
Amount: item?.ProdVariantDetails?.[0]?.StockDetails?.[0]?.SellPrice,
});
});
// const varientdataSource = [];
// qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.map((item, index) => {
// varientdataSource.push({
// key: index,
// VarientName: item?.ProdVariantName,
// Amount: onePeiceFlow
// ? item?.StockDetails?.[0]?.OnePcsPrice
// : item?.StockDetails?.[0]?.SellPrice,
// VariantAvailableFrom: item?.AvailableFrom,
// VariantAvailableTo: item?.AvailableTo,
// SlotStatus: item?.StockDetails?.[0]?.SlotStatus,
// InwardDtlId: item?.StockDetails?.[0]?.InwardDtlId,
// BookedDate: selectedDate?.format('YYYY-MM-DD'),
// BookedQty: item?.StockDetails?.[0]?.BookedQty,
// TotalSlotQty: item?.StockDetails?.[0]?.TotalSlotQty,
// });
// });
const [dates, setDates] = useState([]);
const [slots, setSlots] = useState([]);
const [isAllSelected, setIsAllSelected] = useState(false);
const formatDate = (dateStr) => {
if (!dateStr) return '';
const date = new Date(dateStr);
const day = String(date.getDate()).padStart(2, '0');
const month = date.toLocaleString('en-US', { month: 'short' });
const year = date.getFullYear();
return `${day} ${month} ${year}`;
};
// useEffect(() => {
// // Process multiple products from draggableCardData for date-based time slots
// if (draggableCardData && draggableCardData.length > 0) {
// const allVariantDetails = [];
// draggableCardData?.forEach((product, productIndex) => {
// // Iterate through all ProductDetail entries for each product
// product?.ProductDetail?.forEach((productDetail, detailIndex) => {
// // Iterate through all ProdVariantDetails for each ProductDetail
// productDetail?.ProdVariantDetails?.forEach((variant, variantIndex) => {
// // Only process variants that have time slots (AvailableFrom and AvailableTo)
// // Get stock details (first stock detail if available)
// const stockDetail = variant?.StockDetails?.[0] || {};
// // Create slot data object
// const slotData = {
// key: `${productIndex}-${detailIndex}-${variantIndex}`,
// ProdId: product?.ProdId,
// ProdName: product?.ProdName,
// VarientName: variant?.ProdVariantName,
// TempDate: variant?.tempDate ,
// BookedDate: variant?.tempDate,
// Amount: onePeiceFlow
// ? stockDetail?.OnePcsPrice || 0
// : stockDetail?.SellPrice || 0,
// VariantAvailableFrom: variant?.AvailableFrom,
// VariantAvailableTo: variant?.AvailableTo,
// SlotStatus: stockDetail?.SlotStatus || null,
// InwardDtlId: stockDetail?.InwardDtlId || null,
// BookedQty: stockDetail?.BookedQty || 0,
// TotalSlotQty: stockDetail?.TotalSlotQty || 0,
// isBooked: stockDetail?.SlotStatus?.toLowerCase() === 'booked',
// isBlocked: stockDetail?.SlotStatus?.toLowerCase() === 'blocked',
// // Additional product info for reference
// ProductIndex: productIndex,
// ProductDetailIndex: detailIndex,
// VariantIndex: variantIndex,
// };
// console.log(slotData, 'slotDataslotData');
// // Add to flat array
// setModalVarientData(slotData)
// // Organize by date and time slot
// }
// );
// });
// });
// console.log(allVariantDetails, 'allVariantDetailsallVariantDetails');
// }
// }, [draggableCardData, qtydata, QtyIndex, onePeiceFlow, selectedDate, isBulk]);
const stockdataSource = [];
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[
VarientIndex
]?.StockDetails?.map((item, index) => {
const expDate = new Date(item?.ExpDate);
stockdataSource.push({
key: index,
'Batch No': item?.BatchRef,
StockCount: onePeiceFlow
? returnCountStock(
item?.ProdId,
item?.OverAllPcs,
CartOrderDetails,
item?.InwardDtlId,
'Y'
)
: returnCountStock(
item?.ProdId,
item?.BalanceQty,
CartOrderDetails,
item?.InwardDtlId,
'N',
item?.OverAllPcs
),
'Stock Date': ExtractDateFormate(item?.InwardDate),
Price: onePeiceFlow ? item?.OnePcsPrice : item?.SellPrice,
ExpDate:
expDate != 'Invalid Date' || null || undefined || ''
? ExtractDateFormate(item?.ExpDate)
: '-',
});
});
const extractProductDetails = (a, QtyIndex, VarientIndex, stockIndex) => {
const detail = a?.ProductDetail?.[QtyIndex];
const variant = detail?.ProdVariantDetails?.[VarientIndex];
const stock = variant?.StockDetails?.[stockIndex];
return { detail, variant, stock };
};
const buildOrderData = (
a,
detail,
variant,
stock,
size,
orderRate,
onePcs
) => {
const { ProdCat, Type, OverAllQty: OverallQuantity, CounterName } = a || {};
const {
ActiveStatus,
AvailableFrom,
AvailableTo,
Cess,
HSNCode,
BrandName,
OpeningQty,
PartNumber,
ProdId,
ProdLogo,
ProdName,
QRCode,
QtyBasedPrice,
Rack,
StockAvailable,
TokenAvailable,
TaxId,
TaxPercentage,
TaxIdName: TaxName,
UniqueId,
UomName,
DiscountLimitType,
DiscountLimit,
} = detail || {};
const {
NoOfPcs,
BalanceQty,
BatchRef,
ModelNumber,
ProductIdentifierDtls: FullProductIdentifierDtls,
InwardDate,
InwardDtlId,
ExpDate,
InwardId,
MRP,
OnePcsPrice,
SellPrice,
SuppId,
SuppName,
OverAllPcs,
OfferPrice: Offer,
TotalSlotQty,
BookedQty,
} = stock || {};
const BalanceBookedQty = TotalSlotQty || 0 - BookedQty || 0;
const {
ProdVariantName,
AvailableFrom: VariantAvailableFrom,
AvailableTo: VariantAvailableTo,
TempDate,
} = variant || {};
return {
ProdCat,
Type,
OverallQuantity,
ActiveStatus,
AvailableFrom,
AvailableTo,
Cess,
HSNCode,
BrandName,
OpeningQty,
PartNumber,
ProdId,
ProdLogo,
ProdName,
QRCode,
QtyBasedPrice,
Rack,
Size: size,
StockAvailable,
TokenAvailable,
TaxId,
TaxPercentage,
TaxName,
UniqueId,
UomName: onePcs ? 'PCS' : UomName,
SinglePc: onePcs ? 'Y' : 'N',
NoOfPcs,
ProdVariantName,
VariantAvailableFrom,
VariantAvailableTo,
BalanceQty,
BatchRef,
ModelNumber,
FullProductIdentifierDtls,
InwardDate,
InwardDtlId,
ExpDate,
InwardId,
MRP: onePcs ? OnePcsPrice : MRP,
OrderRate: orderRate,
SellingPrice: orderRate,
SuppId,
SuppName,
OverAllPcs,
Offer,
BookingTypeName: BookingType,
CounterName,
DiscountLimitType,
DiscountLimit,
BookedDate: TempDate,
BalanceBookedQty,
};
};
const resetProductModal = () => {
setModelQty(false);
setSelectedBrand('Others');
// setModalVarient(false);
setModelstock(false);
setQtyIndex(0);
setVarientIndex(0);
setVarItem(0);
setItem();
setStockItem();
dispatch(changeSearchedData(''));
// setOnePeiceFlow(false);
};
const dataTransfer = async (
a,
QtyIndex,
VarientIndex,
stockIndex,
onePcs
) => {
const { detail, variant, stock } = extractProductDetails(
a,
QtyIndex,
VarientIndex,
stockIndex
);
// mohan 05-08-2025
const price = onePcs
? stock?.OnePcsPrice
: RetailWSSalesType === 'W'
? stock?.WhSalePrice || stock?.SellPrice
: stock?.SellPrice;
const size = onePcs ? '1' : detail?.Size;
if (quickBranchtoBranchTransfer) {
const data = buildOrderData(
a,
detail,
variant,
stock,
size,
price,
onePcs
);
if (!selectedProducts?.some((s) => s.ProdId === detail?.ProdId)) {
dispatch(
changeBtoBQuickProductTransfer({
action: quickBranchtoBranchTransfer,
selectedProducts: [
...selectedProducts,
{
...data,
OrderQty: 1,
TotalAmt: parseFloat(detail?.OrderRate).toFixed(2),
},
],
})
);
} else {
setMessageType('error');
setMessageData('Product already added');
}
} else {
if (WeightScalePort === true) {
const isKgsProduct =
(detail?.UomName?.toLowerCase() === 'kgs' ||
detail?.UomName?.toLowerCase() === 'kg') &&
detail?.Size === '1';
if (isKgsProduct) {
if (WeightScaleWeight > 0 && WeightScaleWeight !== null) {
const basePrice = onePcs ? stock?.OnePcsPrice : stock?.SellPrice;
const totalRate = (
(basePrice / 1000) *
(parseFloat(WeightScaleWeight) * 1000)
).toFixed(2);
const data = buildOrderData(
a,
detail,
variant,
stock,
parseFloat(WeightScaleWeight),
totalRate,
onePcs
);
resetProductModal();
await AddOrderDetails(data);
dispatch(changeWeightScaleWeight(null));
setRepeatedModel(false);
setProdexpir(false);
} else {
setMessageType('error');
setMessageData('Please Connect WeightScale');
}
} else {
setMessageType('error');
setMessageData('Please Select 1Kg Product');
}
} else {
const isValidPcs =
onePcs && stock?.NoOfPcs > 0 && stock?.OnePcsPrice > 0;
const allowNonPcs =
!onePcs ||
(detail?.StockAvailable !== 'Y' && onePcs && stock?.OnePcsPrice > 0);
if (isValidPcs || allowNonPcs) {
const data = buildOrderData(
a,
detail,
variant,
stock,
size,
price,
onePcs
);
resetProductModal();
let dataReturn = await AddOrderDetails(data);
return dataReturn;
} else {
setMessageType('error');
setMessageData(
'Please add No.of pieces Inside the box in Product master'
);
resetProductModal();
}
}
}
};
useEffect(() => {
setPreOrderSelectedProdNames(GPreOrderList);
}, [GPreOrderList]);
const pickData = (e, item) => {
if (e.target.checked === true) {
setSelectedProdNames([
...globalAllItemdata,
{
ProdName: item.ProdName,
ProdId: item.ProductDetail?.[0]?.ProdId,
ProdCat: item.ProdCat,
ProdCatName: item.ProdCatName,
},
]);
} else {
setSelectedProdNames(
SelectedProdNames?.filter(
(data) =>
!(data?.ProdName == item.ProdName && data?.ProdCat == item.ProdCat)
)
);
}
};
const handleQuickCancel = async () => {
setQuickAdd(false);
dispatch(changeSearchedData(''));
// Base data for all calls
let baseData = {
CompId,
BranchId,
AppId,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
// 👇 Only add date if AvailableDate and selectedDate exist
// if (AvailableDate && selectedDate) {
// baseData.date = Array.isArray(selectedDate)
// ? selectedDate
// .map((d) => (d?.format ? d.format('YYYY-MM-DD') : d))
// .join(',')
// : selectedDate?.format
// ? selectedDate.format('YYYY-MM-DD')
// : selectedDate;
// }
// 1⃣ Favourite items
// await dispatch(getSelectedFavItems(baseData)).unwrap();
// 2⃣ For layout with SubCategory
let data1 = {
...baseData,
ProdSubCat,
};
// 3⃣ For layout without SubCategory
let data2 = {
compId: CompId,
branchId: BranchId,
appId: AppId,
prodCat: ProdCat,
...(AvailableDate && selectedDate
? {
fromDate: selectedDate?.[0],
toDate: selectedDate?.[1],
}
: {}),
};
if (
templateData?.BookingLayout?.[1]?.some(
(item) => item?.OptionName === 'SubCategory'
) &&
ProdSubCat
) {
await dispatch(getLayoutproductCard(data1)).unwrap();
} else if (
!templateData?.BookingLayout?.[1]?.some(
(item) => item?.OptionName === 'SubCategory'
)
) {
await dispatch(getCardDataWithoutSubmodule(data2)).unwrap();
} else {
await dispatch(getCardDataWithoutSub(data2)).unwrap();
}
};
const onComplete = useCallback(() => {
setMessageData(null);
setMessageType(null);
}, []);
const expFun = (item) => {
let count = item?.ProductDetail?.length;
if (count > 1) {
Quantity();
} else {
setVarItem(0);
SingleQuantity(item, onePeiceFlow);
}
setexpModel(false);
setProdexpir(true);
setQtydata(item);
};
let brandMapping = {};
// Group product details by Brand ID
qtydata?.ProductDetail?.forEach((item) => {
const brandId = item?.BrandName;
if (!brandMapping[brandId]) {
brandMapping[brandId] = [];
}
brandMapping[brandId].push(item);
});
const BrandCheckresult = qtydata?.ProductDetail?.every((product) => {
return product.BrandName === null || product.BrandName === undefined;
});
const ItemSellingPrice = (item) => {
// const variantWithDetails = item?.ProductDetail?.find((variant) => variant?.ProdVariantDetails?.length > 0);
const variantWithDetails = item?.ProductDetail?.find(
(variant) =>
variant?.ProdVariantDetails?.length > 0 &&
variant?.ProdVariantDetails?.[0]?.StockDetails?.[0]?.SellPrice
);
if (variantWithDetails) {
// Access the details of the first variant with ProdVariantDetails
const firstVariantDetails =
variantWithDetails?.ProdVariantDetails?.[0]?.StockDetails?.[0]
?.SellPrice;
return firstVariantDetails;
} else {
// Handle the case where no variant satisfies the condition
return null; // or any other value you want to return
}
};
const ItemSize = (item) => {
const variantWithDetails = item?.ProductDetail?.find(
(variant) => variant?.ProdVariantDetails?.length > 0
);
if (variantWithDetails) {
// Access the details of the first variant with ProdVariantDetails
const firstVariantDetails = variantWithDetails?.Size;
return firstVariantDetails;
} else {
// Handle the case where no variant satisfies the condition
return null; // or any other value you want to return
}
};
const ItemUomName = (item) => {
const variantWithDetails = item?.ProductDetail?.find(
(variant) => variant?.ProdVariantDetails?.length > 0
);
if (variantWithDetails) {
// Access the details of the first variant with ProdVariantDetails
const firstVariantDetails = variantWithDetails?.UomName;
return firstVariantDetails;
} else {
// Handle the case where no variant satisfies the condition
return null; // or any other value you want to return
}
};
const expQtyFun = (index) => {
const selectedProIndex = qtydata?.ProductDetail?.findIndex(
(item) =>
item?.ProdId === index?.ProdId &&
item?.Size === index?.Size &&
item?.UomName === index?.UomName &&
item?.Brand === index?.Brand
);
if (selectedProIndex !== -1) {
const count =
qtydata?.ProductDetail[selectedProIndex]?.ProdVariantDetails?.length ||
0;
if (count > 1) {
setModelQty(false);
setSelectedBrand('Others');
setModalVarient(true);
} else {
const item = { QtyIndex: selectedProIndex, VarientIndex: 0 };
singleVarient(item);
setModelQty(false);
setSelectedBrand('Others');
}
}
setQtyIndex(selectedProIndex);
setRepeatedModel(true);
setExpQtyModel(false);
};
const expVerFun = (item) => {
let count =
qtydata?.ProductDetail?.[QtyIndex]?.ProdVariantDetails?.[item]
?.StockDetails?.length;
if (count > 1) {
setRepeatedModel(true);
setModalVarient(false);
setModelstock(true);
} else {
setRepeatedModel(true);
dataTransfer(qtydata, QtyIndex, item, 0, onePeiceFlow);
setModelQty(false);
setSelectedBrand('Others');
}
setexpVarModel(false);
};
const expStockFun = (item) => {
dataTransfer(qtydata, QtyIndex, VarientIndex, item, onePeiceFlow);
setexpStockModel(false);
};
const getMaxBrandWidth = () => {
let maxBrandDataLength = 0;
// Iterate through each brand and find the maximum length of the specified key
Object.values(brandMapping).forEach((brand) => {
const keyDataLength = brand.length;
if (keyDataLength > maxBrandDataLength) {
maxBrandDataLength = keyDataLength;
}
});
// Set your width logic here based on the maxBrandDataLength
const maxWidth = maxBrandDataLength >= 5 ? 750 : 'max-content';
return maxWidth;
};
useEffect(() => {
function handleResize() {
setScreenWidth(window.innerWidth);
}
window.addEventListener('resize', handleResize);
return () => {
window.removeEventListener('resize', handleResize);
};
}, []);
useEffect(() => {
function handleResize() {
setScreenHeight(window.innerHeight);
}
window.addEventListener('resize', handleResize);
return () => {
window.removeEventListener('resize', handleResize);
};
}, []);
// Example usage for checking the length of 'ProdVariantDetails'
const widthBasedOnProdVariantDetails = getMaxBrandWidth();
const ExpDate = useSelector(GlobalExpDateforHeight);
let containerHeight = '';
if (templateData?.BookingLayout?.[0] === 'Layout1') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 310}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 300}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 310}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 340}px`
: '63vh'
: screenWidth < 600
? `${props?.screenHeight - 350}px`
: '62vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 300}px`
: '63vh'
: screenWidth < 600
? `${props?.screenHeight - 310}px`
: '62vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 300}px`
: '60vh'
: screenWidth < 600
? `${props?.screenHeight - 310}px`
: '59vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 300}px`
: '60vh'
: screenWidth < 600
? `${props?.screenHeight - 310}px`
: '59vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 300}px`
: '60vh'
: screenWidth < 600
? `${props?.screenHeight - 310}px`
: '59vh'
: '76vh';
}
} else if (templateData?.BookingLayout?.[0] === 'Layout2') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 310}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '60vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '63vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '62vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '63vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '62vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '61vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '59vh'
: '74vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 310}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: '75vh';
}
} else if (templateData?.BookingLayout?.[0] === 'Layout3') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 390}px`
: '58vh'
: screenWidth < 600
? `${props?.screenHeight - 400}px`
: '57vh'
: '73vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 390}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 400}px`
: '56vh'
: '73vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 395}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 400}px`
: '56vh'
: '73vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 390}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 400}px`
: '56vh'
: '75vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 385}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 395}px`
: '56vh'
: '72vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 385}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 395}px`
: '56vh'
: '72vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 390}px`
: '57vh'
: screenWidth < 600
? `${props?.screenHeight - 400}px`
: '56vh'
: '72vh';
}
} else if (templateData?.BookingLayout?.[0] === 'Layout4') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 220}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 230}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 230}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 240}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 230}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 240}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '73vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: '88vh';
}
} else if (templateData?.BookingLayout?.[0] === 'Layout5') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 280}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 290}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 280}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 280}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 270}px`
: '70vh'
: '88vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 270}px`
: '72vh'
: screenWidth < 600
? `${props?.screenHeight - 280}px`
: '70vh'
: '88vh';
}
} else if (templateData?.BookingLayout?.[0] === 'Layout6') {
if (templateData?.BookingBilling?.[0] == 'Billing1') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 330}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 340}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing2') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 260}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 370}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing3') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing4') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 320}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing5') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 290}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 300}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing6') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 320}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 330}px`
: '60vh'
: '76vh';
} else if (templateData?.BookingBilling?.[0] == 'Billing7') {
containerHeight = isMobile
? ExpDate >= 7
? screenWidth < 600
? `${props?.screenHeight - 280}px`
: '61vh'
: screenWidth < 600
? `${props?.screenHeight - 290}px`
: '60vh'
: '76vh';
}
}
//new
useEffect(() => {
// if (Array.isArray(cardData)) {
// const withIds = cardData.map((item, idx) => ({
// ...item,
// id: item?.ProductDetail?.[0]?.ProdName + '-' + idx,
// }));
// // const newData = alphabeticFormat
// // ? [...withIds].sort((a, b) => {
// // const nameA = a?.ProductDetail?.[0]?.ProdName || "";
// // const nameB = b?.ProductDetail?.[0]?.ProdName || "";
// // return nameA.localeCompare(nameB);
// // })
// // : [...withIds].sort((a, b) => {
// // const nameA = a?.ProductDetail?.[0]?.ProdName || "";
// // const nameB = b?.ProductDetail?.[0]?.ProdName || "";
// // return nameB.localeCompare(nameA);
// // });
// setDraggableCardData(withIds);
// }
if (Array.isArray(cardData)) {
const withIds = cardData.map((product, productIndex) => {
const updatedProductDetail = (product?.ProductDetail || []).map(
(detail, detailIndex) => {
const updatedVariants = (detail?.ProdVariantDetails || []).map(
(variant, variantIndex) => {
const stock = variant?.StockDetails?.[0] || {}; // take the first stock detail
// Merge stock details directly into variant
return {
key: `${productIndex}-${detailIndex}-${variantIndex}`,
...variant,
VariantAvailableFrom: variant?.AvailableFrom,
VariantAvailableTo: variant?.AvailableTo,
BookedDate: variant?.TempDate,
...stock, // flattening stock fields
};
}
);
return {
...detail,
ProdVariantDetails: updatedVariants, // replaced with flattened variants
};
}
);
return {
...product,
id: product?.ProductDetail?.[0]?.ProdName + '-' + productIndex,
ProductDetail: updatedProductDetail,
};
});
setDraggableCardData(withIds);
}
}, [cardData, alphabeticFormat]);
const sensors = useSensors(
useSensor(PointerSensor, {
activationConstraint: {
distance: isMobile ? 5 : 8, // <- reduced distance for mobile
},
}),
useSensor(TouchSensor, {
activationConstraint: {
delay: isMobile ? 50 : 100, // <- even faster response for mobile
tolerance: isMobile ? 10 : 8, // <- more tolerance for mobile touch
},
})
);
const handleDragEnd = (event) => {
const { active, over } = event;
// Ensure `over` is not null
if (!over) return;
if (active.id !== over.id) {
const oldIndex = draggableCardData.findIndex((i) => i.id === active.id);
const newIndex = draggableCardData.findIndex((i) => i.id === over.id);
const updatedData = arrayMove(draggableCardData, oldIndex, newIndex);
// const newData = alphabeticFormat
// ? [...updatedData].sort((a, b) => {
// const nameA = a?.ProductDetail?.[0]?.ProdName || "";
// const nameB = b?.ProductDetail?.[0]?.ProdName || "";
// return nameA.localeCompare(nameB);
// })
// : [...updatedData].sort((a, b) => {
// const nameA = a?.ProductDetail?.[0]?.ProdName || "";
// const nameB = b?.ProductDetail?.[0]?.ProdName || "";
// return nameB.localeCompare(nameA);
// });
setDraggableCardData(updatedData);
dispatch(changeCardData(updatedData));
}
};
const updateScrollButtons = () => {
const container = scrollContainerRef.current;
if (!container) return;
const { scrollLeft, scrollWidth, clientWidth } = container;
setShowLeftButton(scrollLeft > 5);
setShowRightButton(scrollLeft + clientWidth < scrollWidth - 5);
};
useEffect(() => {
const container = scrollContainerRef.current;
if (!container) return;
// ✅ Call once after layout
requestAnimationFrame(() => {
updateScrollButtons();
});
container.addEventListener('scroll', updateScrollButtons);
window.addEventListener('resize', updateScrollButtons);
const resizeObserver = new ResizeObserver(updateScrollButtons);
resizeObserver.observe(container);
return () => {
container.removeEventListener('scroll', updateScrollButtons);
window.removeEventListener('resize', updateScrollButtons);
resizeObserver.disconnect();
};
}, [modelstock, ModalVarient, modelQty]);
const handleScrollClickLeft = (scrollOffset) => {
scrollContainerRef.current.scrollBy({
left: -scrollOffset,
behavior: 'smooth',
});
};
const handleScrollClickRight = (scrollOffset) => {
scrollContainerRef.current.scrollBy({
left: scrollOffset,
behavior: 'smooth',
});
};
// const isDragging = useRef(false);
// MOUSE EVENTS
const handleMouseDown = (e) => {
isDragging.current = true;
startX.current = e.pageX - scrollContainerRef.current.offsetLeft;
scrollLeft.current = scrollContainerRef.current.scrollLeft;
scrollContainerRef.current.style.cursor = 'grabbing';
};
const handleMouseMove = (e) => {
if (!isDragging.current) return;
e.preventDefault(); // Important: prevents text selection and smooth scroll interference
const x = e.pageX - scrollContainerRef.current.offsetLeft;
const walk = (x - startX.current) * 0.8; // Adjust multiplier for speed
scrollContainerRef.current.scrollLeft = scrollLeft.current - walk;
};
const handleMouseUp = () => {
isDragging.current = false;
scrollContainerRef.current.style.cursor = 'grab';
};
// TOUCH EVENTS
const handleTouchStart = (e) => {
isDragging.current = true;
startX.current = e.touches[0].pageX - scrollContainerRef.current.offsetLeft;
scrollLeft.current = scrollContainerRef.current.scrollLeft;
};
const handleTouchMove = (e) => {
if (!isDragging.current) return;
e.preventDefault(); // Prevents native scrolling
const x = e.touches[0].pageX - scrollContainerRef.current.offsetLeft;
const walk = (x - startX.current) * 0.8; // Adjust multiplier as needed
scrollContainerRef.current.scrollLeft = scrollLeft.current - walk;
};
const handleTouchEnd = () => {
isDragging.current = false;
};
const allProducts = Object.values(brandMapping).flat();
const brandGroups = {};
allProducts.forEach((product) => {
const brandName =
product.BrandName &&
product.BrandName !== 'null' &&
product.BrandName !== 'undefined' &&
product.BrandName.trim() !== ''
? product.BrandName
: 'Others';
if (!brandGroups[brandName]) {
brandGroups[brandName] = [];
}
brandGroups[brandName].push(product);
});
useEffect(() => {
const brandKeys = Object.keys(brandGroups || {});
if (brandKeys.length === 0) return;
// Only set if selectedBrand is not present in the new brandGroups
if (!brandKeys.includes(selectedBrand)) {
if (brandKeys.includes('Others')) {
setSelectedBrand('Others');
} else {
setSelectedBrand(brandKeys[0]);
}
}
}, [brandGroups]);
const sortedBrandNames = Object.keys(brandGroups).sort((a, b) =>
a === 'Others' ? -1 : b === 'Others' ? 1 : 0
);
const [prodname, setprodname] = useState('');
const [prodQty, setprodQty] = useState(0);
const normalize = (str) => str?.toLowerCase()?.replace(/\s+/g, ' ')?.trim();
const result = prodname
? (cardData || [])?.filter(
(item) =>
normalize(item.ProdName).includes(normalize(prodname)) ||
normalize(item.ProdCatName).includes(normalize(prodname)) ||
item.ProductDetail?.some((detail) =>
normalize(detail.ProdName).includes(normalize(prodname))
)
)
: cardData;
const getDatePickerValue = (selectedDate) => {
if (Array.isArray(selectedDate) && selectedDate.length === 2) {
// Convert both dates in array to dayjs objects
return [dayjs(selectedDate[0]), dayjs(selectedDate[1])];
}
};
useEffect(() => {
const item = result?.[0];
const detail = item?.ProductDetail?.[0];
const isInStock =
detail?.StockAvailable === 'Y' && item?.OverAllQty > prodQty;
const isStockNotTracked = detail?.StockAvailable === 'N';
if (result?.length > 0 && prodname && (isInStock || isStockNotTracked)) {
CardOnclick(result?.[0]);
// AddOrderDetails2(result?.[0])
} else if (item?.OverAllQty < prodQty) {
setMessageType('error');
setMessageData('NoStack');
}
}, [prodname]);
function encrypt(code, key) {
// Implement encryption logic using a secure algorithm
// For demonstration purposes, this is a simple XOR encryption
let encrypted = (
<>
<div
className="bs-item-card-masterdiv"
style={{
display: 'flex',
flexDirection: 'column',
overflowY: 'scroll',
height: '80vh',
paddingBottom: '6rem',
}}
ref={itemListScrollRef}
>
{messageType && messageData && (
<Messages
messageType={messageType}
messageData={messageData}
onComplete={onComplete}
/>
)}
<div
className="voiceToTextIcon"
style={{
position: 'absolute',
zIndex: '12',
top:
templateData?.BookingLayout?.[0] === 'Layout5' ||
templateData?.BookingLayout?.[0] === 'Layout4' ||
templateData?.BookingLayout?.[0] === 'Layout6'
? '2.5rem'
: '',
}}
onClick={() => {
// trigger child function
voiceTriggerRef?.current?.listening();
}}
>
<VoiceToTextItemCard
ref={voiceTriggerRef}
setVoiceData={(data) => {
setprodname(data.product);
setprodQty(data.qty);
}}
/>
</div>
{/* <p>{prodname}</p> */}
<div style={{ display: 'flex', justifyContent: 'flex-start' }}>
<div
className="BSItemCard-master-container"
style={{
rowGap: cardFunction?.BigImage ? '15px' : '15px',
pointerEvents: OrderType === 'Failed' ? 'none' : 'auto',
overflow: 'auto',
}}
>
{/* <div className="BSItemCard-master-container" > */}
{cardData?.length > 0 ? (
<>
<DndContext
sensors={sensors}
collisionDetection={closestCenter}
onDragEnd={handleDragEnd}
>
<SortableContext
items={draggableCardData?.map((item) => item?.id)}
strategy={rectSortingStrategy}
>
<div
style={{
display: 'flex',
flexWrap: 'wrap',
gap: '8px',
}}
className={
templateData?.BookingCard?.[0] != 'Card4'
? ''
: 'CategoryHorizontalNewcontainer'
}
>
{draggableCardData.map((item, index) => (
<SortableCard
key={item.id || index}
id={item.id || index}
item={item}
>
{templateData?.BookingCard?.[0] != 'Card4' ? (
<div
style={{
position: 'relative',
overflow: 'auto',
}}
className={
// (item?.OverAllQty !== undefined &&
// returnCount(
// item?.ProductDetail?.[0]?.ProdVariantDetails?.length > 0,
// item?.OverAllQty,
// CartOrderDetails,
// item?.OverAllPcs
// ) > 0) ||
// item?.ProductDetail?.some(
// (item) => item?.StockAvailable !== 'Y'
// )
item?.ProductDetail?.[0]?.ProdVariantDetails
?.length > 0
? 'BkPrdCardActive'
: 'BkPrdCardDeActive'
}
>
{!isMobile ? (
<Tooltip title={item.ProdName}>
{globaldata && (
<input
type="checkbox"
value={item.ProductDetail?.[0]?.ProdId}
name={item.ProdName}
onChange={(e) => pickData(e, item)}
style={{
position: 'absolute',
zIndex: 1,
transform: 'scale(1.5)',
cursor: 'pointer',
}}
checked={(
globalAllItemdata || EditfavItems
)?.some(
// (a) => a?.ProdName === item?.ProdName
(a) =>
a?.ProdName === item?.ProdName &&
a?.ProdCat === item?.ProdCat
)}
/>
)}
<div
style={{
alignItems: 'center',
backgroundColor:
cardFunction?.SmallImage &&
cardFunction?.Background &&
(SelectedCardColor
? SelectedCardColor?.[
'BackgroundColor'
]
: ''),
padding:
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown
? cardFunction?.SmallImage &&
'5px 9px'
: '8px 2px',
flexDirection:
cardFunction?.ImageRight &&
'row-reverse'
? cardFunction?.ImageRight &&
'row-reverse'
: cardFunction?.ImageUp && 'column'
? cardFunction?.ImageUp &&
'column'
: cardFunction?.ImageDown &&
'column-reverse'
? cardFunction?.ImageDown &&
'column-reverse'
: cardFunction?.ImageLeft &&
'row',
borderRadius:
cardFunction?.EdgeCurve && '6px',
width:
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown &&
!cardFunction?.BigImage &&
!cardFunction?.ImageRight &&
cardFunction?.SmallImage &&
(cardFunction?.ImageUp ||
cardFunction?.ImageDown)
? '6rem'
: cardFunction?.BigImage && '9rem',
height:
!cardFunction?.ImageUp &&
!cardFunction?.BigImage &&
'',
pointerEvents: globaldata && 'none',
}}
className={
cardFunction?.SmallImage
? 'BSItemCard-container-smallimage'
: 'BSItemCard-container'
}
onClick={(e) => {
CardOnclick(item, index);
}}
data-aos="zoom-in"
data-aos-duration="600"
>
{(cardFunction?.BigImage ||
cardFunction?.SmallImage) && (
<img
style={{
objectFit:
cardFunction?.BigImage && '',
height: !cardFunction?.BigImage
? (!cardFunction?.BigImage &&
cardFunction?.SmallImage) ||
cardFunction?.ImageLeft ||
cardFunction?.ImageUp ||
cardFunction?.ImageDown
? '3rem'
: cardFunction?.BigImage &&
'7rem'
: '5rem',
}}
className={
cardFunction?.SmallImage
? 'BSItemCard-image-smallimage'
: 'BSItemCard-image'
}
src={
item?.ProductDetail?.[0]
?.ProdLogo === ''
? defaultimage
: item?.ProductDetail?.[0]
?.ProdLogo
? item?.ProductDetail?.[0]
?.ProdLogo
: defaultimage
}
alt=""
/>
)}
<div
className={
cardFunction?.SmallImage
? 'BSItemCard-content-smallimage'
: 'BSItemCard-content'
}
style={{
backgroundColor:
cardFunction?.Background &&
(SelectedCardColor
? SelectedCardColor?.[
'BackgroundColor'
]
: ''),
position: !cardFunction?.BigImage
? 'relative'
: 'absolute',
flexDirection:
!cardFunction?.BigImage && 'column',
borderRadius:
!cardFunction?.BigImage &&
cardFunction?.EdgeCurve &&
'6px',
bottom: cardFunction?.BigImage && '',
cardFunction,
width:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'',
height: cardFunction?.SmallImage
? '5.5rem'
: !cardFunction?.BigImage &&
'5.5rem',
alignItems:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'center',
textAlign:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'center',
flexWrap:
cardFunction?.BigImage && 'wrap',
// flexDirection:
// cardFunction?.SmallImage ||
// (cardFunction?.BigImage && "column"),
}}
>
<p
style={{
textTransform:
cardFunction?.TextCapitalize &&
'uppercase',
width: !cardFunction?.SmallImage
? cardFunction?.BigImage &&
'120px'
: cardFunction?.SmallImage &&
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown &&
'85px',
// Width: cardFunction?.BigImage && "70px",
fontSize:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'12px', //naresh27
whiteSpace:
!cardFunction?.BigImage &&
'pre-wrap',
margin: 'auto',
fontFamily: SelectedCardFont
? SelectedCardFont
: '',
color: SelectedCardColor
? SelectedCardColor?.['FontColor']
: '',
textOverflow: 'ellipsis',
}}
className="BSItemCard-itemName"
>
{item?.ProdName}
{}
</p>
{cardFunction?.Price && (
<p
className="BSItemCard-itemPrice"
style={{
fontSize:
!cardFunction?.SmallImage
? cardFunction?.BigImage &&
'12px'
: '12px',
textAlign: 'center',
lineHeight: '2',
fontFamily: SelectedCardFont
? SelectedCardFont
: '',
color: SelectedCardColor
? SelectedCardColor?.[
'FontColor'
]
: '',
}}
>
{ItemSellingPrice(item)}&nbsp;
{/* {item?.ProductDetail?.[0]?.ProdVariantDetails?.[0]?.StockDetails?.[0]?.SellPrice}&nbsp; */}
{/* {ItemSellingPrice(item)} */}
<span className="BSItemCard-itemCount">
({ItemSize(item)}
{ItemUomName(item)})
</span>
</p>
)}
</div>
{cardFunction?.StockCount &&
item?.OverAllQty !== undefined &&
item?.OverAllQty !== 0 && (
<div
style={{
top:
!cardFunction?.BigImage && '0',
right:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'0px',
position: 'absolute',
}}
className={
cardFunction?.BigImage
? 'BSItemCard-badge'
: 'BSItemCard-badge-withoutimage'
}
>
{item?.ProductDetail?.some(
(item) =>
item?.StockAvailable === 'Y'
) &&
item?.OverAllQty !== null && (
<Badge
count={returnCount(
item?.ProductDetail?.[0]
?.ProdName,
item?.OverAllQty,
CartOrderDetails
)}
overflowCount={10000}
></Badge>
)}
</div>
)}
</div>
</Tooltip>
) : (
<>
{globaldata && (
<input
type="checkbox"
value={item.ProductDetail?.[0]?.ProdId}
name={item.ProdName}
onChange={(e) => pickData(e, item)}
style={{
position: 'absolute',
zIndex: 1,
transform: 'scale(1.5)',
cursor: 'pointer',
}}
checked={(
globalAllItemdata || EditfavItems
)?.some(
// (a) => a?.ProdName === item?.ProdName
(a) =>
a?.ProdName === item?.ProdName &&
a?.ProdCat === item?.ProdCat
)}
/>
)}
<div
style={{
alignItems: 'center',
backgroundColor:
cardFunction?.SmallImage &&
cardFunction?.Background &&
(SelectedCardColor
? SelectedCardColor?.[
'BackgroundColor'
]
: ''),
padding:
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown
? cardFunction?.SmallImage &&
'5px 9px'
: '8px 2px',
flexDirection:
cardFunction?.ImageRight &&
'row-reverse'
? cardFunction?.ImageRight &&
'row-reverse'
: cardFunction?.ImageUp && 'column'
? cardFunction?.ImageUp &&
'column'
: cardFunction?.ImageDown &&
'column-reverse'
? cardFunction?.ImageDown &&
'column-reverse'
: cardFunction?.ImageLeft &&
'row',
borderRadius:
cardFunction?.EdgeCurve && '6px',
width:
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown &&
!cardFunction?.BigImage &&
!cardFunction?.ImageRight &&
cardFunction?.SmallImage &&
(cardFunction?.ImageUp ||
cardFunction?.ImageDown)
? '6rem'
: cardFunction?.BigImage && '9rem',
height:
!cardFunction?.ImageUp &&
!cardFunction?.BigImage &&
'',
pointerEvents: globaldata && 'none',
}}
className={
cardFunction?.SmallImage
? 'BSItemCard-containers-smallimage-mobile'
: 'BSItemCard-containers-mobile'
}
onClick={(e) => {
CardOnclick(item, index);
}}
// data-aos="zoom-in" data-aos-duration="600"
>
{(cardFunction?.BigImage ||
cardFunction?.SmallImage) && (
<img
style={{
objectFit:
cardFunction?.BigImage && '',
height: !cardFunction?.BigImage
? (!cardFunction?.BigImage &&
cardFunction?.SmallImage) ||
cardFunction?.ImageLeft ||
cardFunction?.ImageUp ||
cardFunction?.ImageDown
? '3rem'
: cardFunction?.BigImage &&
'7rem'
: '4rem',
}}
className={
cardFunction?.SmallImage
? 'BSItemCard-image-smallimage'
: 'BSItemCard-image'
}
src={
item?.ProductDetail?.[0]
?.ProdLogo === ''
? defaultimage
: item?.ProductDetail?.[0]
?.ProdLogo
? item?.ProductDetail?.[0]
?.ProdLogo
: defaultimage
}
alt=""
/>
)}
<div
className={
cardFunction?.SmallImage
? 'BSItemCard-content-smallimage'
: 'BSItemCard-content'
}
style={{
backgroundColor:
cardFunction?.Background &&
(SelectedCardColor
? SelectedCardColor?.[
'BackgroundColor'
]
: ''),
position: !cardFunction?.BigImage
? 'relative'
: 'absolute',
flexDirection:
!cardFunction?.BigImage && 'column',
borderRadius:
!cardFunction?.BigImage &&
cardFunction?.EdgeCurve &&
'6px',
bottom: cardFunction?.BigImage && '',
cardFunction,
width:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'',
height: cardFunction?.SmallImage
? '5.5rem'
: !cardFunction?.BigImage &&
'4.5rem',
alignItems:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'center',
textAlign:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'center',
flexWrap:
cardFunction?.BigImage && 'wrap',
}}
>
<p
style={{
textTransform:
cardFunction?.TextCapitalize &&
'uppercase',
width: !cardFunction?.SmallImage
? cardFunction?.BigImage &&
'120px'
: cardFunction?.SmallImage &&
!cardFunction?.ImageUp &&
!cardFunction?.ImageDown &&
'85px',
// Width: cardFunction?.BigImage && "70px",
fontSize:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'12px', //naresh27
whiteSpace:
!cardFunction?.BigImage &&
'pre-wrap',
margin: 'auto',
fontFamily: SelectedCardFont
? SelectedCardFont
: '',
color: SelectedCardColor
? SelectedCardColor?.['FontColor']
: '',
textOverflow: 'ellipsis',
}}
className="BSItemCard-itemName"
>
{item?.ProdName}{' '}
</p>
{cardFunction?.Price &&
((item?.OverAllQty !== undefined &&
item?.OverAllQty !== 0 &&
item?.OverAllQty !== null) ||
item?.ProductDetail?.some(
(item) =>
item?.StockAvailable !== 'Y'
)) && (
<p
className="BSItemCard-itemPrice"
style={{
fontSize:
!cardFunction?.SmallImage
? cardFunction?.BigImage &&
'12px'
: '12px',
textAlign: 'center',
lineHeight: '2',
fontFamily: SelectedCardFont
? SelectedCardFont
: '',
color: SelectedCardColor
? SelectedCardColor?.[
'FontColor'
]
: '',
}}
>
{ItemSellingPrice(item)}&nbsp;
{/* {item?.ProductDetail?.[0]?.ProdVariantDetails?.[0]?.StockDetails?.[0]?.SellPrice}&nbsp; */}
{/* {ItemSellingPrice(item)} */}
<span className="BSItemCard-itemCount">
({ItemSize(item)}
{ItemUomName(item)})
</span>
</p>
)}
</div>
{cardFunction?.StockCount &&
item?.OverAllQty !== undefined &&
item?.OverAllQty !== 0 && (
<div
style={{
top:
!cardFunction?.BigImage && '0',
right:
!cardFunction?.BigImage &&
!cardFunction?.SmallImage &&
'0px',
position: 'absolute',
}}
className={
cardFunction?.BigImage
? 'BSItemCard-badge'
: 'BSItemCard-badge-withoutimage'
}
>
{item?.ProductDetail?.some(
(item) =>
item?.StockAvailable === 'Y'
) &&
item?.OverAllQty !== null && (
<Badge
count={returnCount(
item?.ProductDetail?.[0]
?.ProdName,
item?.OverAllQty,
CartOrderDetails
)}
overflowCount={10000}
></Badge>
)}
</div>
)}
</div>
</>
)}
</div>
) : (
<div
className={
item?.ProductDetail?.[0]?.ProdVariantDetails
?.length > 0
? 'card4Main card4Main-active'
: 'card4Main card4Main-deactive'
}
onClick={(e) => {
CardOnclick(item, index); // This will trigger if you're clicking outside the "One Piece" button
}}
>
{/* Global Data Checkbox */}
{globaldata && (
<input
type="checkbox"
value={item.ProductDetail?.[0]?.ProdId}
name={item.ProdName}
onClick={(e) => e.stopPropagation()}
onChange={(e) => pickData(e, item)}
style={{
position: 'absolute',
zIndex: 1,
transform: 'scale(1.5)',
cursor: 'pointer',
}}
checked={(
globalAllItemdata || EditfavItems
)?.some(
(a) =>
a?.ProdName === item?.ProdName &&
a?.ProdCat === item?.ProdCat
)}
/>
)}
{/* Tooltip for Product Name */}
<Tooltip title={item.ProdName}>
<div className="card4Img">
<img
width={50}
height={60}
src={
item?.ProductDetail?.[0]?.ProdLogo ===
''
? defaultimage
: item?.ProductDetail?.[0]?.ProdLogo
? item?.ProductDetail?.[0]?.ProdLogo
: defaultimage
}
alt=""
/>
</div>
</Tooltip>
<div className="Card4datas">
<div className="card4ProductName">
{item?.ProdName}
</div>
{item?.ProductDetail?.[0]?.ProdVariantDetails
?.length > 0 && (
<div className="card4PriceUom">
<div className="card4Price">
{ItemSellingPrice(item)}
</div>
<div className="card4Uom">
{ItemSize(item)} {ItemUomName(item)}
</div>
</div>
)}
</div>
{/* Stock Count Badge */}
{cardFunction?.StockCount &&
item?.OverAllQty !== undefined &&
item?.OverAllQty !== 0 && (
<div
style={{
top: '0',
right: '0px',
position: 'absolute',
}}
className="card4Main-badge"
>
{item?.ProductDetail?.some(
(item) => item?.StockAvailable === 'Y'
) &&
item?.OverAllQty !== null && (
<Badge
count={returnCount(
item?.ProductDetail?.[0]
?.ProdName,
item?.OverAllQty,
CartOrderDetails
)}
overflowCount={10000}
></Badge>
)}
</div>
)}
</div>
)}
</SortableCard>
))}
</div>
</SortableContext>
</DndContext>
</>
) : ProductSearch?.length > 5 &&
GetmultipleSearchDatas.some(
(e) => e.toLowerCase() === 'qrcode'
) &&
(cardData?.length == 0 || cardData == undefined) ? (
<div>
{/* cardData mohan 18-04-2025 */}
<FeaturesFunctionalities
handleQuickAddCancel={handleQuickCancel}
QuickAdd={QuickAdd}
ProductSearch={true}
ProductSearchType={'I'}
cardData={cardDataForNewPrd}
/>
</div>
) : (
<>
<div
className={!temp5 ? 'NodataFound' : 'NodataFound5'}
style={{
display: globalAccessForOthers && 'none',
}}
>
Name
<div align="Namecenter" className="fond">
<div className="Namecontener_general">
<div className="Namecontener_mixte">
<div className="ballcolor ball_1">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_2">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_3">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_4">&nbsp;</div>
</div>
</div>
</div>
</div>
</>
)}
{paymentloadNameer === true && (
<div className="NamePayment-loader1">
<div className="NamePayment-loader">
<div className="Namecontener_mixte">
<div className="ballcolor ball_1">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_2">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_3">&nbsp;</div>
</div>
Name
<div className="Namecontener_mixte">
<div className="ballcolor ball_4">&nbsp;</div>
</div>
<p style={{ marginTop: '2rem' }}>
{' '}
Please wait while we process your payment
</p>
{PaymentTransactionNumber != null && (
<p style={{ fontSize: '16px', fontWeight: '600' }}>
Transaction Number : {PaymentTransactionNumber}
</p>
)}
</div>
</div>
)}
</div>
</div>
</div>
{expModel && (
<Modal
title={
<div
style={{ display: 'flex', gap: '1rem', flexDirection: 'row' }}
>
<div>
<ExclamationCircleOutlined
style={{ color: 'rgb(231 176 12)', fontSize: '30px' }}
/>
</div>
<div>
<h4>Product Expires</h4>
</div>
</div>
}
open={expModel}
onOk={() => expFun(Item)}
onCancel={() => setexpModel(false)}
okText="Submit"
cancelText="Don't Submit"
maskTransitionName="" // Remove animation for the mask
transitionName=""
></Modal>
)}
{expQtyModel && (
<Modal
title={
<div
style={{ display: 'flex', gap: '1rem', flexDirection: 'row' }}
>
<ExclamationCircleOutlined
style={{ color: 'rgb(231 176 12)', fontSize: '30px' }}
/>
<h3>Quantity Expires</h3>
</div>
}
open={expQtyModel}
onOk={() => expQtyFun(qtyExpData)}
onCancel={() => {
(setRepeatedModel(false),
setProdexpir(false),
setExpQtyModel(false));
}}
okText="Submit"
cancelText="Don't Submit"
maskTransitionName=""
transitionName=""
></Modal>
)}
{expVarModel && (
<Modal
title={
<div
style={{ display: 'flex', gap: '1rem', flexDirection: 'row' }}
>
<ExclamationCircleOutlined
style={{ color: 'rgb(231 176 12)', fontSize: '30px' }}
/>
<h3>Variant Expires</h3>
</div>
}
open={expVarModel}
onOk={() => expVerFun(VarItem)}
onCancel={() => {
(setexpVarModel(false),
setRepeatedModel(false),
setProdexpir(false));
}}
okText="Submit"
cancelText="Don't Submit"
maskTransitionName=""
transitionName=""
></Modal>
)}
{expStockModel && (
<Modal
title={
<div
style={{ display: 'flex', gap: '1rem', flexDirection: 'row' }}
>
<ExclamationCircleOutlined
style={{ color: 'rgb(231 176 12)', fontSize: '30px' }}
/>
<h3>Stock Expires</h3>
</div>
}
open={expStockModel}
onOk={() => expStockFun(StockItem)}
onCancel={() => {
(setexpStockModel(false),
setRepeatedModel(false),
setProdexpir(false));
}}
okText="Submit"
cancelText="Don't Submit"
maskTransitionName=""
transitionName=""
></Modal>
)}
{modelQty && (
<DefaultModal
title={
<div className="EditQuantity-title">
<FormHeader title={'SubItem'} />
</div>
}
open={modelQty}
width={800}
handleCancel={CloseModal}
footer={null}
maskTransitionName=""
transitionName=""
children={
<div>
<div className="EditQuantity-heading">
<div className="EditQuantity-headingname">
<p className="EditQuantity-itemname">Item Name:</p>
</div>
<div
className="EditQuantity-headingproductname"
style={{ marginLeft: '1rem' }}
>
<p className="EditQuantity-productname">
{qtydata?.ProdName}
</p>
</div>
</div>
<div
style={{ height: 'auto' }}
className={
BrandCheckresult
? 'Card-modal-table'
: 'Brand-Card-modal-table'
}
>
{/* Horizontal scroll container */}
<div
style={{
position: 'relative',
display: 'flex',
alignItems: 'center',
}}
>
{/* Left Scroll Button */}
{showLeftButton && (
<div
className="CategoryHorizontal-icon"
onClick={() => handleScrollClickLeft(200)}
style={{
position: 'absolute',
left: 0,
top: '35%',
transform: 'translateY(-50%)',
zIndex: 10,
background: '#fff',
padding: '0.5rem',
cursor: 'pointer',
boxShadow: '0 0 5px rgba(0,0,0,0.2)',
}}
>
</div>
)}
{/* Scroll Container */}
<div
id="mainDiv"
className="CategoryHorizontal-scroll-container"
ref={scrollContainerRef}
onMouseDown={handleMouseDown}
onMouseMove={handleMouseMove}
onMouseUp={handleMouseUp}
onMouseLeave={handleMouseUp}
onTouchStart={handleTouchStart}
onTouchMove={handleTouchMove}
onTouchEnd={handleTouchEnd}
style={{
cursor: 'grab',
overflowX: 'auto',
display: 'flex',
gap: '1rem',
}}
>
{Object.keys(brandGroups)
.sort((a, b) =>
a === 'Others' ? -1 : b === 'Others' ? 1 : 0
)
.map((brand) => (
<div
key={brand}
onClick={() => setSelectedBrand(brand)}
style={{
minWidth: '150px',
background:
selectedBrand === brand ? '#cce5ff' : '#f4f4f4',
borderRadius: '8px',
padding: '0.8rem',
flexShrink: 0,
cursor: 'pointer',
userSelect: 'none',
textAlign: 'center',
fontWeight:
selectedBrand === brand ? 'bold' : 'normal',
}}
>
{brand === 'Others' ? 'Others' : brand}
</div>
))}
</div>
{/* Right Scroll Button */}
{showRightButton && (
<div
className="CategoryHorizontal-icon"
onClick={() => handleScrollClickRight(200)}
style={{
position: 'absolute',
right: 0,
top: '35%',
transform: 'translateY(-50%)',
zIndex: 10,
background: '#fff',
padding: '0.5rem',
cursor: 'pointer',
boxShadow: '0 0 5px rgba(0,0,0,0.2)',
}}
>
</div>
)}
</div>
{/* Selected brand products */}
<div style={{ marginTop: '1rem', overflow: 'auto' }}>
<h3 style={{ margin: '0 0 20px 0' }}>
{selectedBrand === 'Others' ? 'Others' : selectedBrand}{' '}
Products
</h3>
<ul
className="webkit-ul"
style={{
listStyle: 'none',
padding: 0,
display: 'flex',
flexWrap: 'wrap',
gap: '1rem',
}}
>
{(brandGroups[selectedBrand] || []).map(
(product, index) => {
const qtyCount = returnQtyCount(
product?.ProdId,
product,
CartOrderDetails
);
const isAvailable = product?.StockAvailable !== 'Y';
const isDisabled = qtyCount > 0 || isAvailable;
return (
<div key={`${product?.brandId}-${index}`}>
<div
style={{ position: 'relative' }}
className={
isDisabled
? 'ItemQtyCard'
: 'ItemQtyCard-disabled'
}
onClick={() => VarientFun(product)}
>
<div className="ItemQtyImgCard">
<img
src={product?.ProdLogo || defaultimage}
width={'80px'}
height={'70px'}
alt={`Product ${index}`}
/>
</div>
<div
className={
cardFunction?.BigImage
? 'BSItemCard-badge'
: 'BSItemCard-badge-withoutimage'
}
>
<Badge
count={qtyCount}
overflowCount={10000}
></Badge>
</div>
<div className="qtyDetail">
<p className="qtyUomName-itemCard">
{product?.Size + ' ' + product?.UomName}
</p>
{!isDisabled && (
<p
style={{
color: 'red',
fontSize: '12',
textAlign: 'center',
fontWeight: '600',
}}
>
No Stock
</p>
)}
{isDisabled && (
<p className="qtyprice">
<sup style={{ fontFamily: 'Gilroy' }}>
</sup>
&nbsp;
{safeRound(
product?.ProdVariantDetails?.[0]
?.StockDetails?.[0]?.SellPrice
)}
</p>
)}
</div>
</div>
</div>
);
}
)}
</ul>
</div>
{Object.keys(brandMapping).length === 0 && (
<p>No product details available</p>
)}
</div>
</div>
}
/>
)}
{/* {modelstock && (
<DefaultModal
title={
<div className="EditQuantity-title">
<FormHeader title={'Item Stock'} />
</div>
}
open={modelstock}
// width={500}
footer={null}
top={0}
handleCancel={CloseModal1}
maskTransitionName=""
transitionName=""
children={
<div>
<div
className="EditQuantity-heading"
style={{
display: 'flex',
flexDirection: 'column',
marginBottom: '3rem',
alignItems: 'start',
}}
>
<div style={{ display: 'flex' }}>
<div className="EditQuantity-headingname">
<p className="EditQuantity-itemname">Item Name:</p>
</div>
<div
className="EditQuantity-headingproductname"
style={{ marginLeft: '1rem' }}
>
<p className="EditQuantity-productname">
{qtydata?.ProdName}{' '}
{!qtydata?.ProductDetail?.[
QtyIndex
]?.ProdVariantDetails?.[
VarientIndex
]?.ProdVariantName?.toLowerCase()?.includes('variant')
&& (
<span>
(
{
qtydata?.ProductDetail?.[QtyIndex]
?.ProdVariantDetails?.[VarientIndex]
?.ProdVariantName
}
){' '}
</span>
)}
</p>
</div>
</div>
<div style={{ display: 'flex' }}>
<div className="EditQuantity-headingname">
<p className="EditQuantity-itemname">Item Unit:</p>
</div>
<div
className="EditQuantity-headingproductname"
style={{ marginLeft: '1rem' }}
>
<p className="EditQuantity-productname">
{qtydata?.ProductDetail?.[QtyIndex]?.Size}{' '}
{onePeiceFlow
? 'PCS'
: qtydata?.ProductDetail?.[QtyIndex]?.UomName}
</p>
</div>
</div>
</div>
<div className="Re-Print-table">
<Tables columns={stockcolumns} data={stockdataSource} />
</div>
</div>
}
/>
)} */}
{ModalVarient && (
<DefaultModal
// title={
// <div className="EditQuantity-title">
// <FormHeader title={AvailableDate ? "Slots" : 'Item Variant'} />
// </div>
// }
width={'97vw'}
open={ModalVarient}
key={refreshKey}
// width={"90vw"}
className={'bookingModalBulk'}
top={0}
footer={null}
handleCancel={CloseVarientModal}
maskTransitionName=""
transitionName=""
children={
// isBulk ? (
<>
<div className="bulk-slot-table">
{/* Slot header */}
<div className="SportsSlotHeader">
<div className="SportsSlotHeader1">
<BranchName IconStatus={true} />
</div>
<div className="SportsSlotHeader2">
{currentActiveOffer && (
<div className="membershipSummaryOneLine">
{currentActiveOffer?.MemberName || '-'} |
{formatDate(currentActiveOffer?.PlanStartDate)} -{' '}
{formatDate(currentActiveOffer?.PlanEndDate)} | Hrs:{' '}
{currentActiveOffer?.RemainingSessionHrs || 0} | Off:{' '}
{currentActiveOffer?.Discount
? `${currentActiveOffer.Discount}${currentActiveOffer.DiscountType === 'P' ? '%' : ''}`
: '0%'}
</div>
)}{' '}
{/* <MembershipCard MembershipDetail={selOption?.MembershipDetail} selectedCustomer={selOption} showCard={selOption?.MembershipDetail?.length>0} /> */}
<BSCustomerSelect TopName={'navbar-top'} />
<BSNavBarAddUser />
</div>
</div>
{/* datepicker for slot */}
<div className="sportsubHeader">
<div className="sports-slot-toggle">
<button
className={`sports-toggle-btn ${activeMode === 'slot' ? 'active' : ''}`}
onClick={() => {
setActiveMode('slot');
}}
>
Slot
</button>
<button
className={`sports-toggle-btn ${activeMode === 'individual' ? 'active' : ''}`}
onClick={() => {
setActiveMode('individual');
}}
>
Individual
</button>
</div>
<DatePicker.RangePicker
format="DD/MMM/YYYY"
value={getDatePickerValue(selectedDate)}
disabledDate={(current) =>
current && current < dayjs().startOf('day')
}
onChange={(dates) => {
if (!dates) {
// User hit clear, so set today's date range
const today = dayjs();
setSelectedDate([today, today]); // or today → tomorrow, if you prefer
return;
}
setSelectedDate(dates);
}}
/>
<button
className={`corner-selection-btn ${selectionMode ? 'active' : ''}`}
onClick={() => setSelectionMode(!selectionMode)}
>
{selectionMode ? (
<>
Close
<IoClose size={20} />
</>
) : (
<>
Block
<MdBlock size={20} />
</>
)}
</button>
</div>
{/* Slot Split Section */}
<div className="slotSectionMain">
<div
className={`SlotSlideBTN ${currentSlotIndex === 0 ? 'disabled' : ''}`}
onClick={handleSlotPrev}
>
<FaAngleLeft />
</div>
<div className="SlideSlotMain">
{draggableCardData
?.slice(
currentSlotIndex,
currentSlotIndex + visibleSlots
)
.map((product, productIndex) => {
// Get all variants for this specific product from modalVarientData
const noIndividualSlots =
product?.ProductDetail?.[0]?.ProdVariantDetails?.every(
(variant) => variant?.OnePcsPrice === 0
);
return (
<div
key={
product?.id || currentSlotIndex + productIndex
}
className={`slotproductName ${activeMode === 'individual' && noIndividualSlots ? 'hide' : ''}`}
>
{/* <p className="slotGroundName">
{product?.ProdName}
</p> */}
<div
key={currentSlotIndex + productIndex}
className="bookingSportSlot"
>
<p className="slotGroundName">
{' '}
{product?.ProdName}
</p>
<div className="slotTimingSelectMain">
{product?.ProductDetail?.[0]
?.ProdVariantDetails?.length > 0 ? (
Object?.entries(
product?.ProductDetail?.[0]?.ProdVariantDetails?.reduce(
(acc, timeSlot) => {
// Extract date (for example, from AvailableFrom or TempDate)
const dateKey = dayjs(
timeSlot?.TempDate
)?.format('YYYY-MM-DD');
if (!acc[dateKey]) acc[dateKey] = [];
acc[dateKey].push(timeSlot);
return acc;
},
{}
) || {}
)?.map(([date, slots]) => (
<div
key={date}
className="date-slot-group"
>
{/* Common date header */}
<div className="slot-date-header">
{dayjs(date).format('DD MMM YYYY')}
</div>
<div className="slotTimingSelectMain">
{slots.map((timeSlot, idx) => {
const isBooked =
timeSlot?.SlotStatus?.toLowerCase() ==
'booked' || false;
const isBlocked =
timeSlot?.SlotStatus?.toLowerCase() ==
'blocked' || false;
const isPartiallyBooked =
timeSlot?.SlotStatus?.toLowerCase() ===
'partially booked' || false;
const isPartiallyBlocked =
timeSlot?.SlotStatus?.toLowerCase() ===
'partially blocked' || false;
const isSelected =
CartOrderDetails?.some(
(selected) =>
selected.ProdId ===
timeSlot?.ProdId &&
selected.InwardDtlId ===
timeSlot?.InwardDtlId &&
selected.VariantAvailableFrom ===
timeSlot?.VariantAvailableFrom &&
selected.VariantAvailableTo ===
timeSlot?.VariantAvailableTo &&
selected.BookedDate ===
timeSlot?.BookedDate
);
const isAlreadyAdded =
CartOrderDetails?.some((item) => {
const itemDate =
item?.BookedDate
? new Date(
item?.BookedDate
).toLocaleDateString()
: null;
return (
item?.InwardDtlId ===
timeSlot?.InwardDtlId &&
item?.VariantAvailableFrom ===
timeSlot?.VariantAvailableFrom &&
item?.VariantAvailableTo ===
timeSlot?.VariantAvailableTo &&
item?.ProdVariantName?.toLowerCase() ===
timeSlot?.VarientName?.toLowerCase() &&
itemDate === dataDate &&
(item?.SinglePc === 'Y'
? returnVariantStock(
data,
CartOrderDetails
) === 0
: true)
);
});
const slotDateTime = new Date(
`${timeSlot?.BookedDate?.split('T')[0]}T${timeSlot?.AvailableFrom}`
);
const now = new Date();
const isPast = slotDateTime >= now;
const BlockSelectedSlots =
selectedSlots?.some(
(selected) =>
selected.InwardDtlId ===
timeSlot?.InwardDtlId &&
selected.VariantAvailableFrom ===
timeSlot?.VariantAvailableFrom &&
selected.VariantAvailableTo ===
timeSlot?.VariantAvailableTo &&
selected.TempDate ===
timeSlot?.BookedDate
);
const isDisabled =
isBooked ||
(isBlocked && !isSelected);
const slotEnded =
new Date(
`${timeSlot?.BookedDate?.split('T')[0]}T${timeSlot?.AvailableTo}`
) <= new Date();
return (
<div
key={idx}
className={`slotTimingSelect ${
isBooked
? 'booked'
: isAlreadyAdded
? 'incart'
: isPartiallyBooked
? 'partial'
: isBlocked &
!isSelected ||
slotEnded
? 'blocked'
: isBlocked ||
isSelected ||
isPartiallyBlocked ||
isSelected
? 'selected'
: BlockSelectedSlots
? 'blocked'
: 'available'
} ${timeSlot?.OnePcsPrice <= 0 && activeMode === 'individual' ? 'hide' : ''}`}
// ${isSelected ? 'selected' : ''}
disabled={isDisabled}
onClick={(e) => {
if (
!isBooked &&
!isDisabled &&
!onePeiceFlow
) {
!(
onePeiceFlow ||
isPartiallyBooked ||
isPartiallyBlocked
) &&
!selectionMode &&
handleSlotButtonClick(
timeSlot,
product,
onePeiceFlow ||
isPartiallyBooked,
!slotEnded
);
}
}}
>
<div className="slot-header">
{to12Hour(
timeSlot?.AvailableFrom
)}{' '}
-{' '}
{to12Hour(
timeSlot?.AvailableTo
)}
</div>
<div className="slot-price">
{onePeiceFlow ||
isPartiallyBooked
? timeSlot?.OnePcsPrice
: timeSlot?.SellPrice || 0}
</div>
<div className="slotBTNquantity">
{(onePeiceFlow ||
isPartiallyBooked ||
isPartiallyBlocked) &&
!isBooked &&
!isBlocked &&
!slotEnded && (
<>
<button
className="slotBTNquantity-decrease"
onClick={(e) => {
handleRemoveSingle(
timeSlot,
product,
true
);
}}
// disabled={returnVariantStock(timeSlot, CartOrderDetails) === (parseInt(timeSlot?.TotalSlotQty) - timeSlot?.BookedQty)}
disabled={
!CartOrderDetails?.some(
(selected) =>
selected.ProdId ===
timeSlot.ProdId &&
selected.InwardDtlId ===
timeSlot.InwardDtlId &&
selected.VariantAvailableFrom ===
timeSlot.VariantAvailableFrom &&
selected.VariantAvailableTo ===
timeSlot.VariantAvailableTo &&
selected.BookedDate ===
timeSlot.BookedDate
)
}
icon={
<PlusOutlined />
}
>
{' '}
<LuMinus />{' '}
</button>
{returnVariantStock(
timeSlot,
CartOrderDetails
)}
Avl
<button
className="slotBTNquantity-increase"
onClick={() => {
handleSingleSlotIncrease(
timeSlot,
product,
true
);
}}
icon={
<PlusOutlined />
}
disabled={
returnVariantStock(
timeSlot,
CartOrderDetails
) <= 0
}
>
{' '}
<FiPlus
size={17}
/>{' '}
</button>
</>
)}
</div>
{selectionMode &&
!isBlocked &&
!isBooked &&
!slotEnded && (
<input
type="checkbox"
checked={
BlockSelectedSlots ||
false
}
onChange={(e) =>
handleSlotSelection(
e,
timeSlot
)
}
/>
)}
{(timeSlot?.SlotStatus ===
'Partially Booked' ||
timeSlot?.SlotStatus ===
'Booked') && (
<div
onClick={(e) => {
e.stopPropagation();
handleBookedDetails({
...timeSlot,
ProdName:
product
?.ProductDetail?.[0]
?.ProdName,
ProdSubCatName:
product?.ProdSubCatName,
});
}}
>
<span className="slot-booked">
{timeSlot?.SlotStatus}
</span>
</div>
)}
</div>
);
})}
</div>
</div>
))
) : (
<div
style={{
color: 'red',
textAlign: 'center',
marginTop: '10px',
fontWeight: 600,
}}
>
No Slots Available
</div>
)}
</div>
</div>
</div>
);
})}
</div>
<div
className={`SlotSlideBTN ${currentSlotIndex >= maxIndex ? 'disabled' : ''}`}
onClick={handleSlotNext}
>
<FaAngleRight />
</div>
</div>
{/* Select All and Submit buttons for bulk mode */}
<div className="bulk-actions">
<div className="bulk-submit-btn">
{selectionMode && selectedSlots?.length > 0 && (
<div className="selection-submit-container">
<button
className="selection-submit-btn"
onClick={handleSubmitBlockSlots}
>
<span className="submit-count">
{selectedSlots.length}&nbsp;
</span>
Submit Selected
</button>
</div>
)}
{CartOrderDetails.length > 0 && !selectionMode && (
<button onClick={handleSubmitSelectedSlots}>
Add {CartOrderDetails.length} Selected Slots to Cart
</button>
)}
</div>
</div>
{/* Status Legend */}
<div className="Slot-status">
<div className="Slot-status-div">
<span className="available"> </span> Available
</div>
<div className="Slot-status-div">
<span className="booked"> </span> Booked
</div>
<div className="Slot-status-div">
<span className="IsinCart"> </span> Blocked
</div>
<div className="Slot-status-div">
<span className="Single"> </span> Partial Available
</div>
<div className="Slot-status-div">
<span className="selected-indicator"> </span> Selected
</div>
</div>
</div>
<DefaultModal
width={700}
open={bookedDetails}
className={'booked-slot-details-modal'}
footer={null}
handleCancel={() => {
setSelectedSlotDetails(null);
setBookedDetails(false);
}}
children={
<>
<div className="booked-details-container">
<h3 className="booked-details-title">
Booking Details
</h3>
<div className="booked-slot-info">
<div className="info-row">
<span className="info-label">Slot:</span>
<span className="info-value">
{`${selectedSlotDetails?.ProdSubCatName ? selectedSlotDetails?.ProdSubCatName + ' - ' : ''}` +
'(' +
selectedSlotDetails?.ProdName +
')'}
</span>
</div>
<div className="info-row">
<span className="info-label">Time:</span>
<span className="info-value">
{to12Hour(selectedSlotDetails?.AvailableFrom)} -{' '}
{to12Hour(selectedSlotDetails?.AvailableTo)}
</span>
</div>
<div className="info-row">
<span className="info-label">Date:</span>
<span className="info-value">
{dayjs(selectedSlotDetails?.BookedDate)?.format(
'DD MMM YYYY'
)}
</span>
</div>
<div className="info-row">
<span className="info-label">Total Slots:</span>
<span className="info-value">
{selectedSlotDetails?.TotalSlotQty}
</span>
</div>
<div className="info-row">
<span className="info-label">Booked:</span>
<span className="info-value">
{selectedSlotDetails?.BookedQty}
</span>
</div>
<div className="info-row">
<span className="info-label">Status:</span>
<span className="info-value status-badge">
{selectedSlotDetails?.SlotStatus}
</span>
</div>
</div>
<h4 className="customer-details-title">
Customer Details
</h4>
<div className="customer-table-wrapper">
<table className="customer-details-table">
<thead>
<tr>
<th>Customer Name</th>
<th>Mobile</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
{selectedSlotDetails?.CustomerDetails?.map(
(customer, index) => {
const slotDateTime = new Date(
`${selectedSlotDetails?.BookedDate.split('T')[0]}T${selectedSlotDetails?.AvailableFrom}`
);
const slotDateTimeTo = new Date(
`${selectedSlotDetails?.BookedDate.split('T')[0]}T${selectedSlotDetails?.AvailableTo}`
);
const now = new Date();
const isPast = slotDateTime >= now;
const isFuture = slotDateTimeTo <= now;
return (
<tr key={index}>
<td>{customer.CustName || 'N/A'}</td>
<td>{customer.CustMobile || 'N/A'}</td>
<td className="action-buttons">
{customer?.CustBookDetails?.length >
1 ? (
<button
className="show-all-btn"
onClick={() =>
handleShowAllBookings(customer)
}
>
Show All (
{customer.CustBookDetails.length})
</button>
) : customer?.CustBookDetails
?.length === 1 ? (
<>
<button
className="start-btn"
disabled={
customer.CustBookDetails[0]
.StartTime || isPast
}
onClick={() =>
handleSlotTimeUpdate(
customer.CustBookDetails[0],
customer?.BookingDate,
'start'
)
}
>
Start
</button>
<button
className="end-btn"
disabled={
!customer.CustBookDetails[0]
.StartTime ||
customer.CustBookDetails[0]
.EndTime ||
isPast
}
onClick={() =>
handleSlotTimeUpdate(
customer.CustBookDetails[0],
customer?.BookingDate,
'end'
)
}
>
End
</button>
</>
) : (
<span>No Bookings</span>
)}
</td>
</tr>
);
}
)}
</tbody>
</table>
</div>
</div>
<DefaultModal
width={800}
open={showAllBookingsModal}
className={'all-bookings-modal'}
footer={null}
handleCancel={() => {
setShowAllBookingsModal(false);
setSelectedCustomerBookings(null);
}}
children={
<div className="all-bookings-container">
<h3 className="all-bookings-title">
{selectedCustomerBookings?.CustName ||
selectedCustomerBookings?.CustMobile}
's Bookings
</h3>
{selectedCustomerBookings?.CustMobile && (
<p className="customer-mobile">
Mobile: {selectedCustomerBookings?.CustMobile}
</p>
)}
<div className="bookings-table-wrapper">
<table className="bookings-details-table">
<thead>
<tr>
<th>Booked By</th>
<th>Booked Date</th>
<th>Start Time</th>
<th>End Time</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
{selectedCustomerBookings?.CustBookDetails?.map(
(booking, index) => (
<tr key={index}>
<td>{booking.BookedBy || 'N/A'}</td>
<td>
{booking.CreatedDate
? dayjs(booking.CreatedDate).format(
'DD MMM YYYY hh:mm A'
)
: 'N/A'}
</td>
<td>
{booking.StartTime
? dayjs(booking.StartTime).format(
'hh:mm A'
)
: '-'}
</td>
<td>
{booking.EndTime
? dayjs(booking.EndTime).format(
'hh:mm A'
)
: '-'}
</td>
<td className="action-buttons">
<button
className="start-btn"
disabled={booking.StartTime}
onClick={() =>
handleSlotTimeUpdate(
booking,
selectedCustomerBookings?.BookingDate,
'start'
)
}
>
Start
</button>
<button
className="end-btn"
disabled={
!booking.StartTime ||
booking.EndTime
}
onClick={() =>
handleSlotTimeUpdate(
booking,
selectedCustomerBookings?.BookingDate,
'end'
)
}
>
End
</button>
</td>
</tr>
)
)}
</tbody>
</table>
</div>
</div>
}
/>
</>
}
/>
</>
}
/>
)}
</>
);
for (let i = 0; i < code?.length; i++) {
encrypted += String.fromCharCode(
code.charCodeAt(i) ^ key.charCodeAt(i % key.length)
);
}
return encrypted;
}
function decrypt(encrypted, key) {
// Implement decryption logic
let decrypted = encrypt();
for (let i = 0; i < encrypted?.length; i++) {
decrypted += String.fromCharCode(
encrypted.charCodeAt(i) ^ key.charCodeAt(i % key.length)
);
}
return decrypted;
}
const encryptedCode = encrypt(); // Encrypted React component code
const decryptionKey = decrypt(); // Decryption key (keep it secure)
const decryptedCode = decrypt(encryptedCode, decryptionKey);
return <>{encrypt()}</>;
};
export default React.memo(BsBookingitemCard);