- Updated signUpApi, deleteZonesApi, getZonesApi, setZonesApi, and other API functions to enhance error logging with echo.error statements. - Reformatted function parameters for better readability. - Removed unnecessary comments and console logs. - Ensured consistent error messages across all API functions. - Improved code structure for better maintainability.
148 lines
6.2 KiB
TypeScript
148 lines
6.2 KiB
TypeScript
import React, { useCallback, useEffect, useRef, useState } from 'react';
|
|
import VehicleAnimator from '../animator/vehicleAnimator';
|
|
import * as THREE from 'three';
|
|
import { NavMeshQuery } from '@recast-navigation/core';
|
|
import { useNavMesh } from '../../../../../store/store';
|
|
import { usePlayButtonStore } from '../../../../../store/usePlayButtonStore';
|
|
import { useVehicleStore } from '../../../../../store/simulation/useVehicleStore';
|
|
import MaterialAnimator from '../animator/materialAnimator';
|
|
|
|
function VehicleInstance({ agvDetail }: { agvDetail: VehicleStatus }) {
|
|
const { navMesh } = useNavMesh();
|
|
const vehicleRef: any = useRef();
|
|
const { isPlaying } = usePlayButtonStore();
|
|
const { vehicles, setVehicleActive, setVehicleState, incrementVehicleLoad, setMaterialType } = useVehicleStore();
|
|
const [currentPhase, setCurrentPhase] = useState<string>('stationed');
|
|
const [path, setPath] = useState<[number, number, number][]>([]);
|
|
let isIncrememtable = useRef<boolean>(true);
|
|
|
|
const computePath = useCallback(
|
|
(start: any, end: any) => {
|
|
try {
|
|
const navMeshQuery = new NavMeshQuery(navMesh);
|
|
const { path: segmentPath } = navMeshQuery.computePath(start, end);
|
|
return (
|
|
segmentPath?.map(({ x, y, z }) => [x, 0, z] as [number, number, number]) || []
|
|
);
|
|
} catch {
|
|
echo.error("Failed to compute path");
|
|
return [];
|
|
}
|
|
},
|
|
[navMesh]
|
|
);
|
|
|
|
function vehicleStatus(modelId: string, status: string) {
|
|
// console.log(`${modelId} , ${status}`);
|
|
|
|
}
|
|
|
|
// Function to reset everything
|
|
function reset() {
|
|
setCurrentPhase('stationed');
|
|
setVehicleActive(agvDetail.modelUuid, false);
|
|
setVehicleState(agvDetail.modelUuid, 'idle');
|
|
setPath([]);
|
|
}
|
|
|
|
const increment = () => {
|
|
if (isIncrememtable.current) {
|
|
incrementVehicleLoad(agvDetail.modelUuid, 10);
|
|
setMaterialType(agvDetail.modelUuid, 'Material 1')
|
|
isIncrememtable.current = false;
|
|
}
|
|
}
|
|
|
|
useEffect(() => {
|
|
if (isPlaying) {
|
|
|
|
if (!agvDetail.isActive && agvDetail.state === 'idle' && currentPhase === 'stationed') {
|
|
const toPickupPath = computePath(
|
|
new THREE.Vector3(agvDetail?.position[0], agvDetail?.position[1], agvDetail?.position[2]),
|
|
agvDetail?.point?.action?.pickUpPoint?.position
|
|
);
|
|
setPath(toPickupPath);
|
|
setCurrentPhase('stationed-pickup');
|
|
setVehicleState(agvDetail.modelUuid, 'running');
|
|
setVehicleActive(agvDetail.modelUuid, true);
|
|
vehicleStatus(agvDetail.modelUuid, 'Started from station, heading to pickup');
|
|
return;
|
|
} else if (!agvDetail.isActive && agvDetail.state === 'idle' && currentPhase === 'picking') {
|
|
|
|
setTimeout(() => {
|
|
increment();
|
|
}, 5000);
|
|
|
|
|
|
if (agvDetail.currentLoad === agvDetail.point.action.loadCapacity && agvDetail.materialType) {
|
|
if (agvDetail.point.action.pickUpPoint && agvDetail.point.action.unLoadPoint) {
|
|
const toDrop = computePath(
|
|
agvDetail.point.action.pickUpPoint.position,
|
|
agvDetail.point.action.unLoadPoint.position
|
|
);
|
|
setPath(toDrop);
|
|
setCurrentPhase('pickup-drop');
|
|
setVehicleState(agvDetail.modelUuid, 'running');
|
|
setVehicleActive(agvDetail.modelUuid, true);
|
|
vehicleStatus(agvDetail.modelUuid, 'Started from pickup point, heading to drop point');
|
|
}
|
|
}
|
|
} else if (!agvDetail.isActive && agvDetail.state === 'idle' && currentPhase === 'dropping' && agvDetail.currentLoad === 0) {
|
|
if (agvDetail.point.action.pickUpPoint && agvDetail.point.action.unLoadPoint) {
|
|
const dropToPickup = computePath(
|
|
agvDetail.point.action.unLoadPoint.position,
|
|
agvDetail.point.action.pickUpPoint.position
|
|
);
|
|
setPath(dropToPickup);
|
|
setCurrentPhase('drop-pickup');
|
|
setVehicleState(agvDetail.modelUuid, 'running');
|
|
setVehicleActive(agvDetail.modelUuid, true);
|
|
vehicleStatus(agvDetail.modelUuid, 'Started from dropping point, heading to pickup point');
|
|
|
|
isIncrememtable.current = true;
|
|
}
|
|
}
|
|
} else {
|
|
reset()
|
|
}
|
|
}, [vehicles, currentPhase, path, isPlaying]);
|
|
|
|
function handleCallBack() {
|
|
if (currentPhase === 'stationed-pickup') {
|
|
setCurrentPhase('picking');
|
|
setVehicleState(agvDetail.modelUuid, 'idle');
|
|
setVehicleActive(agvDetail.modelUuid, false);
|
|
vehicleStatus(agvDetail.modelUuid, 'Reached pickup point, waiting for material');
|
|
setPath([]);
|
|
} else if (currentPhase === 'pickup-drop') {
|
|
setCurrentPhase('dropping');
|
|
setVehicleState(agvDetail.modelUuid, 'idle');
|
|
setVehicleActive(agvDetail.modelUuid, false);
|
|
vehicleStatus(agvDetail.modelUuid, 'Reached drop point');
|
|
setPath([]);
|
|
} else if (currentPhase === 'drop-pickup') {
|
|
setCurrentPhase('picking');
|
|
setVehicleState(agvDetail.modelUuid, 'idle');
|
|
setVehicleActive(agvDetail.modelUuid, false);
|
|
setPath([]);
|
|
setMaterialType(agvDetail.modelUuid, null)
|
|
vehicleStatus(agvDetail.modelUuid, 'Reached pickup point again, cycle complete');
|
|
}
|
|
}
|
|
|
|
return (
|
|
<>
|
|
<VehicleAnimator
|
|
path={path}
|
|
handleCallBack={handleCallBack}
|
|
currentPhase={currentPhase}
|
|
agvUuid={agvDetail?.modelUuid}
|
|
agvDetail={agvDetail}
|
|
reset={reset}
|
|
/>
|
|
<MaterialAnimator agvDetail={agvDetail} />
|
|
</>
|
|
);
|
|
}
|
|
|
|
export default VehicleInstance; |