import React, { useState } from 'react'; import {Stepper, Step, StepLabel, Typography, Menu, MenuItem, IconButton, Box} from '@mui/material'; import AirplanemodeActiveIcon from '@mui/icons-material/AirplanemodeActive'; import StoreIcon from '@mui/icons-material/Store'; import RecycleIcon from '@mui/icons-material/Restore'; import AirplaneIcon from '@mui/icons-material/AirplanemodeActive'; import { Dewar, DewarsService } from "../../openapi"; import { DewarStatus, getStatusStepIndex, determineIconColor } from './statusUtils'; import Tooltip from "@mui/material/Tooltip"; import './DewarStepper.css'; const ICON_STYLE = { width: 24, height: 24 }; // Custom SVG Icon Component const BottleIcon: React.FC<{ fill: string }> = ({ fill }) => ( ); // Icons Mapping const ICONS: { [key: number]: (props?: React.ComponentProps) => React.ReactElement; } = { 0: (props) => , 1: (props) => ( ), 2: (props) => , 3: (props) => , 4: (props) => ( ), 5: (props) => ( ), }; // StepIconContainer Component interface StepIconContainerProps { completed?: boolean; active?: boolean; error?: boolean; children?: React.ReactNode; } const StepIconContainer: React.FC = ({ completed, active, error, children, }) => { const className = [ completed ? 'completed' : '', active ? 'active' : '', error ? 'error' : '', ] .filter(Boolean) .join(' '); return (
{children}
); }; const StepIconComponent: React.FC = ({ icon, dewar, isSelected, refreshShipments, ...rest }) => { const [anchorEl, setAnchorEl] = useState(null); const handleMenuOpen = (event: React.MouseEvent) => { // Trigger menu ONLY for the BottleIcon (icon === 0) if (icon === 0) { setAnchorEl(event.currentTarget); } }; const handleMenuClose = () => { setAnchorEl(null); }; const handleStatusChange = async (status: DewarStatus) => { try { const today = new Date().toISOString().split('T')[0]; const payload = { dewar_id: dewar.id, dewar_name: dewar.dewar_name, tracking_number: dewar.tracking_number, number_of_pucks: dewar.number_of_pucks, number_of_samples: dewar.number_of_samples, status: status, ready_date: status === 'Ready for Shipping' ? today : null, shipping_date: dewar.shipping_date, arrival_date: dewar.arrival_date, returning_date: dewar.returning_date, qrcode: dewar.qrcode, return_address_id: dewar.return_address_id, contact_id: dewar.contact_id, }; await DewarsService.updateDewarDewarsDewarIdPut(dewar.id, payload); setAnchorEl(null); refreshShipments(); } catch (error) { console.error('Failed to update dewar status:', error); alert('Failed to update dewar status. Please try again.'); } }; const { iconIndex, color } = getIconProperties(icon, dewar); return (
{ICONS[iconIndex]?.({ style: iconIndex === 0 ? { fill: color } : undefined, }) ?? Invalid icon} {icon === 0 && ( setAnchorEl(anchorEl), // Keep menu open on hover onMouseLeave: handleMenuClose, // Close menu when leaving }} > {['In Preparation', 'Ready for Shipping'].map((status) => ( handleStatusChange(status as DewarStatus)}> {status} ))} )}
); }; // Icon properties retrieval based on the status and icon number const getIconProperties = (icon: number, dewar: Dewar) => { const status = dewar.status as DewarStatus; const iconIndex = status === 'Delayed' && icon === 1 ? 5 : icon; const color = determineIconColor(icon, status); return { iconIndex, color }; }; // Steps of the stepper const steps = ['In-House', 'Transit', 'At SLS', 'Returned']; // Props for the CustomStepper type CustomStepperProps = { dewar: Dewar; selectedDewarId: number | null; refreshShipments: () => void; }; // CustomStepper Component const CustomStepper: React.FC = ({ dewar, selectedDewarId, refreshShipments }) => { const activeStep = getStatusStepIndex(dewar.status as DewarStatus); const isSelected = dewar.id === selectedDewarId; return (
{steps.map((label, index) => ( ( )} > {/* Step label */} {label} {/* Optional: Date below the step */} {index === 0 ? dewar.ready_date : index === 1 ? dewar.shipping_date : index === 2 ? dewar.arrival_date : index === 3 ? dewar.returning_date : ''} ))}
); }; export default CustomStepper;