From e0736b26b90560034b9d327060399ba6516e6f91 Mon Sep 17 00:00:00 2001 From: Gomathi9520 Date: Tue, 10 Jun 2025 11:54:57 +0530 Subject: [PATCH 01/17] enhance loading state management and streamline throughput data handling --- app/src/components/ui/analysis/ROISummary.tsx | 5 +- .../ui/analysis/ThroughputSummary.tsx | 15 +-- .../analysis/throughPut/throughPutData.tsx | 97 ++++++++++++++----- 3 files changed, 82 insertions(+), 35 deletions(-) diff --git a/app/src/components/ui/analysis/ROISummary.tsx b/app/src/components/ui/analysis/ROISummary.tsx index a03b15c..0de3c4a 100644 --- a/app/src/components/ui/analysis/ROISummary.tsx +++ b/app/src/components/ui/analysis/ROISummary.tsx @@ -86,8 +86,9 @@ const ROISummary = ({ useEffect(() => { if (roiSummary.productName) { - // If productName is set, assume data is loaded - setIsLoading(false); + setTimeout(() => { + setIsLoading(false); + }, 4000) } else { // If productName is empty, assume still loading setIsLoading(true); diff --git a/app/src/components/ui/analysis/ThroughputSummary.tsx b/app/src/components/ui/analysis/ThroughputSummary.tsx index a01ac61..6660e90 100644 --- a/app/src/components/ui/analysis/ThroughputSummary.tsx +++ b/app/src/components/ui/analysis/ThroughputSummary.tsx @@ -11,9 +11,6 @@ const ProductionCapacity = ({ throughputValue = 128, timeRange = { startTime: "08:00 AM", endTime: "09:00 AM" }, }) => { - - - const { machineActiveTime } = useMachineUptime(); const { materialCycleTime } = useMaterialCycle(); const { throughputData } = useThroughPutData() @@ -30,14 +27,10 @@ const ProductionCapacity = ({ const [isLoading, setIsLoading] = useState(false); useEffect(() => { - console.log('typeof throughputData:', typeof throughputData); - console.log('throughputData > 0: ', throughputData > 0); if (throughputData > 0) { - // console.log('machineActiveTime: ', machineActiveTime); - // console.log('materialCycleTime: ', materialCycleTime); - // console.log('throughputData: ', throughputData); - // console.log('productionCapacityData: ', productionCapacityData); - setIsLoading(false); + setTimeout(() => { + setIsLoading(false); + }, 3000) } else { setIsLoading(true); } @@ -60,7 +53,7 @@ const ProductionCapacity = ({ - {isLoading ? ( + {!isLoading ? ( <>
diff --git a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx index aa7fc19..6efc814 100644 --- a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx +++ b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx @@ -16,7 +16,7 @@ export default function ThroughPutData() { const { machines } = machineStore(); const { conveyors } = conveyorStore(); const { storageUnits } = storageUnitStore(); - const { materialHistory } = materialStore(); + const { materialHistory, materials } = materialStore(); const { machineCount, setMachineCount } = useMachineCount(); const { machineActiveTime, setMachineActiveTime } = useMachineUptime(); const { materialCycleTime, setMaterialCycleTime } = useMaterialCycle(); @@ -109,39 +109,92 @@ export default function ThroughPutData() { // if (materialCycleTime <= 0) return }, [products, selectedProduct, getProductById, setMachineCount, materialCycleTime, armBots, vehicles, machines]); - // Setting material cycle time useEffect(() => { - materialHistory.forEach((material) => { - const start = material.material.startTime ?? 0; - const end = material.material.endTime ?? 0; - if (start === 0 || end === 0) return; - const totalCycleTime = (end - start) / 1000; // Convert milliseconds to seconds - setMaterialCycleTime(Number(totalCycleTime.toFixed(2))); // Set the material cycle time in the store - }); - }, [materialHistory]); + async function getMachineActive() { + const productData = getProductById(selectedProduct.productUuid); + let anyArmActive; + let anyVehicleActive; + let anyMachineActive; + if (productData) { + const productSequenceData = await determineExecutionMachineSequences([productData]); + if (productSequenceData?.length > 0) { + productSequenceData.forEach(sequence => { + sequence.forEach(item => { + if (item.type === "roboticArm") { + armBots + .filter(arm => arm.modelUuid === item.modelUuid) + .forEach(arm => { + if (arm.isActive) { + anyArmActive = true; + } else { + anyArmActive = false; + } + }); + } + if (item.type === "vehicle") { + vehicles + .filter(vehicle => vehicle.modelUuid === item.modelUuid) + .forEach(vehicle => { + if (vehicle.isActive) { + anyVehicleActive = true; + } else { + anyVehicleActive = false; + } + }); + } + if (item.type === "machine") { + machines + .filter(machine => machine.modelUuid === item.modelUuid) + .forEach(machine => { + if (machine.isActive) { + anyMachineActive = true; + } else { + anyMachineActive = false; + } + }); + } + }); + }); + } + } + const allInactive = !anyArmActive && !anyVehicleActive && !anyMachineActive; + if (allInactive && materials.length === 0 && materialHistory.length > 0) { + console.log("inside allInactive condition"); + let totalCycleTimeSum = 0; + let cycleCount = 0; + + materialHistory.forEach((material) => { + const start = material.material.startTime ?? 0; + const end = material.material.endTime ?? 0; + if (start === 0 || end === 0) return; + + const totalCycleTime = (end - start) / 1000; // Convert milliseconds to seconds + totalCycleTimeSum += totalCycleTime; + cycleCount++; + }); + + if (cycleCount > 0) { + const averageCycleTime = totalCycleTimeSum / cycleCount; + setMaterialCycleTime(Number(averageCycleTime.toFixed(2))); + } + } + } + + getMachineActive(); + }, [armBots, materials, materialHistory, machines, vehicles, selectedProduct]) useEffect(() => { if (machineActiveTime > 0 && materialCycleTime > 0 && machineCount > 0) { const utilization = machineActiveTime / 3600; // Active time per hour const unitsPerMachinePerHour = 3600 / materialCycleTime; const throughput = unitsPerMachinePerHour * machineCount * utilization; - - setThroughputData(throughput.toFixed(2)); // Set throughput to state/store - - // console.log('---Throughput Results---'); - // console.log('Machine Active Time (s):', machineActiveTime); - // console.log('Material Cycle Time (s):', materialCycleTime); - // console.log('Machine Count:', machineCount); - // console.log('Utilization:', utilization); - // console.log('Throughput (units/hr):', throughput); + setThroughputData(Number(throughput.toFixed(2))); // Keep as number + // console.log('throughput ', Number(throughput.toFixed(2))); } }, [machineActiveTime, materialCycleTime, machineCount]); - - - return ( <> -- 2.40.1 From 365d096d8e72ad8dcdba46114856478c20131e16 Mon Sep 17 00:00:00 2001 From: Gomathi9520 Date: Tue, 10 Jun 2025 13:41:50 +0530 Subject: [PATCH 02/17] Update response message checks and enhance loading state management across components --- .../properties/ZoneProperties.tsx | 10 +++---- .../ui/analysis/ProductionCapacity.tsx | 5 +++- app/src/components/ui/analysis/ROISummary.tsx | 4 +-- .../ui/analysis/ThroughputSummary.tsx | 7 ++--- app/src/components/ui/list/List.tsx | 6 ++-- .../analysis/throughPut/throughPutData.tsx | 28 +++++++++++-------- .../instances/animator/vehicleAnimator.tsx | 2 +- app/src/pages/UserAuth.tsx | 6 ++-- 8 files changed, 37 insertions(+), 31 deletions(-) diff --git a/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx b/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx index 2cad712..b12a45f 100644 --- a/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx +++ b/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx @@ -35,9 +35,9 @@ const ZoneProperties: React.FC = () => { viewPortCenter: zoneTarget, }; - let response = await zoneCameraUpdate(zonesdata, organization,projectId); + let response = await zoneCameraUpdate(zonesdata, organization, projectId); console.log('response: ', response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setEdit(false); } else { // console.log(response); @@ -59,10 +59,10 @@ const ZoneProperties: React.FC = () => { zoneName: newName, }; // Call your API to update the zone - let response = await zoneCameraUpdate(zonesdata, organization,projectId); + let response = await zoneCameraUpdate(zonesdata, organization, projectId); console.log('response: ', response); - // console.log("response: ", response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { + setSelectedZone((prev) => ({ ...prev, zoneName: newName })); setZones((prevZones: any[]) => prevZones.map((zone) => zone.zoneUuid === selectedZone.zoneUuid diff --git a/app/src/components/ui/analysis/ProductionCapacity.tsx b/app/src/components/ui/analysis/ProductionCapacity.tsx index 7c2e883..e29a09a 100644 --- a/app/src/components/ui/analysis/ProductionCapacity.tsx +++ b/app/src/components/ui/analysis/ProductionCapacity.tsx @@ -93,7 +93,10 @@ const ThroughputSummary: React.FC = () => { useEffect(() => { // console.log('productionCapacityData > 0: ', productionCapacityData > 0); if (productionCapacityData > 0) { - setIsLoading(false); + setTimeout(() => { + + setIsLoading(false); + }, 3000) console.log("productionCapacityData: ", productionCapacityData); } else { setIsLoading(true); diff --git a/app/src/components/ui/analysis/ROISummary.tsx b/app/src/components/ui/analysis/ROISummary.tsx index 0de3c4a..56ac5dd 100644 --- a/app/src/components/ui/analysis/ROISummary.tsx +++ b/app/src/components/ui/analysis/ROISummary.tsx @@ -80,7 +80,7 @@ const ROISummary = ({ const year = now.getFullYear(); return `${day} ${month}, ${year}`; } - const [isLoading, setIsLoading] = useState(false); + const [isLoading, setIsLoading] = useState(true); const { roiSummary } = useROISummaryData(); @@ -88,7 +88,7 @@ const ROISummary = ({ if (roiSummary.productName) { setTimeout(() => { setIsLoading(false); - }, 4000) + }, 4500) } else { // If productName is empty, assume still loading setIsLoading(true); diff --git a/app/src/components/ui/analysis/ThroughputSummary.tsx b/app/src/components/ui/analysis/ThroughputSummary.tsx index 6660e90..fd3fb60 100644 --- a/app/src/components/ui/analysis/ThroughputSummary.tsx +++ b/app/src/components/ui/analysis/ThroughputSummary.tsx @@ -24,17 +24,14 @@ const ProductionCapacity = ({ const partialFillPercent = ((progressPercent / 100) * totalBars - barsToFill) * 100; - const [isLoading, setIsLoading] = useState(false); + const [isLoading, setIsLoading] = useState(true); useEffect(() => { if (throughputData > 0) { - setTimeout(() => { - setIsLoading(false); - }, 3000) + setIsLoading(false); } else { setIsLoading(true); } - }, [throughputData]) return ( diff --git a/app/src/components/ui/list/List.tsx b/app/src/components/ui/list/List.tsx index 8136a18..f85acfa 100644 --- a/app/src/components/ui/list/List.tsx +++ b/app/src/components/ui/list/List.tsx @@ -119,17 +119,15 @@ const List: React.FC = ({ items = [], remove }) => { alert("Zone name already exists. Please choose a different name."); return; // DO NOT update state } - const zonesdata = { zoneUuid: selectedZone.zoneUuid, zoneName: newName, }; - + console.log('zonesdata: ', zonesdata); const response = await zoneCameraUpdate(zonesdata, organization,projectId); console.log('response: ', response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setSelectedZone((prev) => ({ ...prev, zoneName: newName })); - setZones((prevZones: any[]) => prevZones.map((zone) => zone.zoneUuid === selectedZone.zoneUuid diff --git a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx index 6efc814..5a03141 100644 --- a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx +++ b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx @@ -49,16 +49,15 @@ export default function ThroughPutData() { if (item.type === "roboticArm") { armBots.filter(arm => arm.modelUuid === item.modelUuid) .forEach(arm => { - if (arm.activeTime >= 0) { + if (arm.activeTime > 0) { process.push({ modelid: arm.modelUuid, modelName: arm.modelName, activeTime: arm?.activeTime }) totalActiveTime += arm.activeTime; - } }); } else if (item.type === "vehicle") { vehicles.filter(vehicle => vehicle.modelUuid === item.modelUuid) .forEach(vehicle => { - if (vehicle.activeTime >= 0) { + if (vehicle.activeTime > 0) { process.push({ modelid: vehicle.modelUuid, modelName: vehicle.modelName, activeTime: vehicle?.activeTime }) totalActiveTime += vehicle.activeTime; @@ -67,7 +66,7 @@ export default function ThroughPutData() { } else if (item.type === "machine") { machines.filter(machine => machine.modelUuid === item.modelUuid) .forEach(machine => { - if (machine.activeTime >= 0) { + if (machine.activeTime > 0) { process.push({ modelid: machine.modelUuid, modelName: machine.modelName, activeTime: machine?.activeTime }) totalActiveTime += machine.activeTime; } @@ -75,16 +74,16 @@ export default function ThroughPutData() { } else if (item.type === "transfer") { conveyors.filter(conveyor => conveyor.modelUuid === item.modelUuid) .forEach(conveyor => { - if (conveyor.activeTime >= 0) { - totalActiveTime += conveyor.activeTime; + if (conveyor.activeTime > 0) { + // totalActiveTime += conveyor.activeTime; } }); } else if (item.type === "storageUnit") { storageUnits.filter(storage => storage.modelUuid === item.modelUuid) .forEach(storage => { - if (storage.activeTime >= 0) { - totalActiveTime += storage.activeTime; - + if (storage.activeTime > 0) { + // totalActiveTime += storage.activeTime; +// } }); } @@ -93,6 +92,7 @@ export default function ThroughPutData() { totalItems += sequence.length; }); + console.log(totalActiveTime); setMachineCount(totalItems); setMachineActiveTime(totalActiveTime); let arr = process.map((item: any) => ({ @@ -181,12 +181,18 @@ export default function ThroughPutData() { } } } - - getMachineActive(); + if (isPlaying) { + setTimeout(() => { + getMachineActive(); + }, 500) + } }, [armBots, materials, materialHistory, machines, vehicles, selectedProduct]) useEffect(() => { if (machineActiveTime > 0 && materialCycleTime > 0 && machineCount > 0) { + console.log('machineActiveTime: ', machineActiveTime); + console.log('materialCycleTime: ', materialCycleTime); + console.log('machineCount: ', machineCount); const utilization = machineActiveTime / 3600; // Active time per hour const unitsPerMachinePerHour = 3600 / materialCycleTime; const throughput = unitsPerMachinePerHour * machineCount * utilization; diff --git a/app/src/modules/simulation/vehicle/instances/animator/vehicleAnimator.tsx b/app/src/modules/simulation/vehicle/instances/animator/vehicleAnimator.tsx index 4c76e71..9d45fd8 100644 --- a/app/src/modules/simulation/vehicle/instances/animator/vehicleAnimator.tsx +++ b/app/src/modules/simulation/vehicle/instances/animator/vehicleAnimator.tsx @@ -32,7 +32,7 @@ function VehicleAnimator({ path, handleCallBack, currentPhase, agvUuid, agvDetai useEffect(() => { if (currentPhase === 'stationed-pickup' && path.length > 0) { - console.log('path: ', path); + // console.log('path: ', path); setCurrentPath(path); setObjectRotation(agvDetail.point.action?.pickUpPoint?.rotation) } else if (currentPhase === 'pickup-drop' && path.length > 0) { diff --git a/app/src/pages/UserAuth.tsx b/app/src/pages/UserAuth.tsx index fb8de9e..dd6757f 100644 --- a/app/src/pages/UserAuth.tsx +++ b/app/src/pages/UserAuth.tsx @@ -38,13 +38,12 @@ const UserAuth: React.FC = () => { const { userId, organization } = getUserData(); - - const handleLogin = async (e: FormEvent) => { e.preventDefault(); const organization = email.split("@")[1].split(".")[0]; try { const res = await signInApi(email, password, organization, fingerprint); + console.log('res: ', res); if (res.message.message === "login successfull") { setError(""); setOrganization(organization); @@ -57,7 +56,10 @@ const UserAuth: React.FC = () => { localStorage.setItem("refreshToken", res.message.refreshToken); try { + console.log('res.message.userId: ', res.message.userId); + console.log('organization: ', organization); const projects = await recentlyViewed(organization, res.message.userId); + console.log('projects: ', projects); if (Object.values(projects.RecentlyViewed).length > 0) { const firstId = (Object.values(projects?.RecentlyViewed || {})[0] as any)?._id; -- 2.40.1 From d80d5ae16159cfe27df6762cfb5e8fbf26344ec3 Mon Sep 17 00:00:00 2001 From: Vishnu Date: Tue, 10 Jun 2025 14:55:23 +0530 Subject: [PATCH 03/17] refactor: Update response message checks and improve zone name duplication logic across components --- app/src/components/layout/sidebarLeft/SideBarLeft.tsx | 3 --- .../layout/sidebarRight/properties/ZoneProperties.tsx | 9 ++++----- app/src/components/ui/list/List.tsx | 7 +++---- 3 files changed, 7 insertions(+), 12 deletions(-) diff --git a/app/src/components/layout/sidebarLeft/SideBarLeft.tsx b/app/src/components/layout/sidebarLeft/SideBarLeft.tsx index 30f4778..8fd5bea 100644 --- a/app/src/components/layout/sidebarLeft/SideBarLeft.tsx +++ b/app/src/components/layout/sidebarLeft/SideBarLeft.tsx @@ -33,9 +33,6 @@ const SideBarLeft: React.FC = () => { console.log(value); }; - console.log('isVersionSaved: ', isVersionSaved); - console.log('toggleUILeft: ', toggleUILeft); - return (
{ let response = await zoneCameraUpdate(zonesdata, organization,projectId); console.log('response: ', response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setEdit(false); } else { // console.log(response); @@ -60,9 +60,8 @@ const ZoneProperties: React.FC = () => { }; // Call your API to update the zone let response = await zoneCameraUpdate(zonesdata, organization,projectId); - console.log('response: ', response); - // console.log("response: ", response); - if (response.message === "updated successfully") { + setSelectedZone((prev) => ({ ...prev, zoneName: newName })); + if (response.message === "zone updated") { setZones((prevZones: any[]) => prevZones.map((zone) => zone.zoneUuid === selectedZone.zoneUuid @@ -83,7 +82,7 @@ const ZoneProperties: React.FC = () => { const checkZoneNameDuplicate = (name: string) => { return zones.some( (zone: any) => - zone.zoneName.trim().toLowerCase() === name.trim().toLowerCase() && + zone.zoneName?.trim().toLowerCase() === name?.trim().toLowerCase() && zone.zoneUuid !== selectedZone.zoneUuid ); }; diff --git a/app/src/components/ui/list/List.tsx b/app/src/components/ui/list/List.tsx index 8136a18..09087cd 100644 --- a/app/src/components/ui/list/List.tsx +++ b/app/src/components/ui/list/List.tsx @@ -18,7 +18,6 @@ import { } from "../../../store/builder/store"; import { zoneCameraUpdate } from "../../../services/visulization/zone/zoneCameraUpdation"; import { setFloorItemApi } from "../../../services/factoryBuilder/assest/floorAsset/setFloorItemApi"; -import OuterClick from "../../../utils/outerClick"; import { useParams } from "react-router-dom"; import { useAssetsStore } from "../../../store/builder/useAssetStore"; @@ -111,7 +110,7 @@ const List: React.FC = ({ items = [], remove }) => { const isDuplicate = zones.some( (zone: any) => - zone.zoneName.trim().toLowerCase() === newName.trim().toLowerCase() && + zone.zoneName?.trim().toLowerCase() === newName?.trim().toLowerCase() && zone.zoneUuid !== selectedZone.zoneUuid ); @@ -127,7 +126,7 @@ const List: React.FC = ({ items = [], remove }) => { const response = await zoneCameraUpdate(zonesdata, organization,projectId); console.log('response: ', response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setSelectedZone((prev) => ({ ...prev, zoneName: newName })); setZones((prevZones: any[]) => @@ -158,7 +157,7 @@ const List: React.FC = ({ items = [], remove }) => { const checkZoneNameDuplicate = (name: string) => { return zones.some( (zone: any) => - zone.zoneName.trim().toLowerCase() === name.trim().toLowerCase() && + zone.zoneName?.trim().toLowerCase() === name?.trim().toLowerCase() && zone.zoneUuid !== selectedZone.zoneUuid ); }; -- 2.40.1 From a316413e231fcbb85236188cb13592a354187d75 Mon Sep 17 00:00:00 2001 From: Gomathi9520 Date: Tue, 10 Jun 2025 15:03:57 +0530 Subject: [PATCH 04/17] material cycle time calculated --- .../components/ui/analysis/ProductionCapacity.tsx | 4 ++-- .../analysis/throughPut/throughPutData.tsx | 12 ++++++------ 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/app/src/components/ui/analysis/ProductionCapacity.tsx b/app/src/components/ui/analysis/ProductionCapacity.tsx index e29a09a..5e2fc73 100644 --- a/app/src/components/ui/analysis/ProductionCapacity.tsx +++ b/app/src/components/ui/analysis/ProductionCapacity.tsx @@ -91,13 +91,13 @@ const ThroughputSummary: React.FC = () => { const [isLoading, setIsLoading] = useState(true); useEffect(() => { - // console.log('productionCapacityData > 0: ', productionCapacityData > 0); + // if (productionCapacityData > 0) { setTimeout(() => { setIsLoading(false); }, 3000) - console.log("productionCapacityData: ", productionCapacityData); + } else { setIsLoading(true); } diff --git a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx index 5a03141..bb548ba 100644 --- a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx +++ b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx @@ -92,7 +92,7 @@ export default function ThroughPutData() { totalItems += sequence.length; }); - console.log(totalActiveTime); + setMachineCount(totalItems); setMachineActiveTime(totalActiveTime); let arr = process.map((item: any) => ({ @@ -161,7 +161,7 @@ export default function ThroughPutData() { const allInactive = !anyArmActive && !anyVehicleActive && !anyMachineActive; if (allInactive && materials.length === 0 && materialHistory.length > 0) { - console.log("inside allInactive condition"); + let totalCycleTimeSum = 0; let cycleCount = 0; @@ -190,14 +190,14 @@ export default function ThroughPutData() { useEffect(() => { if (machineActiveTime > 0 && materialCycleTime > 0 && machineCount > 0) { - console.log('machineActiveTime: ', machineActiveTime); - console.log('materialCycleTime: ', materialCycleTime); - console.log('machineCount: ', machineCount); + + + const utilization = machineActiveTime / 3600; // Active time per hour const unitsPerMachinePerHour = 3600 / materialCycleTime; const throughput = unitsPerMachinePerHour * machineCount * utilization; setThroughputData(Number(throughput.toFixed(2))); // Keep as number - // console.log('throughput ', Number(throughput.toFixed(2))); + // } }, [machineActiveTime, materialCycleTime, machineCount]); -- 2.40.1 From de4688f201e186ceb7447bc0efe57479b96bd098 Mon Sep 17 00:00:00 2001 From: Jerald-Golden-B Date: Tue, 10 Jun 2025 15:04:33 +0530 Subject: [PATCH 05/17] refactor: Update zone update response message and clean up code formatting --- .../layout/sidebarRight/properties/ZoneProperties.tsx | 4 ++-- app/src/components/ui/list/List.tsx | 5 ++--- app/src/modules/builder/asset/assetsGroup.tsx | 2 +- app/src/modules/builder/asset/models/model/model.tsx | 10 +++++----- .../simulation/vehicle/instances/vehicleInstances.tsx | 4 ++-- .../services/visulization/zone/zoneCameraUpdation.ts | 2 +- 6 files changed, 13 insertions(+), 14 deletions(-) diff --git a/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx b/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx index 2cad712..0c8f210 100644 --- a/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx +++ b/app/src/components/layout/sidebarRight/properties/ZoneProperties.tsx @@ -37,7 +37,7 @@ const ZoneProperties: React.FC = () => { let response = await zoneCameraUpdate(zonesdata, organization,projectId); console.log('response: ', response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setEdit(false); } else { // console.log(response); @@ -62,7 +62,7 @@ const ZoneProperties: React.FC = () => { let response = await zoneCameraUpdate(zonesdata, organization,projectId); console.log('response: ', response); // console.log("response: ", response); - if (response.message === "updated successfully") { + if (response.message === "zone updated") { setZones((prevZones: any[]) => prevZones.map((zone) => zone.zoneUuid === selectedZone.zoneUuid diff --git a/app/src/components/ui/list/List.tsx b/app/src/components/ui/list/List.tsx index 8136a18..4fc2ee1 100644 --- a/app/src/components/ui/list/List.tsx +++ b/app/src/components/ui/list/List.tsx @@ -125,9 +125,8 @@ const List: React.FC = ({ items = [], remove }) => { zoneName: newName, }; - const response = await zoneCameraUpdate(zonesdata, organization,projectId); - console.log('response: ', response); - if (response.message === "updated successfully") { + const response = await zoneCameraUpdate(zonesdata, organization, projectId); + if (response.message === "zone updated") { setSelectedZone((prev) => ({ ...prev, zoneName: newName })); setZones((prevZones: any[]) => diff --git a/app/src/modules/builder/asset/assetsGroup.tsx b/app/src/modules/builder/asset/assetsGroup.tsx index 4ca6c45..c83eb64 100644 --- a/app/src/modules/builder/asset/assetsGroup.tsx +++ b/app/src/modules/builder/asset/assetsGroup.tsx @@ -176,7 +176,7 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea actionName: "Action 1", actionType: "process", processTime: 10, - swapMaterial: "material-id", + swapMaterial: "Default Material", triggers: [] } } diff --git a/app/src/modules/builder/asset/models/model/model.tsx b/app/src/modules/builder/asset/models/model/model.tsx index f70176b..f28c16a 100644 --- a/app/src/modules/builder/asset/models/model/model.tsx +++ b/app/src/modules/builder/asset/models/model/model.tsx @@ -36,7 +36,7 @@ function Model({ asset }: { readonly asset: Asset }) { const { renderDistance } = useRenderDistance(); const [isRendered, setIsRendered] = useState(false); const url_Backend_dwinzo = `http://${process.env.REACT_APP_SERVER_MARKETPLACE_URL}`; - const [gltfScene, setGltfScene] = useState(null); + const [gltfScene, setGltfScene] = useState(null); const [boundingBox, setBoundingBox] = useState(null); const groupRef = useRef(null); const { projectId } = useParams(); @@ -53,7 +53,7 @@ function Model({ asset }: { readonly asset: Asset }) { const assetId = asset.assetId; const cachedModel = THREE.Cache.get(assetId); if (cachedModel) { - setGltfScene(cachedModel); + setGltfScene(cachedModel.scene.clone()); calculateBoundingBox(cachedModel.scene); return; } @@ -66,7 +66,7 @@ function Model({ asset }: { readonly asset: Asset }) { URL.revokeObjectURL(blobUrl); THREE.Cache.remove(blobUrl); THREE.Cache.add(assetId, gltf); - setGltfScene(gltf); + setGltfScene(gltf.scene.clone()); calculateBoundingBox(gltf.scene); }, undefined, @@ -86,7 +86,7 @@ function Model({ asset }: { readonly asset: Asset }) { const modelBlob = await response.blob(); await storeGLTF(assetId, modelBlob); THREE.Cache.add(assetId, gltf); - setGltfScene(gltf); + setGltfScene(gltf.scene.clone()); calculateBoundingBox(gltf.scene); } catch (error) { console.error(`[Backend] Error storing/loading ${asset.modelName}:`, error); @@ -285,7 +285,7 @@ function Model({ asset }: { readonly asset: Asset }) { > {gltfScene && ( isRendered ? ( - + ) : ( ) diff --git a/app/src/modules/simulation/vehicle/instances/vehicleInstances.tsx b/app/src/modules/simulation/vehicle/instances/vehicleInstances.tsx index d81a91c..989242b 100644 --- a/app/src/modules/simulation/vehicle/instances/vehicleInstances.tsx +++ b/app/src/modules/simulation/vehicle/instances/vehicleInstances.tsx @@ -5,8 +5,8 @@ import { useSceneContext } from "../../../scene/sceneContext"; import { useViewSceneStore } from "../../../../store/builder/store"; function VehicleInstances() { - const { vehicleStore } = useSceneContext(); - const { vehicles } = vehicleStore(); + const { vehicleStore } = useSceneContext(); + const { vehicles } = vehicleStore(); const { viewSceneLabels } = useViewSceneStore(); return ( diff --git a/app/src/services/visulization/zone/zoneCameraUpdation.ts b/app/src/services/visulization/zone/zoneCameraUpdation.ts index e7dbdde..57bd153 100644 --- a/app/src/services/visulization/zone/zoneCameraUpdation.ts +++ b/app/src/services/visulization/zone/zoneCameraUpdation.ts @@ -11,7 +11,7 @@ export const zoneCameraUpdate = async (zoneData: {}, organization: string, proje token: localStorage.getItem("token") || "", refresh_token: localStorage.getItem("refreshToken") || "", }, - body: JSON.stringify({ zoneData,projectId }), + body: JSON.stringify({ zoneData, projectId }), }); if (!response.ok) { -- 2.40.1 From e2ef19ca4e86aa790fda772c7483261a44751c11 Mon Sep 17 00:00:00 2001 From: Jerald-Golden-B Date: Tue, 10 Jun 2025 16:59:57 +0530 Subject: [PATCH 06/17] feat: Add clearEvents and clearProducts actions to event and product stores --- .../instances/animator/roboticArmAnimator.tsx | 14 ++----- .../armInstance/roboticArmInstance.tsx | 3 +- .../instances/ikInstance/ikInstance.tsx | 40 +++++++------------ .../instances/roboticArmInstances.tsx | 8 ++-- app/src/pages/Project.tsx | 6 ++- app/src/store/simulation/useEventsStore.ts | 7 ++++ app/src/store/simulation/useProductStore.ts | 7 ++++ 7 files changed, 45 insertions(+), 40 deletions(-) diff --git a/app/src/modules/simulation/roboticArm/instances/animator/roboticArmAnimator.tsx b/app/src/modules/simulation/roboticArm/instances/animator/roboticArmAnimator.tsx index 1ad53de..a9681d6 100644 --- a/app/src/modules/simulation/roboticArm/instances/animator/roboticArmAnimator.tsx +++ b/app/src/modules/simulation/roboticArm/instances/animator/roboticArmAnimator.tsx @@ -259,10 +259,9 @@ function RoboticArmAnimator({ HandleCallback, restPosition, ikSolver, targetBone } }); - //Helper to Visible the Circle and Curve return ( <> - {customCurvePoints && customCurvePoints?.length >= 2 && currentPath && isPlaying && ( + {/* {customCurvePoints && customCurvePoints?.length >= 2 && currentPath && isPlaying && ( [p.x, p.y, p.z] as [number, number, number])} @@ -277,19 +276,16 @@ function RoboticArmAnimator({ HandleCallback, restPosition, ikSolver, targetBone rotation={[armBot.rotation[0], armBot.rotation[1], armBot.rotation[2]]} visible={false} > - {/* Green ring */} - {/* Markers at 90°, 180°, 270°, 360° */} {[90, 180, 270, 360].map((degree, index) => { const rad = ((degree) * Math.PI) / 180; const x = CIRCLE_RADIUS * Math.cos(rad); const z = CIRCLE_RADIUS * Math.sin(rad); - const y = 0; // same plane as the ring (Y axis) - + const y = 0; return ( @@ -302,7 +298,7 @@ function RoboticArmAnimator({ HandleCallback, restPosition, ikSolver, targetBone const rad = ((degree) * Math.PI) / 180; const x = CIRCLE_RADIUS * Math.cos(rad); const z = CIRCLE_RADIUS * Math.sin(rad); - const y = 0.15; // lift the text slightly above the ring + const y = 0.15; return ( ); })} - - - + */} ); diff --git a/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx b/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx index f773b7c..51f044d 100644 --- a/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx +++ b/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx @@ -10,6 +10,7 @@ import { useProductStore } from '../../../../../store/simulation/useProductStore import { useTriggerHandler } from '../../../triggers/triggerHandler/useTriggerHandler'; import { useSceneContext } from '../../../../scene/sceneContext'; import { useProductContext } from '../../../products/productContext'; +import { Preload } from '@react-three/drei'; function RoboticArmInstance({ armBot }: { readonly armBot: ArmBotStatus }) { @@ -392,7 +393,7 @@ function RoboticArmInstance({ armBot }: { readonly armBot: ArmBotStatus }) { <> {!isReset && isPlaying && ( <> - + { const draco = new DRACOLoader(); draco.setDecoderPath("https://cdn.jsdelivr.net/npm/three@0.160.0/examples/jsm/libs/draco/"); @@ -24,7 +22,6 @@ function IKInstance({ modelUrl, setIkSolver, ikSolver, armBot, groupRef }: IKIns const cloned = useMemo(() => clone(gltf?.scene), [gltf]); const targetBoneName = "Target"; const skinnedMeshName = "link_0"; - const [selectedArm, setSelectedArm] = useState(); useEffect(() => { if (!gltf) return; @@ -66,28 +63,21 @@ function IKInstance({ modelUrl, setIkSolver, ikSolver, armBot, groupRef }: IKIns const solver = new CCDIKSolver(OOI.Skinned_Mesh, iks); setIkSolver(solver); - const helper = new CCDIKHelper(OOI.Skinned_Mesh, iks, 0.05) - - setSelectedArm(OOI.Target_Bone); + // const helper = new CCDIKHelper(OOI.Skinned_Mesh, iks, 0.05) // scene.add(helper); - }, [cloned, gltf, setIkSolver]); + }, [cloned, gltf]); return ( - <> - { - setSelectedArm(groupRef.current?.getObjectByName(targetBoneName)) - }}> - - - {/* {selectedArm && } */} - + + + ) } diff --git a/app/src/modules/simulation/roboticArm/instances/roboticArmInstances.tsx b/app/src/modules/simulation/roboticArm/instances/roboticArmInstances.tsx index b1295a3..f0958b3 100644 --- a/app/src/modules/simulation/roboticArm/instances/roboticArmInstances.tsx +++ b/app/src/modules/simulation/roboticArm/instances/roboticArmInstances.tsx @@ -1,18 +1,20 @@ +import { useViewSceneStore } from "../../../../store/builder/store"; import { useSceneContext } from "../../../scene/sceneContext"; import RoboticArmInstance from "./armInstance/roboticArmInstance"; -// import RoboticArmContentUi from "../../ui3d/RoboticArmContentUi"; +import RoboticArmContentUi from "../../ui3d/RoboticArmContentUi"; import React from "react"; function RoboticArmInstances() { - const {armBotStore} = useSceneContext(); + const { armBotStore } = useSceneContext(); const { armBots } = armBotStore(); + const { viewSceneLabels } = useViewSceneStore(); return ( <> {armBots?.map((robot: ArmBotStatus) => ( - {/* */} + {viewSceneLabels && } ))} diff --git a/app/src/pages/Project.tsx b/app/src/pages/Project.tsx index cc984af..428930f 100644 --- a/app/src/pages/Project.tsx +++ b/app/src/pages/Project.tsx @@ -34,6 +34,7 @@ import { setFloorItemApi } from "../services/factoryBuilder/assest/floorAsset/se import { useAssetsStore } from "../store/builder/useAssetStore"; import ComparisonSceneProvider from "../components/layout/scenes/ComparisonSceneProvider"; import MainSceneProvider from "../components/layout/scenes/MainSceneProvider"; +import { useEventsStore } from "../store/simulation/useEventsStore"; const Project: React.FC = () => { let navigate = useNavigate(); @@ -46,7 +47,8 @@ const Project: React.FC = () => { const { setWallItems } = useWallItems(); const { setZones } = useZones(); const { isVersionSaved } = useSaveVersion(); - const { setProducts } = useProductStore(); + const { setProducts, clearProducts } = useProductStore(); + const { clearEvents } = useEventsStore(); const { projectId } = useParams(); const { setProjectName } = useProjectName(); @@ -105,6 +107,8 @@ const Project: React.FC = () => { setWallItems([]); setZones([]); setProducts([]); + clearProducts(); + clearEvents(); setActiveModule("builder"); const email = localStorage.getItem("email"); if (email) { diff --git a/app/src/store/simulation/useEventsStore.ts b/app/src/store/simulation/useEventsStore.ts index dbba722..105b0b5 100644 --- a/app/src/store/simulation/useEventsStore.ts +++ b/app/src/store/simulation/useEventsStore.ts @@ -7,6 +7,7 @@ type EventsStore = { // Event-level actions addEvent: (event: EventsSchema) => void; removeEvent: (modelUuid: string) => void; + clearEvents: () => void; updateEvent: (modelUuid: string, updates: Partial) => EventsSchema | undefined; // Point-level actions @@ -61,6 +62,12 @@ export const useEventsStore = create()( }); }, + clearEvents: () => { + set((state) => { + state.events = []; + }); + }, + updateEvent: (modelUuid, updates) => { let updatedEvent: EventsSchema | undefined; set((state) => { diff --git a/app/src/store/simulation/useProductStore.ts b/app/src/store/simulation/useProductStore.ts index ec80d50..7270233 100644 --- a/app/src/store/simulation/useProductStore.ts +++ b/app/src/store/simulation/useProductStore.ts @@ -7,6 +7,7 @@ type ProductsStore = { // Product-level actions addProduct: (productName: string, productUuid: string) => void; setProducts: (products: productsSchema) => void; + clearProducts: () => void; removeProduct: (productUuid: string) => void; updateProduct: (productUuid: string, updates: Partial<{ productName: string; eventDatas: EventsSchema[] }>) => void; @@ -99,6 +100,12 @@ export const useProductStore = create()( }); }, + clearProducts: () => { + set((state) => { + state.products = []; + }); + }, + removeProduct: (productUuid) => { set((state) => { state.products = state.products.filter(p => p.productUuid !== productUuid); -- 2.40.1 From 5f9d2b4106ca347dc00016af049a081ee39101ca Mon Sep 17 00:00:00 2001 From: Jerald-Golden-B Date: Tue, 10 Jun 2025 17:58:56 +0530 Subject: [PATCH 07/17] refactor: Remove unnecessary setIsPlaying calls and clean up event handling in simulation components --- app/src/components/layout/scenes/ComparisonScene.tsx | 1 - app/src/components/ui/compareVersion/CompareLayOut.tsx | 1 - app/src/components/ui/simulation/simulationPlayer.tsx | 3 +++ app/src/modules/simulation/simulator/simulator.tsx | 1 + app/src/pages/Dashboard.tsx | 9 +++++++++ app/src/pages/Project.tsx | 6 +----- 6 files changed, 14 insertions(+), 7 deletions(-) diff --git a/app/src/components/layout/scenes/ComparisonScene.tsx b/app/src/components/layout/scenes/ComparisonScene.tsx index 635ebec..311f4a3 100644 --- a/app/src/components/layout/scenes/ComparisonScene.tsx +++ b/app/src/components/layout/scenes/ComparisonScene.tsx @@ -22,7 +22,6 @@ function ComparisonScene() { const product = products.find((product) => product.productName === option); if (product) { setComparisonProduct(product.productUuid, product.productName); - setIsPlaying(true); setIsPaused(true); } }; diff --git a/app/src/components/ui/compareVersion/CompareLayOut.tsx b/app/src/components/ui/compareVersion/CompareLayOut.tsx index 6cce453..48bb686 100644 --- a/app/src/components/ui/compareVersion/CompareLayOut.tsx +++ b/app/src/components/ui/compareVersion/CompareLayOut.tsx @@ -118,7 +118,6 @@ const CompareLayOut = () => { if (product) { setComparisonProduct(product.productUuid, product.productName); setLoadingProgress(1); - setIsPlaying(true); setIsPaused(true); } }; diff --git a/app/src/components/ui/simulation/simulationPlayer.tsx b/app/src/components/ui/simulation/simulationPlayer.tsx index 1002a9b..7218c98 100644 --- a/app/src/components/ui/simulation/simulationPlayer.tsx +++ b/app/src/components/ui/simulation/simulationPlayer.tsx @@ -59,6 +59,9 @@ const SimulationPlayer: React.FC = () => { }; const handlePlayStop = () => { setIsPaused(!isPaused); + if (isPaused) { + setIsPlaying(true); + } echo.warn(`Simulation is ${isPaused ? "Resumed" : "Paused"}`); }; const handleExit = () => { diff --git a/app/src/modules/simulation/simulator/simulator.tsx b/app/src/modules/simulation/simulator/simulator.tsx index 5b2f8a8..f9e4714 100644 --- a/app/src/modules/simulation/simulator/simulator.tsx +++ b/app/src/modules/simulation/simulator/simulator.tsx @@ -15,6 +15,7 @@ function Simulator() { useEffect(() => { if (!isPlaying || isReset || !selectedProduct.productUuid) return; + console.log('selectedProduct: ', selectedProduct); const product = getProductById(selectedProduct.productUuid); if (!product) return; diff --git a/app/src/pages/Dashboard.tsx b/app/src/pages/Dashboard.tsx index 7065e20..e8de9c3 100644 --- a/app/src/pages/Dashboard.tsx +++ b/app/src/pages/Dashboard.tsx @@ -8,11 +8,20 @@ import DashboardTrash from "../components/Dashboard/DashboardTrash"; import { getUserData } from "../components/Dashboard/functions/getUserData"; import SidePannel from "../components/Dashboard/SidePannel"; import DashboardTutorial from "../components/Dashboard/DashboardTutorial"; +import { useProductStore } from "../store/simulation/useProductStore"; +import { useEventsStore } from "../store/simulation/useEventsStore"; const Dashboard: React.FC = () => { const [activeTab, setActiveTab] = useState("Home"); const { socket } = useSocketStore(); const { userId, organization, email, userName } = getUserData(); + const { clearProducts } = useProductStore(); + const { clearEvents } = useEventsStore(); + + useEffect(() => { + clearEvents(); + clearProducts(); + }, []) useEffect(() => { const token = localStorage.getItem("token"); diff --git a/app/src/pages/Project.tsx b/app/src/pages/Project.tsx index 428930f..cc984af 100644 --- a/app/src/pages/Project.tsx +++ b/app/src/pages/Project.tsx @@ -34,7 +34,6 @@ import { setFloorItemApi } from "../services/factoryBuilder/assest/floorAsset/se import { useAssetsStore } from "../store/builder/useAssetStore"; import ComparisonSceneProvider from "../components/layout/scenes/ComparisonSceneProvider"; import MainSceneProvider from "../components/layout/scenes/MainSceneProvider"; -import { useEventsStore } from "../store/simulation/useEventsStore"; const Project: React.FC = () => { let navigate = useNavigate(); @@ -47,8 +46,7 @@ const Project: React.FC = () => { const { setWallItems } = useWallItems(); const { setZones } = useZones(); const { isVersionSaved } = useSaveVersion(); - const { setProducts, clearProducts } = useProductStore(); - const { clearEvents } = useEventsStore(); + const { setProducts } = useProductStore(); const { projectId } = useParams(); const { setProjectName } = useProjectName(); @@ -107,8 +105,6 @@ const Project: React.FC = () => { setWallItems([]); setZones([]); setProducts([]); - clearProducts(); - clearEvents(); setActiveModule("builder"); const email = localStorage.getItem("email"); if (email) { -- 2.40.1 From 5be5526da65ccf3def47d1ddfcb4123e51b08ea3 Mon Sep 17 00:00:00 2001 From: Gomathi9520 Date: Tue, 10 Jun 2025 18:06:41 +0530 Subject: [PATCH 08/17] Enhance ROIData component with product comparison functionality and clean up unused code --- .../simulation/analysis/ROI/roiData.tsx | 82 +++++++++++++------ .../analysis/throughPut/throughPutData.tsx | 5 +- 2 files changed, 56 insertions(+), 31 deletions(-) diff --git a/app/src/modules/simulation/analysis/ROI/roiData.tsx b/app/src/modules/simulation/analysis/ROI/roiData.tsx index 4d6444d..4c0f17f 100644 --- a/app/src/modules/simulation/analysis/ROI/roiData.tsx +++ b/app/src/modules/simulation/analysis/ROI/roiData.tsx @@ -2,6 +2,7 @@ import React, { useEffect, useState } from 'react' import { useInputValues, useProductionCapacityData, useROISummaryData } from '../../../../store/builder/store'; import { usePlayButtonStore } from '../../../../store/usePlayButtonStore'; import { useProductContext } from '../../products/productContext'; +import { useProductStore } from '../../../../store/simulation/useProductStore'; export default function ROIData() { const { selectedProductStore } = useProductContext(); @@ -10,6 +11,9 @@ export default function ROIData() { const { selectedProduct } = selectedProductStore(); const { isPlaying } = usePlayButtonStore(); const { setRoiSummaryData } = useROISummaryData(); + const { products, getProductById } = useProductStore(); + const [compareProducts, setCompareProducts] = useState([]); + useEffect(() => { if (!isPlaying) { setRoiSummaryData({ @@ -43,47 +47,36 @@ export default function ROIData() { !isNaN(materialCost) && !isNaN(productionPeriod) && !isNaN(salvageValue) && !isNaN(sellingPrice) && !isNaN(shiftLength) && !isNaN(shiftsPerDay) && !isNaN(workingDaysPerYear) && productionCapacityData > 0) { - - - const totalHoursPerYear = shiftLength * shiftsPerDay * workingDaysPerYear; - // Total good units produced per year const annualProductionUnits = productionCapacityData * totalHoursPerYear; - // Revenue for a year const annualRevenue = annualProductionUnits * sellingPrice; - // Costs const totalMaterialCost = annualProductionUnits * materialCost; const totalLaborCost = laborCost * totalHoursPerYear; const totalEnergyCost = electricityCost * totalHoursPerYear; const totalMaintenanceCost = maintenanceCost + fixedCost; - const totalAnnualCost = totalMaterialCost + totalLaborCost + totalEnergyCost + totalMaintenanceCost; - // Annual Profit const annualProfit = annualRevenue - totalAnnualCost; - console.log('annualProfit: ', annualProfit); - + // Net Profit over production period const netProfit = annualProfit * productionPeriod; - // ROI const roiPercentage = ((netProfit + salvageValue - initialInvestment) / initialInvestment) * 100; - // Payback Period const paybackPeriod = initialInvestment / (annualProfit || 1); // Avoid division by 0 - console.log('paybackPeriod: ', paybackPeriod); + - // console.log("--- ROI Breakdown ---"); - // console.log("Annual Production Units:", annualProductionUnits.toFixed(2)); - // console.log("Annual Revenue:", annualRevenue.toFixed(2)); - // console.log("Total Annual Cost:", totalAnnualCost.toFixed(2)); - // console.log("Annual Profit:", annualProfit.toFixed(2)); - // console.log("Net Profit:", netProfit.toFixed(2)); - // console.log("ROI %:", roiPercentage.toFixed(2)); - // console.log("Payback Period (years):", paybackPeriod.toFixed(2)); + // + // + // + // + // + // + // + // setRoiSummaryData({ productName: selectedProduct.productName, @@ -107,13 +100,48 @@ export default function ROIData() { const netProfitForTarget = profitForTargetUnits > 0 ? profitForTargetUnits : 0; const netLossForTarget = profitForTargetUnits < 0 ? -profitForTargetUnits : 0; - // console.log("--- Fixed Product Count (" + productCount + ") ---"); - // console.log("Cost per Unit:", costPerUnit.toFixed(2)); - // console.log("Total Cost for " + productCount + " Units:", costForTargetUnits.toFixed(2)); - // console.log("Revenue for " + productCount + " Units:", revenueForTargetUnits.toFixed(2)); - // console.log("Profit:", netProfitForTarget.toFixed(2)); - // console.log("Loss:", netLossForTarget.toFixed(2)); + // + // + // + // + // + // + const productData = getProductById(selectedProduct.productUuid); + + + setCompareProducts(prev => { + const newData = { + productUuid: productData?.productUuid, + productName: productData?.productName, + costPerUnit: parseFloat(costPerUnit.toFixed(2)), + workingDaysPerYear: parseFloat(workingDaysPerYear.toFixed(2)), + shiftLength: parseFloat(shiftLength.toFixed(2)), + shiftsPerDay: parseFloat(shiftsPerDay.toFixed(2)), + roiPercentage: parseFloat((roiPercentage / 100).toFixed(2)), + paybackPeriod: parseFloat(paybackPeriod.toFixed(2)), + totalCost: parseFloat(totalAnnualCost.toFixed(2)), + revenueGenerated: parseFloat(annualRevenue.toFixed(2)), + netProfit: netProfit > 0 ? parseFloat(netProfit.toFixed(2)) : 0, + netLoss: netProfit < 0 ? parseFloat((-netProfit).toFixed(2)) : 0 + }; + + const existingIndex = prev.findIndex( + item => item.productUuid === productData?.productUuid + ); + + if (existingIndex !== -1) { + // Replace the existing item + const updated = [...prev]; + updated[existingIndex] = newData; + return updated; + } else { + // Add as new item + return [...prev, newData]; + } + }); + console.log('compareProducts: ', compareProducts); + } }, [inputValues, productionCapacityData]); diff --git a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx index bb548ba..78bd1a7 100644 --- a/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx +++ b/app/src/modules/simulation/analysis/throughPut/throughPutData.tsx @@ -36,7 +36,7 @@ export default function ThroughPutData() { setMaterialCycleTime(0); setProcessBar([]); setThroughputData(0); - return; + return; } else { let process: any = []; const fetchProductSequenceData = async () => { @@ -190,9 +190,6 @@ export default function ThroughPutData() { useEffect(() => { if (machineActiveTime > 0 && materialCycleTime > 0 && machineCount > 0) { - - - const utilization = machineActiveTime / 3600; // Active time per hour const unitsPerMachinePerHour = 3600 / materialCycleTime; const throughput = unitsPerMachinePerHour * machineCount * utilization; -- 2.40.1 From 9e25fb7acef5fc19f5b7ffb6a316db8240e03860 Mon Sep 17 00:00:00 2001 From: Nalvazhuthi Date: Tue, 10 Jun 2025 18:07:13 +0530 Subject: [PATCH 09/17] refactor: remove unnecessary console logs in SideBarLeft; update comparePopUp default state to false; fix color variable in dashboard styles --- app/src/components/layout/sidebarLeft/SideBarLeft.tsx | 3 --- .../components/layout/sidebarRight/simulation/Simulations.tsx | 1 + app/src/modules/visualization/widgets/panel/Panel.tsx | 2 +- app/src/store/builder/store.ts | 3 ++- app/src/styles/pages/dashboard.scss | 4 ++-- 5 files changed, 6 insertions(+), 7 deletions(-) diff --git a/app/src/components/layout/sidebarLeft/SideBarLeft.tsx b/app/src/components/layout/sidebarLeft/SideBarLeft.tsx index 30f4778..8fd5bea 100644 --- a/app/src/components/layout/sidebarLeft/SideBarLeft.tsx +++ b/app/src/components/layout/sidebarLeft/SideBarLeft.tsx @@ -33,9 +33,6 @@ const SideBarLeft: React.FC = () => { console.log(value); }; - console.log('isVersionSaved: ', isVersionSaved); - console.log('toggleUILeft: ', toggleUILeft); - return (
{ } ); } + }, [selectedProduct.productUuid, products]); return ( diff --git a/app/src/modules/visualization/widgets/panel/Panel.tsx b/app/src/modules/visualization/widgets/panel/Panel.tsx index add1855..c9c62c9 100644 --- a/app/src/modules/visualization/widgets/panel/Panel.tsx +++ b/app/src/modules/visualization/widgets/panel/Panel.tsx @@ -340,4 +340,4 @@ const Panel: React.FC = ({ ); }; -export default Panel; +export default Panel; \ No newline at end of file diff --git a/app/src/store/builder/store.ts b/app/src/store/builder/store.ts index c384f20..2f1de1b 100644 --- a/app/src/store/builder/store.ts +++ b/app/src/store/builder/store.ts @@ -626,11 +626,12 @@ interface CompareStore { } export const useCompareStore = create((set) => ({ - comparePopUp: true, + comparePopUp: false, setComparePopUp: (value) => set({ comparePopUp: value }), toggleComparePopUp: () => set((state) => ({ comparePopUp: !state.comparePopUp })), })); + // Save state store interface SaveVersionStore { isVersionSaved: boolean; diff --git a/app/src/styles/pages/dashboard.scss b/app/src/styles/pages/dashboard.scss index a136974..95898db 100644 --- a/app/src/styles/pages/dashboard.scss +++ b/app/src/styles/pages/dashboard.scss @@ -144,7 +144,7 @@ &.active { background: var(--background-color-button); - color: var(--text-color); + color: var(--text-button-color); } } } @@ -342,4 +342,4 @@ font-family: #{$font-roboto}; cursor: pointer; } -} +} \ No newline at end of file -- 2.40.1 From 4d77aa6a994d8bd94c14162f7eb8455050a1bc3a Mon Sep 17 00:00:00 2001 From: Poovizhi99 Date: Tue, 10 Jun 2025 18:46:48 +0530 Subject: [PATCH 10/17] refactor: Improve path computation logic and enhance error handling in VehicleInstance; add debug logs in UserAuth for API response --- .../instances/instance/vehicleInstance.tsx | 22 +++++++++++++++---- app/src/pages/UserAuth.tsx | 14 ++++++------ 2 files changed, 25 insertions(+), 11 deletions(-) diff --git a/app/src/modules/simulation/vehicle/instances/instance/vehicleInstance.tsx b/app/src/modules/simulation/vehicle/instances/instance/vehicleInstance.tsx index 2031f99..9952888 100644 --- a/app/src/modules/simulation/vehicle/instances/instance/vehicleInstance.tsx +++ b/app/src/modules/simulation/vehicle/instances/instance/vehicleInstance.tsx @@ -48,14 +48,24 @@ function VehicleInstance({ agvDetail }: Readonly<{ agvDetail: VehicleStatus }>) const computePath = useCallback( (start: any, end: any) => { + console.log('end: ', end); 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]) || [] - ); + if ( + segmentPath.length > 0 && + Math.round(segmentPath[segmentPath.length - 1].x) == Math.round(end.x) && + Math.round(segmentPath[segmentPath.length - 1].z) == Math.round(end.z) + ) { + console.log('if ', segmentPath); + return segmentPath?.map(({ x, y, z }) => [x, 0, z] as [number, number, number]) || []; + } else { + console.log("There is no path here...Choose valid path") + const { path: segmentPaths } = navMeshQuery.computePath(start, start); + return segmentPaths.map(({ x, y, z }) => [x, 0, z] as [number, number, number]) || []; + } } catch { - echo.error("Failed to compute path"); + console.error("Failed to compute path"); return []; } }, @@ -96,6 +106,10 @@ function VehicleInstance({ agvDetail }: Readonly<{ agvDetail: VehicleStatus }>) new THREE.Vector3(agvDetail?.position[0], agvDetail?.position[1], agvDetail?.position[2]), agvDetail?.point?.action?.pickUpPoint?.position ); + // const toPickupPath = computePath( + // new THREE.Vector3(agvDetail?.position[0], agvDetail?.position[1], agvDetail?.position[2]), + // new THREE.Vector3(agvDetail?.position[0], agvDetail?.position[1], agvDetail?.position[2]) + // ); setPath(toPickupPath); setCurrentPhase('stationed-pickup'); setVehicleState(agvDetail.modelUuid, 'running'); diff --git a/app/src/pages/UserAuth.tsx b/app/src/pages/UserAuth.tsx index fb8de9e..700265a 100644 --- a/app/src/pages/UserAuth.tsx +++ b/app/src/pages/UserAuth.tsx @@ -45,6 +45,7 @@ const UserAuth: React.FC = () => { const organization = email.split("@")[1].split(".")[0]; try { const res = await signInApi(email, password, organization, fingerprint); + console.log('res: ', res); if (res.message.message === "login successfull") { setError(""); setOrganization(organization); @@ -59,14 +60,13 @@ const UserAuth: React.FC = () => { try { const projects = await recentlyViewed(organization, res.message.userId); - if (Object.values(projects.RecentlyViewed).length > 0) { - const firstId = (Object.values(projects?.RecentlyViewed || {})[0] as any)?._id; - setLoadingProgress(1) - navigate(`/${firstId}`) - } else { - if (res.message.isShare) { + if (res.message.isShare) { + if (Object.values(projects.RecentlyViewed).length > 0) { + const firstId = (Object.values(projects?.RecentlyViewed || {})[0] as any)?._id; + setLoadingProgress(1) + navigate(`/${firstId}`) + } else { setLoadingProgress(1); - // navigate("/Project"); navigate("/Dashboard"); } } -- 2.40.1 From 5d03a2bc61f014856bfe38736fcee27ec9bd5e1f Mon Sep 17 00:00:00 2001 From: Gomathi9520 Date: Wed, 11 Jun 2025 09:33:09 +0530 Subject: [PATCH 11/17] Update ComparisonScene to include mainProduct and loadingProgress, --- app/src/components/layout/scenes/ComparisonScene.tsx | 8 +++++--- app/src/modules/simulation/analysis/ROI/roiData.tsx | 2 +- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/app/src/components/layout/scenes/ComparisonScene.tsx b/app/src/components/layout/scenes/ComparisonScene.tsx index 311f4a3..d29b54a 100644 --- a/app/src/components/layout/scenes/ComparisonScene.tsx +++ b/app/src/components/layout/scenes/ComparisonScene.tsx @@ -1,11 +1,11 @@ import { useProductContext } from '../../../modules/simulation/products/productContext' import RegularDropDown from '../../ui/inputs/RegularDropDown'; import { useProductStore } from '../../../store/simulation/useProductStore'; -import { useSaveVersion } from '../../../store/builder/store'; +import { useLoadingProgress, useSaveVersion } from '../../../store/builder/store'; import useModuleStore from '../../../store/useModuleStore'; import CompareLayOut from '../../ui/compareVersion/CompareLayOut'; import ComparisonResult from '../../ui/compareVersion/ComparisonResult'; -import { useComparisonProduct } from '../../../store/simulation/useSimulationStore'; +import { useComparisonProduct, useMainProduct } from '../../../store/simulation/useSimulationStore'; import { usePauseButtonStore, usePlayButtonStore } from '../../../store/usePlayButtonStore'; function ComparisonScene() { @@ -16,7 +16,9 @@ function ComparisonScene() { const { selectedProductStore } = useProductContext(); const { selectedProduct } = selectedProductStore(); const { comparisonProduct, setComparisonProduct } = useComparisonProduct(); + const { mainProduct } = useMainProduct(); const { setIsPaused } = usePauseButtonStore(); + const { loadingProgress } = useLoadingProgress(); const handleSelectLayout = (option: string) => { const product = products.find((product) => product.productName === option); @@ -40,7 +42,7 @@ function ComparisonScene() {
} - {false && } + {(comparisonProduct && mainProduct && !loadingProgress) && } )} diff --git a/app/src/modules/simulation/analysis/ROI/roiData.tsx b/app/src/modules/simulation/analysis/ROI/roiData.tsx index 4c0f17f..6551d54 100644 --- a/app/src/modules/simulation/analysis/ROI/roiData.tsx +++ b/app/src/modules/simulation/analysis/ROI/roiData.tsx @@ -140,7 +140,7 @@ export default function ROIData() { return [...prev, newData]; } }); - console.log('compareProducts: ', compareProducts); + // console.log('compareProducts: ', compareProducts); } -- 2.40.1 From ab1230f166956cc171fbc75290365ceccc0b1de9 Mon Sep 17 00:00:00 2001 From: Nalvazhuthi Date: Wed, 11 Jun 2025 09:52:40 +0530 Subject: [PATCH 12/17] refactor: enhance chart layout and styles in ComparisonResult component; add Pie chart for cycle time data --- .../ui/compareVersion/ComparisonResult.tsx | 28 +++++++++++-------- app/src/styles/layout/compareLayout.scss | 17 +++++++++++ 2 files changed, 33 insertions(+), 12 deletions(-) diff --git a/app/src/components/ui/compareVersion/ComparisonResult.tsx b/app/src/components/ui/compareVersion/ComparisonResult.tsx index 0f91a36..79fa57c 100644 --- a/app/src/components/ui/compareVersion/ComparisonResult.tsx +++ b/app/src/components/ui/compareVersion/ComparisonResult.tsx @@ -1,7 +1,7 @@ import React, { useMemo } from "react"; import PerformanceResult from "./result-card/PerformanceResult"; import EnergyUsage from "./result-card/EnergyUsage"; -import { Bar, Line } from "react-chartjs-2"; +import { Bar, Line, Pie } from "react-chartjs-2"; const ComparisonResult = () => { const options = useMemo( @@ -33,21 +33,22 @@ const ComparisonResult = () => { backgroundColor: [purpleDark, purpleLight], borderColor: [purpleDark, purpleLight], borderWidth: 1, + borderRadius: 10, // ✅ Rounded all corners (TypeScript-safe) + // borderSkipped: "bottom", // ✅ This is allowed by the Chart.js types }, ], }; - const cycleTimeData = { + + const cycleTimePieData = { labels: ["Layout 1", "Layout 2"], datasets: [ { label: "Cycle Time (sec)", - data: [110, 110], - backgroundColor: [purpleLight], - borderColor: purpleDark, + data: [120, 110], + backgroundColor: [purpleDark, purpleLight], + borderColor: "#fff", borderWidth: 2, - tension: 0.4, - fill: false, }, ], }; @@ -61,6 +62,8 @@ const ComparisonResult = () => { backgroundColor: [purpleDark, purpleLight], borderColor: [purpleDark, purpleLight], borderWidth: 1, + borderRadius: 10, + borderSkipped: false, }, ], }; @@ -74,6 +77,8 @@ const ComparisonResult = () => { backgroundColor: [purpleDark, purpleLight], borderColor: [purpleDark, purpleLight], borderWidth: 1, + borderRadius: 10, + borderSkipped: false, }, ], }; @@ -83,7 +88,6 @@ const ComparisonResult = () => {
Performance Comparison
-

Throughput (units/hr)

@@ -95,9 +99,9 @@ const ComparisonResult = () => {
Layout 2
550/ hr
-
-
- +
+ +
@@ -122,7 +126,7 @@ const ComparisonResult = () => {
- +
diff --git a/app/src/styles/layout/compareLayout.scss b/app/src/styles/layout/compareLayout.scss index 07b5ad2..31966be 100644 --- a/app/src/styles/layout/compareLayout.scss +++ b/app/src/styles/layout/compareLayout.scss @@ -463,6 +463,7 @@ width: 100%; display: flex; justify-content: space-between; + position: relative; .layer-wrapper { display: flex; @@ -472,6 +473,12 @@ justify-content: end; } } + + .chart { + width: 60%; + height: 70%; + position: absolute; + } } .chart { @@ -484,6 +491,8 @@ } .cycle-time-container { + position: relative; + .cycle-main { display: flex; justify-content: space-between; @@ -519,6 +528,14 @@ } } } + + .chart { + position: absolute; + bottom: 0; + left: 10px; + width: 60%; + height: 80%; + } } .overallDowntime-container { -- 2.40.1 From ef6c0c6cbb0b57ebad3125af5adf836b7a6916fc Mon Sep 17 00:00:00 2001 From: Poovizhi99 Date: Wed, 11 Jun 2025 10:44:13 +0530 Subject: [PATCH 13/17] feat: Integrate rename functionality in MainScene and AssetsGroup; add RenameTooltip component for user interaction --- .../components/layout/scenes/MainScene.tsx | 25 ++++++++++++++++- .../components/ui/features/RenameTooltip.tsx | 2 ++ app/src/modules/builder/asset/assetsGroup.tsx | 28 +++++++++++++++++-- app/src/modules/builder/groups/floorGroup.tsx | 8 +++--- 4 files changed, 56 insertions(+), 7 deletions(-) diff --git a/app/src/components/layout/scenes/MainScene.tsx b/app/src/components/layout/scenes/MainScene.tsx index d299dc9..02c034a 100644 --- a/app/src/components/layout/scenes/MainScene.tsx +++ b/app/src/components/layout/scenes/MainScene.tsx @@ -1,7 +1,9 @@ import React from "react"; import { useLoadingProgress, + useRenameModeStore, useSaveVersion, + useSelectedFloorItem, useSocketStore, useWidgetSubOption, } from "../../../store/builder/store"; @@ -30,6 +32,9 @@ import { import { useProductContext } from "../../../modules/simulation/products/productContext"; import { useProductStore } from "../../../store/simulation/useProductStore"; import RegularDropDown from "../../ui/inputs/RegularDropDown"; +import RenameTooltip from "../../ui/features/RenameTooltip"; +import { setFloorItemApi } from "../../../services/factoryBuilder/assest/floorAsset/setFloorItemApi"; +import { useAssetsStore } from "../../../store/builder/useAssetStore"; function MainScene() { const { products } = useProductStore(); @@ -47,13 +52,30 @@ function MainScene() { const { selectedZone } = useSelectedZoneStore(); const { setFloatingWidget } = useFloatingWidget(); const { comparisonProduct } = useComparisonProduct(); - + const { selectedFloorItem, setSelectedFloorItem } = useSelectedFloorItem(); + const { setName } = useAssetsStore(); + const { isRenameMode, setIsRenameMode } = useRenameModeStore(); const handleSelectLayout = (option: string) => { const product = products.find((product) => product.productName === option); if (product) { setMainProduct(product.productUuid, product.productName); } }; + const handleObjectRename = async (newName: string) => { + const email = localStorage.getItem("email") ?? ""; + const organization = email?.split("@")[1]?.split(".")[0]; + let response = await setFloorItemApi( + organization, + selectedFloorItem.userData.modelUuid, + newName + ); + console.log('selectedFloorItem: ', selectedFloorItem.userData.modelUuid); + selectedFloorItem.userData.modelName = newName; + setSelectedFloorItem(selectedFloorItem); + setIsRenameMode(false); + + setName(selectedFloorItem.userData.modelUuid, newName); + } return ( <> @@ -79,6 +101,7 @@ function MainScene() { {(isPlaying || comparisonProduct !== null) && activeModule !== "simulation" && } + {isRenameMode && selectedFloorItem?.userData.modelName && } {/* remove this later */} {activeModule === "builder" && !toggleThreeD && } diff --git a/app/src/components/ui/features/RenameTooltip.tsx b/app/src/components/ui/features/RenameTooltip.tsx index 87de122..0419071 100644 --- a/app/src/components/ui/features/RenameTooltip.tsx +++ b/app/src/components/ui/features/RenameTooltip.tsx @@ -12,6 +12,7 @@ type RenameTooltipProps = { }; const RenameTooltip: React.FC = ({ name, onSubmit }) => { + console.log('name: ', name); const [value, setValue] = useState(name); const { top, setTop } = useTopData(); @@ -19,6 +20,7 @@ const RenameTooltip: React.FC = ({ name, onSubmit }) => { const handleSubmit = (e: React.FormEvent) => { e.preventDefault(); + console.log('value.trim(): ', value.trim()); onSubmit(value.trim()); setTop(0); setLeft(0); diff --git a/app/src/modules/builder/asset/assetsGroup.tsx b/app/src/modules/builder/asset/assetsGroup.tsx index c83eb64..b1533a4 100644 --- a/app/src/modules/builder/asset/assetsGroup.tsx +++ b/app/src/modules/builder/asset/assetsGroup.tsx @@ -1,7 +1,7 @@ import * as THREE from "three" import { useEffect } from 'react' import { getFloorAssets } from '../../../services/factoryBuilder/assest/floorAsset/getFloorItemsApi'; -import { useLoadingProgress, useSelectedFloorItem, useSelectedItem, useSocketStore } from '../../../store/builder/store'; +import { useLoadingProgress, useRenameModeStore, useSelectedFloorItem, useSelectedItem, useSocketStore } from '../../../store/builder/store'; import { GLTFLoader } from "three/examples/jsm/loaders/GLTFLoader"; import { DRACOLoader } from "three/examples/jsm/loaders/DRACOLoader"; import { FloorItems, RefGroup, RefMesh } from "../../../types/world/worldTypes"; @@ -13,6 +13,7 @@ import { useThree } from "@react-three/fiber"; import { CameraControls } from "@react-three/drei"; import addAssetModel from "./functions/addAssetModel"; import { useParams } from "react-router-dom"; +import { useLeftData, useTopData } from "../../../store/visualization/useZone3DWidgetStore"; const gltfLoaderWorker = new Worker( new URL( @@ -31,9 +32,12 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea const { setSelectedFloorItem } = useSelectedFloorItem(); const { selectedItem, setSelectedItem } = useSelectedItem(); const { projectId } = useParams(); + const { isRenameMode, setIsRenameMode } = useRenameModeStore(); const email = localStorage.getItem("email"); const organization = email!.split("@")[1].split(".")[0]; const userId = localStorage.getItem("userId")!; + const { setTop } = useTopData(); + const { setLeft } = useLeftData(); const loader = new GLTFLoader(); const dracoLoader = new DRACOLoader(); @@ -257,6 +261,7 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea useEffect(() => { const canvasElement = gl.domElement; + const onDrop = (event: any) => { if (!event.dataTransfer?.files[0]) return; @@ -272,11 +277,28 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea const onDragOver = (event: any) => { event.preventDefault(); }; + const onMouseMove = (evt: any) => { + if (!canvasElement) return; + const canvasRect = canvasElement.getBoundingClientRect(); + const relativeX = evt.clientX - canvasRect.left; + const relativeY = evt.clientY - canvasRect.top; + if (!isRenameMode) { + setTop(relativeY); + setLeft(relativeX); + } + + + }; + const onMouseUp = (evt: any) => { + setIsRenameMode(false); + } if (activeModule === "builder") { canvasElement.addEventListener("drop", onDrop); canvasElement.addEventListener("dragover", onDragOver); + canvasElement.addEventListener("mousemove", onMouseMove); + canvasElement.addEventListener("mouseup", onMouseUp); } else { if ((controls as CameraControls)) { const target = (controls as CameraControls).getTarget(new THREE.Vector3()); @@ -288,8 +310,10 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea return () => { canvasElement.removeEventListener("drop", onDrop); canvasElement.removeEventListener("dragover", onDragOver); + canvasElement.removeEventListener("mousemove", onMouseMove); + canvasElement.removeEventListener("mouseup", onMouseUp); }; - }, [selectedItem, camera, pointer, activeModule, controls]); + }, [selectedItem, camera, pointer, activeModule, controls, isRenameMode]); return ( diff --git a/app/src/modules/builder/groups/floorGroup.tsx b/app/src/modules/builder/groups/floorGroup.tsx index 2cf5586..eb77f03 100644 --- a/app/src/modules/builder/groups/floorGroup.tsx +++ b/app/src/modules/builder/groups/floorGroup.tsx @@ -87,10 +87,10 @@ const FloorGroup = ({ const canvasRect = canvasElement.getBoundingClientRect(); const relativeX = evt.clientX - canvasRect.left; const relativeY = evt.clientY - canvasRect.top; - if (!isRenameMode) { - setTop(relativeY); - setLeft(relativeX); - } + // if (!isRenameMode) { + // setTop(relativeY); + // setLeft(relativeX); + // } if (isLeftMouseDown) { drag = true; } -- 2.40.1 From 13ad2dc49068225d4a47c7e0a0d586a3c7e532f2 Mon Sep 17 00:00:00 2001 From: Poovizhi99 Date: Wed, 11 Jun 2025 10:52:10 +0530 Subject: [PATCH 14/17] feat: Add projectId parameter to setFloorItemApi and update related components in MainScene and List --- app/src/components/layout/scenes/MainScene.tsx | 5 ++++- app/src/components/ui/list/List.tsx | 5 +++-- .../factoryBuilder/assest/floorAsset/setFloorItemApi.ts | 2 ++ 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/app/src/components/layout/scenes/MainScene.tsx b/app/src/components/layout/scenes/MainScene.tsx index 02c034a..08ebb8a 100644 --- a/app/src/components/layout/scenes/MainScene.tsx +++ b/app/src/components/layout/scenes/MainScene.tsx @@ -35,6 +35,7 @@ import RegularDropDown from "../../ui/inputs/RegularDropDown"; import RenameTooltip from "../../ui/features/RenameTooltip"; import { setFloorItemApi } from "../../../services/factoryBuilder/assest/floorAsset/setFloorItemApi"; import { useAssetsStore } from "../../../store/builder/useAssetStore"; +import { useParams } from "react-router-dom"; function MainScene() { const { products } = useProductStore(); @@ -54,6 +55,7 @@ function MainScene() { const { comparisonProduct } = useComparisonProduct(); const { selectedFloorItem, setSelectedFloorItem } = useSelectedFloorItem(); const { setName } = useAssetsStore(); + const { projectId } = useParams() const { isRenameMode, setIsRenameMode } = useRenameModeStore(); const handleSelectLayout = (option: string) => { const product = products.find((product) => product.productName === option); @@ -67,7 +69,8 @@ function MainScene() { let response = await setFloorItemApi( organization, selectedFloorItem.userData.modelUuid, - newName + newName, + projectId ); console.log('selectedFloorItem: ', selectedFloorItem.userData.modelUuid); selectedFloorItem.userData.modelName = newName; diff --git a/app/src/components/ui/list/List.tsx b/app/src/components/ui/list/List.tsx index 22653ff..9a39054 100644 --- a/app/src/components/ui/list/List.tsx +++ b/app/src/components/ui/list/List.tsx @@ -122,7 +122,7 @@ const List: React.FC = ({ items = [], remove }) => { zoneUuid: selectedZone.zoneUuid, zoneName: newName, }; - const response = await zoneCameraUpdate(zonesdata, organization,projectId); + const response = await zoneCameraUpdate(zonesdata, organization, projectId); if (response.message === "zone updated") { setSelectedZone((prev) => ({ ...prev, zoneName: newName })); setZones((prevZones: any[]) => @@ -143,7 +143,8 @@ const List: React.FC = ({ items = [], remove }) => { let response = await setFloorItemApi( organization, zoneAssetId.id, - newName + newName, + projectId ); // console.log("response: ", response); diff --git a/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts b/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts index d9e67e9..b819062 100644 --- a/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts +++ b/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts @@ -3,6 +3,7 @@ export const setFloorItemApi = async ( organization: string, modelUuid?: string, modelName?: string, + projectId?: string, modelfileID?: string, position?: Object, rotation?: Object, @@ -14,6 +15,7 @@ export const setFloorItemApi = async ( organization, modelUuid, modelName, + projectId, position, rotation, modelfileID, -- 2.40.1 From 4a2f1b64e3b7517c041d7f733a92b64754cfef1d Mon Sep 17 00:00:00 2001 From: Poovizhi99 Date: Wed, 11 Jun 2025 11:46:58 +0530 Subject: [PATCH 15/17] refactor: Update user data structure in MainScene and clean up console logs in RenameTooltip and List components --- app/src/components/layout/scenes/MainScene.tsx | 9 +++++---- app/src/components/ui/features/RenameTooltip.tsx | 2 -- app/src/components/ui/list/List.tsx | 1 + 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/app/src/components/layout/scenes/MainScene.tsx b/app/src/components/layout/scenes/MainScene.tsx index 08ebb8a..7f398df 100644 --- a/app/src/components/layout/scenes/MainScene.tsx +++ b/app/src/components/layout/scenes/MainScene.tsx @@ -72,12 +72,13 @@ function MainScene() { newName, projectId ); - console.log('selectedFloorItem: ', selectedFloorItem.userData.modelUuid); - selectedFloorItem.userData.modelName = newName; + selectedFloorItem.userData = { + ...selectedFloorItem.userData, + modelName: newName + }; setSelectedFloorItem(selectedFloorItem); setIsRenameMode(false); - - setName(selectedFloorItem.userData.modelUuid, newName); + setName(selectedFloorItem.userData.modelUuid, response.modelName); } return ( diff --git a/app/src/components/ui/features/RenameTooltip.tsx b/app/src/components/ui/features/RenameTooltip.tsx index 0419071..87de122 100644 --- a/app/src/components/ui/features/RenameTooltip.tsx +++ b/app/src/components/ui/features/RenameTooltip.tsx @@ -12,7 +12,6 @@ type RenameTooltipProps = { }; const RenameTooltip: React.FC = ({ name, onSubmit }) => { - console.log('name: ', name); const [value, setValue] = useState(name); const { top, setTop } = useTopData(); @@ -20,7 +19,6 @@ const RenameTooltip: React.FC = ({ name, onSubmit }) => { const handleSubmit = (e: React.FormEvent) => { e.preventDefault(); - console.log('value.trim(): ', value.trim()); onSubmit(value.trim()); setTop(0); setLeft(0); diff --git a/app/src/components/ui/list/List.tsx b/app/src/components/ui/list/List.tsx index 9a39054..2ca44ac 100644 --- a/app/src/components/ui/list/List.tsx +++ b/app/src/components/ui/list/List.tsx @@ -147,6 +147,7 @@ const List: React.FC = ({ items = [], remove }) => { projectId ); // console.log("response: ", response); + console.log(' zoneAssetId.id,: ', zoneAssetId.id,); setName(zoneAssetId.id, response.modelName); } -- 2.40.1 From 280ec8a7565408d8b6861d4d7ff89529d50b082d Mon Sep 17 00:00:00 2001 From: Jerald-Golden-B Date: Wed, 11 Jun 2025 13:19:27 +0530 Subject: [PATCH 16/17] Refactor tool mode handling across simulation and builder modules - Removed the use of deleteTool and deletePointOrLine states, replacing them with a unified toolMode state. - Updated Point, Arrows, PointsCreator, TriggerConnector, and other components to utilize toolMode for determining delete actions. - Cleaned up unused imports and commented-out code related to deleteTool. - Enhanced event handling in selectionControls and trigger connections to respond to toolMode changes. - Adjusted color and interaction logic based on the current toolMode. --- app/src/app.tsx | 8 +- app/src/components/ui/Tools.tsx | 19 +- .../builder/asset/models/model/model.tsx | 22 +- app/src/modules/builder/builder.tsx | 31 +- app/src/modules/builder/csg/csg.tsx | 8 +- app/src/modules/builder/functions/draw.ts | 10 +- app/src/modules/builder/groups/floorGroup.tsx | 10 +- .../modules/builder/groups/floorPlanGroup.tsx | 29 +- .../modules/builder/groups/wallItemsGroup.tsx | 22 +- .../builder/groups/wallsAndWallItems.tsx | 8 +- app/src/modules/builder/groups/zoneGroup.tsx | 1289 ++++++++--------- app/src/modules/builder/point/point.tsx | 15 +- .../socket/socketResponses.dev.tsx | 5 - .../selectionControls/selectionControls.tsx | 7 +- .../simulation/events/arrows/arrows.tsx | 8 +- .../events/points/creator/pointsCreator.tsx | 43 +- .../triggerConnections/triggerConnector.tsx | 14 +- .../armInstance/roboticArmInstance.tsx | 18 +- .../simulation/simulator/simulator.tsx | 1 - .../triggerHandler/useTriggerHandler.ts | 1 + app/src/store/builder/store.ts | 16 +- .../utils/shortcutkeys/handleShortcutKeys.ts | 4 - 22 files changed, 735 insertions(+), 853 deletions(-) diff --git a/app/src/app.tsx b/app/src/app.tsx index 6d223be..b03d4df 100644 --- a/app/src/app.tsx +++ b/app/src/app.tsx @@ -1,4 +1,5 @@ -import React, { useEffect, useState } from "react"; +import React, { useEffect } from "react"; +import { Cache } from "three"; import { BrowserRouter as Router, Routes, Route } from "react-router-dom"; import Dashboard from "./pages/Dashboard"; import Project from "./pages/Project"; @@ -8,6 +9,11 @@ import { LoggerProvider } from "./components/ui/log/LoggerContext"; const App: React.FC = () => { + useEffect(() => { + Cache.clear(); + Cache.enabled = true; + }, []); + return ( diff --git a/app/src/components/ui/Tools.tsx b/app/src/components/ui/Tools.tsx index b36b00f..4deacab 100644 --- a/app/src/components/ui/Tools.tsx +++ b/app/src/components/ui/Tools.tsx @@ -22,8 +22,6 @@ import { useSelectedZoneStore } from "../../store/visualization/useZoneStore"; import { useActiveTool, useAddAction, - useDeleteTool, - useDeletePointOrLine, useRefTextUpdate, useSelectedWallItem, useSocketStore, @@ -32,7 +30,7 @@ import { useActiveSubTool, useShortcutStore, } from "../../store/builder/store"; -import {useToggleStore} from "../../store/useUIToggleStore"; +import { useToggleStore } from "../../store/useUIToggleStore"; import { use3DWidget, useFloatingWidget, @@ -72,8 +70,6 @@ const Tools: React.FC = () => { setActiveTool, setToolMode, setAddAction, - setDeleteTool, - setDeletePointOrLine, } = useStoreHooks(); const { setActiveSubTool, activeSubTool } = useActiveSubTool(); @@ -131,18 +127,14 @@ const Tools: React.FC = () => { const resetTools = () => { setToolMode(null); - setDeleteTool(false); setAddAction(null); - setDeletePointOrLine(false); setRefTextUpdate((prev) => prev - 1); }; const updateToolBehavior = (tool: string, is2D: boolean) => { switch (tool) { case "cursor": - if (toggleView) { - setToolMode("move"); - } + is2D ? setToolMode("move") : setToolMode("cursor"); break; case "draw-wall": is2D && setToolMode("Wall"); @@ -160,10 +152,10 @@ const Tools: React.FC = () => { setToolMode("MeasurementScale"); break; case "Add pillar": - if (!is2D) setAddAction("pillar"); + if (!is2D) setAddAction("Pillar"); break; case "delete": - is2D ? setDeletePointOrLine(true) : setDeleteTool(true); + is2D ? setToolMode('2D-Delete') : setToolMode('3D-Delete'); break; } }; @@ -175,7 +167,6 @@ const Tools: React.FC = () => { setToggleUI(toggleTo2D, toggleTo2D); if (toggleTo2D) { setSelectedWallItem(null); - setDeleteTool(false); setAddAction(null); } setActiveTool("cursor"); @@ -410,9 +401,7 @@ const useStoreHooks = () => { return { ...useActiveTool(), ...useToolMode(), - ...useDeleteTool(), ...useAddAction(), - ...useDeletePointOrLine(), ...useRefTextUpdate(), }; }; diff --git a/app/src/modules/builder/asset/models/model/model.tsx b/app/src/modules/builder/asset/models/model/model.tsx index f28c16a..5b6e53b 100644 --- a/app/src/modules/builder/asset/models/model/model.tsx +++ b/app/src/modules/builder/asset/models/model/model.tsx @@ -1,10 +1,10 @@ import * as THREE from 'three'; -import { useEffect, useRef, useState } from 'react'; +import { useCallback, useEffect, useRef, useState } from 'react'; import { retrieveGLTF, storeGLTF } from '../../../../../utils/indexDB/idbUtils'; import { GLTF, GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'; import { DRACOLoader } from 'three/examples/jsm/loaders/DRACOLoader'; import { ThreeEvent, useFrame, useThree } from '@react-three/fiber'; -import { useActiveTool, useDeletableFloorItem, useRenderDistance, useSelectedFloorItem, useSocketStore, useToggleView } from '../../../../../store/builder/store'; +import { useActiveTool, useDeletableFloorItem, useRenderDistance, useSelectedFloorItem, useSocketStore, useToggleView, useToolMode } from '../../../../../store/builder/store'; import { AssetBoundingBox } from '../../functions/assetBoundingBox'; import { CameraControls } from '@react-three/drei'; import { useAssetsStore } from '../../../../../store/builder/useAssetStore'; @@ -39,8 +39,13 @@ function Model({ asset }: { readonly asset: Asset }) { const [gltfScene, setGltfScene] = useState(null); const [boundingBox, setBoundingBox] = useState(null); const groupRef = useRef(null); + const { toolMode } = useToolMode(); const { projectId } = useParams(); + useEffect(() => { + setDeletableFloorItem(null); + }, [activeModule, toolMode]) + useEffect(() => { const loader = new GLTFLoader(); const dracoLoader = new DRACOLoader(); @@ -191,21 +196,21 @@ function Model({ asset }: { readonly asset: Asset }) { } } - const handlePointerOver = (asset: Asset) => { - if (activeTool === "delete") { + const handlePointerOver = useCallback((asset: Asset) => { + if (activeTool === "delete" && activeModule === 'builder') { if (deletableFloorItem && deletableFloorItem.uuid === asset.modelUuid) { return; } else { setDeletableFloorItem(groupRef.current); } } - } + }, [activeTool, activeModule, deletableFloorItem]); - const handlePointerOut = (asset: Asset) => { + const handlePointerOut = useCallback((asset: Asset) => { if (activeTool === "delete" && deletableFloorItem && deletableFloorItem.uuid === asset.modelUuid) { setDeletableFloorItem(null); } - } + }, [activeTool, deletableFloorItem]); const handleContextMenu = (asset: Asset, evt: ThreeEvent) => { if (activeTool === "cursor" && subModule === 'simulations') { @@ -247,6 +252,7 @@ function Model({ asset }: { readonly asset: Asset }) { return ( { + onPointerEnter={(e) => { if (!toggleView) { e.stopPropagation(); handlePointerOver(asset); diff --git a/app/src/modules/builder/builder.tsx b/app/src/modules/builder/builder.tsx index 6a5093f..1401267 100644 --- a/app/src/modules/builder/builder.tsx +++ b/app/src/modules/builder/builder.tsx @@ -13,7 +13,6 @@ import ReferenceDistanceText from "./geomentries/lines/distanceText/referenceDis import { useToggleView, - useDeletePointOrLine, useActiveLayer, useWallVisibility, useRoofVisibility, @@ -58,18 +57,10 @@ export default function Builder() { const csg = useRef(); // Reference for CSG object, used for 3D modeling. const CSGGroup = useRef() as Types.RefMesh; // Reference to a group of CSG objects. const scene = useRef() as Types.RefScene; // Reference to the scene. - const camera = useRef() as Types.RefCamera; // Reference to the camera object. - const controls = useRef(); // Reference to the controls object. - const raycaster = useRef() as Types.RefRaycaster; // Reference for raycaster used for detecting objects being pointed at in the scene. const dragPointControls = useRef() as Types.RefDragControl; // Reference for drag point controls, an array for drag control. // Assigning the scene and camera from the Three.js state to the references. - scene.current = state.scene; - camera.current = state.camera; - controls.current = state.controls; - raycaster.current = state.raycaster; - const plane = useRef(null); // Reference for a plane object for raycaster reference. const grid = useRef() as any; // Reference for a grid object for raycaster reference. const snappedPoint = useRef() as Types.RefVector3; // Reference for storing a snapped point at the (end = isSnapped) and (start = ispreSnapped) of the line. @@ -78,8 +69,6 @@ export default function Builder() { const isAngleSnapped = useRef(false) as Types.RefBoolean; // Boolean to indicate if angle snapping is active. const isSnappedUUID = useRef() as Types.RefString; // UUID reference to identify the snapped point. const ispreSnapped = useRef(false) as Types.RefBoolean; // Boolean reference to indicate if an object is snapped at the (start). - const tempLoader = useRef() as Types.RefMesh; // Reference for a temporary loader for the floor items. - const isTempLoader = useRef() as Types.RefBoolean; // Reference to check if a temporary loader is active. const Tube = useRef() as Types.RefTubeGeometry; // Reference for tubes used for reference line creation and updation. const line = useRef([]) as Types.RefLine; // Reference for line which stores the current line that is being drawn. const lines = useRef([]) as Types.RefLines; // Reference for lines which stores all the lines that are ever drawn. @@ -88,13 +77,10 @@ export default function Builder() { const ReferenceLineMesh = useRef() as Types.RefMesh; // Reference for storing the mesh of the reference line for moving it during draw. const LineCreated = useRef(false) as Types.RefBoolean; // Boolean to track whether the reference line is created or not. const referencePole = useRef() as Types.RefMesh; // Reference for a pole that is used as the reference for the user to show where it is placed. - const itemsGroup = useRef() as Types.RefGroup; // Reference to the THREE.Group that has the floor items (Gltf). const floorGroup = useRef() as Types.RefGroup; // Reference to the THREE.Group that has the roofs and the floors. const floorPlanGroup = useRef() as Types.RefGroup; // Reference for a THREE.Group that has the lines group and the points group. const floorPlanGroupLine = useRef() as Types.RefGroup; // Reference for a THREE.Group that has the lines that are drawn. const floorPlanGroupPoint = useRef() as Types.RefGroup; // Reference for a THREE.Group that has the points that are created. - const floorGroupAisle = useRef() as Types.RefGroup; - const zoneGroup = useRef() as Types.RefGroup; const currentLayerPoint = useRef([]) as Types.RefMeshArray; // Reference for points that re in the current layer used to update the points in drag controls. const hoveredDeletablePoint = useRef() as Types.RefMesh; // Reference for the currently hovered point that can be deleted. const hoveredDeletableLine = useRef() as Types.RefMesh; // Reference for the currently hovered line that can be deleted. @@ -108,7 +94,6 @@ export default function Builder() { const { activeLayer } = useActiveLayer(); // State that changes based on which layer the user chooses in Layers.jsx. const { toggleView } = useToggleView(); // State for toggling between 2D and 3D. const { toolMode, setToolMode } = useToolMode(); - const { setDeletePointOrLine } = useDeletePointOrLine(); const { setRoofVisibility } = useRoofVisibility(); const { setWallVisibility } = useWallVisibility(); const { setShadows } = useShadows(); @@ -141,19 +126,13 @@ export default function Builder() { ); } else { setHoveredPoint(null); - setToolMode(null); - setDeletePointOrLine(false); + setToolMode('cursor'); loadWalls(lines, setWalls); setUpdateScene(true); line.current = []; } }, [toggleView]); - useEffect(() => { - THREE.Cache.clear(); - THREE.Cache.enabled = true; - }, []); - useEffect(() => { const email = localStorage.getItem("email"); const organization = email!.split("@")[1].split(".")[0]; @@ -180,12 +159,10 @@ export default function Builder() { plane, cursorPosition, floorPlanGroupPoint, - floorPlanGroupLine, snappedPoint, isSnapped, isSnappedUUID, line, - lines, ispreSnapped, floorPlanGroup, ReferenceLineMesh, @@ -219,16 +196,11 @@ export default function Builder() { floorPlanGroup={floorPlanGroup} lines={lines} floorGroup={floorGroup} - floorGroupAisle={floorGroupAisle} scene={scene} onlyFloorlines={onlyFloorlines} - itemsGroup={itemsGroup} - isTempLoader={isTempLoader} - tempLoader={tempLoader} currentLayerPoint={currentLayerPoint} floorPlanGroupPoint={floorPlanGroupPoint} floorPlanGroupLine={floorPlanGroupLine} - zoneGroup={zoneGroup} dragPointControls={dragPointControls} /> @@ -290,6 +262,7 @@ export default function Builder() { + = (props) => { - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const modelRef = useRef(); const originalMaterials = useRef>(new Map()); const handleHover = (hovered: boolean, object: THREE.Mesh | null) => { - if (modelRef.current && deleteTool) { + if (modelRef.current && toolMode === "3D-Delete") { modelRef.current.traverse((child) => { if (child instanceof THREE.Mesh) { if (!originalMaterials.current.has(child)) { originalMaterials.current.set(child, child.material); } child.material = child.material.clone(); - child.material.color.set(hovered && deleteTool ? 0xff0000 : (originalMaterials.current.get(child) as any).color); + child.material.color.set(hovered && toolMode === "3D-Delete" ? 0xff0000 : (originalMaterials.current.get(child) as any).color); } }); } diff --git a/app/src/modules/builder/functions/draw.ts b/app/src/modules/builder/functions/draw.ts index 0172707..425fbbb 100644 --- a/app/src/modules/builder/functions/draw.ts +++ b/app/src/modules/builder/functions/draw.ts @@ -7,12 +7,10 @@ async function Draw( plane: Types.RefMesh, cursorPosition: Types.Vector3, floorPlanGroupPoint: Types.RefGroup, - floorPlanGroupLine: Types.RefGroup, snappedPoint: Types.RefVector3, isSnapped: Types.RefBoolean, isSnappedUUID: Types.RefString, line: Types.RefLine, - lines: Types.RefLines, ispreSnapped: Types.RefBoolean, floorPlanGroup: Types.RefGroup, ReferenceLineMesh: Types.RefMesh, @@ -29,7 +27,7 @@ async function Draw( if (!plane.current) return; const intersects = state.raycaster.intersectObject(plane.current, true); - if (intersects.length > 0 && (toolMode === "Wall" || toolMode === "Aisle" || toolMode === "Floor")) { + if (intersects.length > 0 && (toolMode === "Wall" || toolMode === "Floor")) { const intersectionPoint = intersects[0].point; cursorPosition.copy(intersectionPoint); const snapThreshold = 1; @@ -40,8 +38,7 @@ async function Draw( const canSnap = ((toolMode === "Wall") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) || - ((toolMode === "Floor") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) || - ((toolMode === "Aisle") && pointType === CONSTANTS.lineConfig.aisleName);; + ((toolMode === "Floor") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) if (canSnap && cursorPosition.distanceTo(point.position) < snapThreshold + 0.5 && point.visible) { cursorPosition.copy(point.position); @@ -60,8 +57,7 @@ async function Draw( let canSnap = ((toolMode === "Wall") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) || - ((toolMode === "Floor") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) || - ((toolMode === "Aisle") && pointType === CONSTANTS.lineConfig.aisleName); + ((toolMode === "Floor") && (pointType === CONSTANTS.lineConfig.wallName || pointType === CONSTANTS.lineConfig.floorName)) if (canSnap && cursorPosition.distanceTo(point.position) < snapThreshold && point.visible) { cursorPosition.copy(point.position); diff --git a/app/src/modules/builder/groups/floorGroup.tsx b/app/src/modules/builder/groups/floorGroup.tsx index 2cf5586..8835ede 100644 --- a/app/src/modules/builder/groups/floorGroup.tsx +++ b/app/src/modules/builder/groups/floorGroup.tsx @@ -1,12 +1,12 @@ import { useFrame, useThree } from "@react-three/fiber"; import { useAddAction, - useDeleteTool, useRoofVisibility, useToggleView, useWallVisibility, useUpdateScene, useRenameModeStore, + useToolMode, } from "../../../store/builder/store"; import hideRoof from "../geomentries/roofs/hideRoof"; import hideWalls from "../geomentries/walls/hideWalls"; @@ -30,7 +30,7 @@ const FloorGroup = ({ const { toggleView } = useToggleView(); const { scene, camera, raycaster, gl } = useThree(); const { addAction } = useAddAction(); - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const { updateScene, setUpdateScene } = useUpdateScene(); const { setTop } = useTopData(); const { setLeft } = useLeftData(); @@ -75,7 +75,7 @@ const FloorGroup = ({ if (addAction === "pillar") { addPillar(referencePole, floorGroup); } - if (deleteTool) { + if (toolMode === '3D-Delete') { DeletePillar(hoveredDeletablePillar, floorGroup); } } @@ -105,7 +105,7 @@ const FloorGroup = ({ canvasElement.removeEventListener("mouseup", onMouseUp); canvasElement.removeEventListener("mousemove", onMouseMove); }; - }, [deleteTool, addAction, isRenameMode]); + }, [toolMode, addAction, isRenameMode]); useFrame(() => { hideRoof(roofVisibility, floorGroup, camera); @@ -114,7 +114,7 @@ const FloorGroup = ({ if (addAction === "pillar") { addAndUpdateReferencePillar(raycaster, floorGroup, referencePole); } - if (deleteTool) { + if (toolMode === '3D-Delete') { DeletableHoveredPillar(state, floorGroup, hoveredDeletablePillar); } }); diff --git a/app/src/modules/builder/groups/floorPlanGroup.tsx b/app/src/modules/builder/groups/floorPlanGroup.tsx index d9f01c3..23128e5 100644 --- a/app/src/modules/builder/groups/floorPlanGroup.tsx +++ b/app/src/modules/builder/groups/floorPlanGroup.tsx @@ -1,6 +1,6 @@ import { useEffect } from "react"; import * as Types from '../../../types/world/worldTypes'; -import { useActiveLayer, useDeletedLines, useDeletePointOrLine, useToolMode, useNewLines, useRemovedLayer, useSocketStore, useToggleView, useUpdateScene } from "../../../store/builder/store"; +import { useActiveLayer, useDeletedLines, useToolMode, useNewLines, useRemovedLayer, useSocketStore, useToggleView, useUpdateScene } from "../../../store/builder/store"; import Layer2DVisibility from "../geomentries/layers/layer2DVisibility"; import { useFrame, useThree } from "@react-three/fiber"; import DeletableLineorPoint from "../functions/deletableLineOrPoint"; @@ -23,8 +23,7 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin const { camera, gl, raycaster, controls } = state; const { activeLayer } = useActiveLayer(); const { toggleView } = useToggleView(); - const { deletePointOrLine, setDeletePointOrLine } = useDeletePointOrLine(); - const { toolMode, setToolMode } = useToolMode(); + const { toolMode } = useToolMode(); const { removedLayer, setRemovedLayer } = useRemovedLayer(); const { setUpdateScene } = useUpdateScene(); const { setNewLines } = useNewLines(); @@ -32,7 +31,6 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin const { socket } = useSocketStore(); const { projectId } = useParams(); - useEffect(() => { if (toolMode === 'move') { addDragControl(dragPointControls, currentLayerPoint, state, floorPlanGroupPoint, floorPlanGroupLine, lines, onlyFloorlines, socket, projectId); @@ -74,17 +72,12 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin }, [toggleView]); useEffect(() => { - if (toolMode === "Wall" || toolMode === "Floor") { - setDeletePointOrLine(false); - } else { - removeSoloPoint(line, floorPlanGroupLine, floorPlanGroupPoint); - removeReferenceLine(floorPlanGroup, ReferenceLineMesh, LineCreated, line); - } + removeSoloPoint(line, floorPlanGroupLine, floorPlanGroupPoint); + removeReferenceLine(floorPlanGroup, ReferenceLineMesh, LineCreated, line); }, [toolMode]); useEffect(() => { if (toolMode === 'move' && toggleView) { - setDeletePointOrLine(false); if (dragPointControls.current) { dragPointControls.current.enabled = true; } @@ -95,12 +88,6 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin } }, [toolMode, toggleView, state]); - useEffect(() => { - if (deletePointOrLine) { - setToolMode(null); - } - }, [deletePointOrLine]); - useEffect(() => { Layer2DVisibility(activeLayer, floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoint, currentLayerPoint, dragPointControls); }, [activeLayer]); @@ -151,7 +138,7 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin const onMouseClick = (evt: any) => { if (!plane.current || drag) return; - if (deletePointOrLine) { + if (toolMode === "2D-Delete") { if (hoveredDeletablePoint.current !== null) { deletePoint(hoveredDeletablePoint, onlyFloorlines, floorPlanGroupPoint, floorPlanGroupLine, lines, setDeletedLines, socket, projectId); } @@ -169,7 +156,7 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin } } - if (deletePointOrLine || toolMode === "Wall" || toolMode === "Floor") { + if (toolMode === "2D-Delete" || toolMode === "Wall" || toolMode === "Floor") { canvasElement.addEventListener("mousedown", onMouseDown); canvasElement.addEventListener("mouseup", onMouseUp); canvasElement.addEventListener("mousemove", onMouseMove); @@ -184,11 +171,11 @@ const FloorPlanGroup = ({ floorPlanGroup, floorPlanGroupLine, floorPlanGroupPoin canvasElement.removeEventListener("click", onMouseClick); canvasElement.removeEventListener("contextmenu", onContextMenu); }; - }, [deletePointOrLine, toolMode, activeLayer]) + }, [toolMode, activeLayer]) useFrame(() => { - if (deletePointOrLine) { + if (toolMode === '2D-Delete') { DeletableLineorPoint(state, plane, floorPlanGroupLine, floorPlanGroupPoint, hoveredDeletableLine, hoveredDeletablePoint); } }) diff --git a/app/src/modules/builder/groups/wallItemsGroup.tsx b/app/src/modules/builder/groups/wallItemsGroup.tsx index 8f8cdcb..d4e1efa 100644 --- a/app/src/modules/builder/groups/wallItemsGroup.tsx +++ b/app/src/modules/builder/groups/wallItemsGroup.tsx @@ -1,13 +1,12 @@ import { useEffect } from "react"; import { - useDeleteTool, - useDeletePointOrLine, useObjectPosition, useObjectRotation, useSelectedWallItem, useSocketStore, useWallItems, useSelectedItem, + useToolMode, } from "../../../store/builder/store"; import { Csg } from "../csg/csg"; import * as Types from "../../../types/world/worldTypes"; @@ -31,11 +30,10 @@ const WallItemsGroup = ({ const state = useThree(); const { socket } = useSocketStore(); const { pointer, camera, raycaster } = state; - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const { wallItems, setWallItems } = useWallItems(); const { setObjectPosition } = useObjectPosition(); const { setObjectRotation } = useObjectRotation(); - const { deletePointOrLine } = useDeletePointOrLine(); const { setSelectedWallItem } = useSelectedWallItem(); const { activeModule } = useModuleStore(); const { selectedItem } = useSelectedItem(); @@ -43,7 +41,7 @@ const WallItemsGroup = ({ useEffect(() => { // Load Wall Items from the backend - loadInitialWallItems(setWallItems,projectId); + loadInitialWallItems(setWallItems, projectId); }, []); ////////// Update the Position value changes in the selected item ////////// @@ -51,7 +49,7 @@ const WallItemsGroup = ({ useEffect(() => { const canvasElement = state.gl.domElement; function handlePointerMove(e: any) { - if (selectedItemsIndex !== null && !deletePointOrLine && e.buttons === 1) { + if (selectedItemsIndex !== null && toolMode === 'cursor' && e.buttons === 1) { const Raycaster = state.raycaster; const intersects = Raycaster.intersectObjects(CSGGroup.current?.children[0].children!, true); const Object = intersects.find((child) => child.object.name.includes("WallRaycastReference")); @@ -123,7 +121,7 @@ const WallItemsGroup = ({ setTimeout(async () => { const email = localStorage.getItem("email"); - const organization = email!.split("@")[1].split(".")[0]; + const organization = email!.split("@")[1].split(".")[0]; const userId = localStorage.getItem("userId"); //REST @@ -191,12 +189,12 @@ const WallItemsGroup = ({ const onMouseUp = (evt: any) => { if (evt.button === 0) { isLeftMouseDown = false; - if (!drag && deleteTool && activeModule === "builder") { + if (!drag && toolMode === '3D-Delete' && activeModule === "builder") { DeleteWallItems( hoveredDeletableWallItem, setWallItems, wallItems, - socket,projectId + socket, projectId ); } } @@ -248,10 +246,10 @@ const WallItemsGroup = ({ canvasElement.removeEventListener("drop", onDrop); canvasElement.removeEventListener("dragover", onDragOver); }; - }, [deleteTool, wallItems, selectedItem, camera]); + }, [toolMode, wallItems, selectedItem, camera]); useEffect(() => { - if (deleteTool && activeModule === "builder") { + if (toolMode && activeModule === "builder") { handleMeshMissed( currentWallItem, setSelectedWallItem, @@ -260,7 +258,7 @@ const WallItemsGroup = ({ setSelectedWallItem(null); setSelectedItemsIndex(null); } - }, [deleteTool]); + }, [toolMode]); return ( <> diff --git a/app/src/modules/builder/groups/wallsAndWallItems.tsx b/app/src/modules/builder/groups/wallsAndWallItems.tsx index 82acd99..d4d52ec 100644 --- a/app/src/modules/builder/groups/wallsAndWallItems.tsx +++ b/app/src/modules/builder/groups/wallsAndWallItems.tsx @@ -1,8 +1,8 @@ import { Geometry } from "@react-three/csg"; import { - useDeleteTool, useSelectedWallItem, useToggleView, + useToolMode, useWallItems, useWalls, } from "../../../store/builder/store"; @@ -23,7 +23,7 @@ const WallsAndWallItems = ({ const { walls } = useWalls(); const { wallItems } = useWallItems(); const { toggleView } = useToggleView(); - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const { setSelectedWallItem } = useSelectedWallItem(); return ( @@ -34,7 +34,7 @@ const WallsAndWallItems = ({ receiveShadow visible={!toggleView} onClick={(event) => { - if (!deleteTool) { + if (toolMode === "cursor") { handleMeshDown( event, currentWallItem, @@ -46,7 +46,7 @@ const WallsAndWallItems = ({ } }} onPointerMissed={() => { - if (!deleteTool) { + if (toolMode === "cursor") { handleMeshMissed( currentWallItem, setSelectedWallItem, diff --git a/app/src/modules/builder/groups/zoneGroup.tsx b/app/src/modules/builder/groups/zoneGroup.tsx index 19d3d31..55a5821 100644 --- a/app/src/modules/builder/groups/zoneGroup.tsx +++ b/app/src/modules/builder/groups/zoneGroup.tsx @@ -3,15 +3,13 @@ import { Html, Line, Sphere } from "@react-three/drei"; import { useThree, useFrame } from "@react-three/fiber"; import * as THREE from "three"; import { - useActiveLayer, - useDeleteTool, - useDeletePointOrLine, - useSocketStore, - useToggleView, - useToolMode, - useRemovedLayer, - useZones, - useZonePoints, + useActiveLayer, + useSocketStore, + useToggleView, + useToolMode, + useRemovedLayer, + useZones, + useZonePoints, } from "../../../store/builder/store"; import { getZonesApi } from "../../../services/factoryBuilder/zones/getZonesApi"; @@ -22,43 +20,41 @@ import { useSelectedZoneStore } from "../../../store/visualization/useZoneStore" import { useParams } from "react-router-dom"; const ZoneGroup: React.FC = () => { - const { camera, pointer, gl, raycaster, scene, controls } = useThree(); - const [startPoint, setStartPoint] = useState(null); - const [endPoint, setEndPoint] = useState(null); - const { zones, setZones } = useZones(); - const { zonePoints, setZonePoints } = useZonePoints(); - const [isDragging, setIsDragging] = useState(false); - const { selectedZone } = useSelectedZoneStore(); - const [draggedSphere, setDraggedSphere] = useState( - null - ); - const plane = useMemo( - () => new THREE.Plane(new THREE.Vector3(0, 1, 0), 0), - [] - ); - const { toggleView } = useToggleView(); - const { deletePointOrLine, setDeletePointOrLine } = useDeletePointOrLine(); - const { removedLayer, setRemovedLayer } = useRemovedLayer(); - const { toolMode } = useToolMode(); - const { setDeleteTool } = useDeleteTool(); - const { activeLayer } = useActiveLayer(); - const { socket } = useSocketStore(); - const { projectId } = useParams(); + const { camera, pointer, gl, raycaster, scene, controls } = useThree(); + const [startPoint, setStartPoint] = useState(null); + const [endPoint, setEndPoint] = useState(null); + const { zones, setZones } = useZones(); + const { zonePoints, setZonePoints } = useZonePoints(); + const [isDragging, setIsDragging] = useState(false); + const { selectedZone } = useSelectedZoneStore(); + const [draggedSphere, setDraggedSphere] = useState( + null + ); + const plane = useMemo( + () => new THREE.Plane(new THREE.Vector3(0, 1, 0), 0), + [] + ); + const { toggleView } = useToggleView(); + const { removedLayer, setRemovedLayer } = useRemovedLayer(); + const { toolMode } = useToolMode(); + const { activeLayer } = useActiveLayer(); + const { socket } = useSocketStore(); + const { projectId } = useParams(); - const groupsRef = useRef(); + const groupsRef = useRef(); - const zoneMaterial = useMemo( - () => - new THREE.ShaderMaterial({ - side: THREE.DoubleSide, - vertexShader: ` + const zoneMaterial = useMemo( + () => + new THREE.ShaderMaterial({ + side: THREE.DoubleSide, + vertexShader: ` varying vec2 vUv; void main(){ gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0); vUv = uv; } `, - fragmentShader: ` + fragmentShader: ` varying vec2 vUv; uniform vec3 uOuterColor; void main(){ @@ -66,677 +62,606 @@ const ZoneGroup: React.FC = () => { gl_FragColor = vec4(uOuterColor, alpha); } `, - uniforms: { - uOuterColor: { value: new THREE.Color(CONSTANTS.zoneConfig.color) }, - }, - transparent: true, - depthWrite: false, - }), - [] - ); - - useEffect(() => { - const fetchZones = async () => { - const email = localStorage.getItem("email"); - if (!email) return; - - const organization = email.split("@")[1].split(".")[0]; - const data = await getZonesApi(organization, projectId); - // console.log('data: ', data); - - if (data.length > 0) { - const fetchedZones = data.map((zone: any) => ({ - zoneUuid: zone.zoneUuid, - zoneName: zone.zoneName, - points: zone.points, - viewPortCenter: zone.viewPortCenter, - viewPortposition: zone.viewPortposition, - layer: zone.layer, - })); - - setZones(fetchedZones); - - const fetchedPoints = data.flatMap((zone: any) => - zone.points - .slice(0, 4) - .map( - (point: [number, number, number]) => new THREE.Vector3(...point) - ) - ); - - setZonePoints(fetchedPoints); - } - }; - - fetchZones(); - }, []); - - useEffect(() => { - localStorage.setItem("zones", JSON.stringify(zones)); - }, [zones]); - - useEffect(() => { - if (removedLayer) { - const updatedZones = zones.filter( - (zone: any) => zone.layer !== removedLayer - ); - setZones(updatedZones); - - const updatedzonePoints = zonePoints.filter((_: any, index: any) => { - const zoneIndex = Math.floor(index / 4); - return zones[zoneIndex]?.layer !== removedLayer; - }); - setZonePoints(updatedzonePoints); - - zones - .filter((zone: any) => zone.layer === removedLayer) - .forEach((zone: any) => { - deleteZoneFromBackend(zone.zoneUuid); - }); - - setRemovedLayer(null); - } - }, [removedLayer]); - - useEffect(() => { - if (toolMode !== "Zone") { - setStartPoint(null); - setEndPoint(null); - } else { - setDeletePointOrLine(false); - setDeleteTool(false); - } - if (!toggleView) { - setStartPoint(null); - setEndPoint(null); - } - }, [toolMode, toggleView]); - - // eslint-disable-next-line react-hooks/exhaustive-deps - const addZoneToBackend = async (zone: { - zoneUuid: string; - zoneName: string; - points: [number, number, number][]; - layer: string; - }) => { - console.log('zoneUuid: ', zone); - const email = localStorage.getItem("email"); - const userId = localStorage.getItem("userId"); - const organization = email!.split("@")[1].split(".")[0]; - - const calculateCenter = (points: number[][]) => { - if (!points || points.length === 0) return null; - - let sumX = 0, - sumY = 0, - sumZ = 0; - const numPoints = points.length; - - points.forEach(([x, y, z]) => { - sumX += x; - sumY += y; - sumZ += z; - }); - - return [sumX / numPoints, sumY / numPoints, sumZ / numPoints] as [ - number, - number, - number - ]; - }; - - const target: [number, number, number] | null = calculateCenter( - zone.points + uniforms: { + uOuterColor: { value: new THREE.Color(CONSTANTS.zoneConfig.color) }, + }, + transparent: true, + depthWrite: false, + }), + [] ); - if (!target || zone.points.length < 4) return; - const position = [target[0], 10, target[2]]; - const input = { - userId: userId, - projectId, - organization: organization, - zoneData: { - zoneName: zone.zoneName, - zoneUuid: zone.zoneUuid, - points: zone.points, - viewPortCenter: target, - viewPortposition: position, - layer: zone.layer, - }, - }; + useEffect(() => { + const fetchZones = async () => { + const email = localStorage.getItem("email"); + if (!email) return; - socket.emit("v1:zone:set", input); - }; + const organization = email.split("@")[1].split(".")[0]; + const data = await getZonesApi(organization, projectId); + // console.log('data: ', data); - // eslint-disable-next-line react-hooks/exhaustive-deps - const updateZoneToBackend = async (zone: { - zoneUuid: string; - zoneName: string; - points: [number, number, number][]; - layer: string; - }) => { - const email = localStorage.getItem("email"); - const userId = localStorage.getItem("userId"); - const organization = email!.split("@")[1].split(".")[0]; + if (data.length > 0) { + const fetchedZones = data.map((zone: any) => ({ + zoneUuid: zone.zoneUuid, + zoneName: zone.zoneName, + points: zone.points, + viewPortCenter: zone.viewPortCenter, + viewPortposition: zone.viewPortposition, + layer: zone.layer, + })); - const calculateCenter = (points: number[][]) => { - if (!points || points.length === 0) return null; + setZones(fetchedZones); - let sumX = 0, - sumY = 0, - sumZ = 0; - const numPoints = points.length; + const fetchedPoints = data.flatMap((zone: any) => + zone.points.slice(0, 4).map((point: [number, number, number]) => new THREE.Vector3(...point)) + ); - points.forEach(([x, y, z]) => { - sumX += x; - sumY += y; - sumZ += z; - }); - - return [sumX / numPoints, sumY / numPoints, sumZ / numPoints] as [ - number, - number, - number - ]; - }; - - const target: [number, number, number] | null = calculateCenter( - zone.points - ); - if (!target || zone.points.length < 4) return; - const position = [target[0], 10, target[2]]; - - const input = { - userId: userId, - projectId, - organization: organization, - zoneData: { - zoneName: zone.zoneName, - zoneUuid: zone.zoneUuid, - points: zone.points, - viewPortCenter: target, - viewPortposition: position, - layer: zone.layer, - }, - }; - - socket.emit("v1:zone:set", input); - }; - - const deleteZoneFromBackend = async (zoneUuid: string) => { - const email = localStorage.getItem("email"); - const userId = localStorage.getItem("userId"); - const organization = email!.split("@")[1].split(".")[0]; - - const input = { - userId: userId, - projectId, - organization: organization, - zoneUuid: zoneUuid, - }; - - socket.emit("v1:zone:delete", input); - }; - - // eslint-disable-next-line react-hooks/exhaustive-deps - const handleDeleteZone = (zoneUuid: string) => { - const updatedZones = zones.filter((zone: any) => zone.zoneUuid !== zoneUuid); - setZones(updatedZones); - - const zoneIndex = zones.findIndex((zone: any) => zone.zoneUuid === zoneUuid); - if (zoneIndex !== -1) { - const zonePointsToRemove = zonePoints.slice( - zoneIndex * 4, - zoneIndex * 4 + 4 - ); - zonePointsToRemove.forEach((point: any) => - groupsRef.current.remove(point) - ); - const updatedzonePoints = zonePoints.filter( - (_: any, index: any) => - index < zoneIndex * 4 || index >= zoneIndex * 4 + 4 - ); - setZonePoints(updatedzonePoints); - } - deleteZoneFromBackend(zoneUuid); - }; - - useEffect(() => { - if (!camera || !toggleView) return; - const canvasElement = gl.domElement; - - let drag = false; - let isLeftMouseDown = false; - - const onMouseDown = (evt: any) => { - if (evt.button === 0) { - isLeftMouseDown = true; - drag = false; - - raycaster.setFromCamera(pointer, camera); - const intersects = raycaster.intersectObjects( - groupsRef.current.children, - true - ); - - if (intersects.length > 0 && toolMode === "move") { - const clickedObject = intersects[0].object; - const sphereIndex = zonePoints.findIndex((point: any) => - point.equals(clickedObject.position) - ); - if (sphereIndex !== -1) { - (controls as any).enabled = false; - setDraggedSphere(zonePoints[sphereIndex]); - setIsDragging(true); - } - } - } - }; - - const onMouseUp = (evt: any) => { - if (evt.button === 0 && !drag && !isDragging && !deletePointOrLine) { - isLeftMouseDown = false; - - if (!startPoint && toolMode !== "move") { - raycaster.setFromCamera(pointer, camera); - const intersectionPoint = new THREE.Vector3(); - const point = raycaster.ray.intersectPlane(plane, intersectionPoint); - if (point) { - setStartPoint(point); - setEndPoint(null); - } - } else if (startPoint && toolMode !== "move") { - raycaster.setFromCamera(pointer, camera); - const intersectionPoint = new THREE.Vector3(); - const point = raycaster.ray.intersectPlane(plane, intersectionPoint); - if (!point) return; - - const points = [ - [startPoint.x, 0.15, startPoint.z], - [point.x, 0.15, startPoint.z], - [point.x, 0.15, point.z], - [startPoint.x, 0.15, point.z], - [startPoint.x, 0.15, startPoint.z], - ] as [number, number, number][]; - - const zoneName = `Zone ${zones.length + 1}`; - const zoneUuid = THREE.MathUtils.generateUUID(); - const newZone = { - zoneUuid, - zoneName, - points: points, - layer: activeLayer, - }; - - const newZones = [...zones, newZone]; - - setZones(newZones); - - const newzonePoints = [ - new THREE.Vector3(startPoint.x, 0.15, startPoint.z), - new THREE.Vector3(point.x, 0.15, startPoint.z), - new THREE.Vector3(point.x, 0.15, point.z), - new THREE.Vector3(startPoint.x, 0.15, point.z), - ]; - - const updatedZonePoints = [...zonePoints, ...newzonePoints]; - setZonePoints(updatedZonePoints); - - addZoneToBackend(newZone); - setStartPoint(null); - setEndPoint(null); - } - } else if ( - evt.button === 0 && - !drag && - !isDragging && - deletePointOrLine - ) { - raycaster.setFromCamera(pointer, camera); - const intersects = raycaster.intersectObjects( - groupsRef.current.children, - true - ); - - if (intersects.length > 0) { - const clickedObject = intersects[0].object; - - const sphereIndex = zonePoints.findIndex((point: any) => - point.equals(clickedObject.position) - ); - if (sphereIndex !== -1) { - const zoneIndex = Math.floor(sphereIndex / 4); - const zoneUuid = zones[zoneIndex].zoneUuid; - handleDeleteZone(zoneUuid); - return; - } - } - } - - if (evt.button === 0) { - if (isDragging && draggedSphere) { - setIsDragging(false); - setDraggedSphere(null); - - const sphereIndex = zonePoints.findIndex( - (point: any) => point === draggedSphere - ); - if (sphereIndex !== -1) { - const zoneIndex = Math.floor(sphereIndex / 4); - - if (zoneIndex !== -1 && zones[zoneIndex]) { - updateZoneToBackend(zones[zoneIndex]); + setZonePoints(fetchedPoints); } - } + }; + + fetchZones(); + }, []); + + useEffect(() => { + localStorage.setItem("zones", JSON.stringify(zones)); + }, [zones]); + + useEffect(() => { + if (removedLayer) { + const updatedZones = zones.filter((zone: any) => zone.layer !== removedLayer); + setZones(updatedZones); + + const updatedzonePoints = zonePoints.filter((_: any, index: any) => { + const zoneIndex = Math.floor(index / 4); + return zones[zoneIndex]?.layer !== removedLayer; + }); + setZonePoints(updatedzonePoints); + + zones.filter((zone: any) => zone.layer === removedLayer).forEach((zone: any) => { deleteZoneFromBackend(zone.zoneUuid); }); + + setRemovedLayer(null); } - } + }, [removedLayer]); + + useEffect(() => { + if (toolMode !== "Zone") { + setStartPoint(null); + setEndPoint(null); + } + if (!toggleView) { + setStartPoint(null); + setEndPoint(null); + } + }, [toolMode, toggleView]); + + // eslint-disable-next-line react-hooks/exhaustive-deps + const addZoneToBackend = async (zone: { + zoneUuid: string; + zoneName: string; + points: [number, number, number][]; + layer: string; + }) => { + const email = localStorage.getItem("email"); + const userId = localStorage.getItem("userId"); + const organization = email!.split("@")[1].split(".")[0]; + + const calculateCenter = (points: number[][]) => { + if (!points || points.length === 0) return null; + + let sumX = 0, sumY = 0, sumZ = 0; + const numPoints = points.length; + + points.forEach(([x, y, z]) => { + sumX += x; + sumY += y; + sumZ += z; + }); + + return [sumX / numPoints, sumY / numPoints, sumZ / numPoints] as [ + number, + number, + number + ]; + }; + + const target: [number, number, number] | null = calculateCenter(zone.points); + if (!target || zone.points.length < 4) return; + const position = [target[0], 10, target[2]]; + + const input = { + userId: userId, + projectId, + organization: organization, + zoneData: { + zoneName: zone.zoneName, + zoneUuid: zone.zoneUuid, + points: zone.points, + viewPortCenter: target, + viewPortposition: position, + layer: zone.layer, + }, + }; + + socket.emit("v1:zone:set", input); }; - const onMouseMove = () => { - if (!groupsRef.current) return; - if (isLeftMouseDown) { - drag = true; - } - raycaster.setFromCamera(pointer, camera); - const intersects = raycaster.intersectObjects( - groupsRef.current.children, - true - ); + // eslint-disable-next-line react-hooks/exhaustive-deps + const updateZoneToBackend = async (zone: { + zoneUuid: string; + zoneName: string; + points: [number, number, number][]; + layer: string; + }) => { + const email = localStorage.getItem("email"); + const userId = localStorage.getItem("userId"); + const organization = email!.split("@")[1].split(".")[0]; - if ( - intersects.length > 0 && - intersects[0].object.name.includes("point") - ) { - gl.domElement.style.cursor = - toolMode === "move" ? "pointer" : "default"; - } else { - gl.domElement.style.cursor = "default"; - } - if (isDragging && draggedSphere) { + const calculateCenter = (points: number[][]) => { + if (!points || points.length === 0) return null; + + let sumX = 0, sumY = 0, sumZ = 0; + const numPoints = points.length; + + points.forEach(([x, y, z]) => { + sumX += x; + sumY += y; + sumZ += z; + }); + + return [sumX / numPoints, sumY / numPoints, sumZ / numPoints] as [ + number, + number, + number + ]; + }; + + const target: [number, number, number] | null = calculateCenter(zone.points); + if (!target || zone.points.length < 4) return; + const position = [target[0], 10, target[2]]; + + const input = { + userId: userId, + projectId, + organization: organization, + zoneData: { + zoneName: zone.zoneName, + zoneUuid: zone.zoneUuid, + points: zone.points, + viewPortCenter: target, + viewPortposition: position, + layer: zone.layer, + }, + }; + + socket.emit("v1:zone:set", input); + }; + + const deleteZoneFromBackend = async (zoneUuid: string) => { + const email = localStorage.getItem("email"); + const userId = localStorage.getItem("userId"); + const organization = email!.split("@")[1].split(".")[0]; + + const input = { + userId: userId, + projectId, + organization: organization, + zoneUuid: zoneUuid, + }; + + socket.emit("v1:zone:delete", input); + }; + + // eslint-disable-next-line react-hooks/exhaustive-deps + const handleDeleteZone = (zoneUuid: string) => { + const updatedZones = zones.filter((zone: any) => zone.zoneUuid !== zoneUuid); + setZones(updatedZones); + + const zoneIndex = zones.findIndex((zone: any) => zone.zoneUuid === zoneUuid); + if (zoneIndex !== -1) { + const zonePointsToRemove = zonePoints.slice(zoneIndex * 4, zoneIndex * 4 + 4); + zonePointsToRemove.forEach((point: any) => groupsRef.current.remove(point)); + const updatedzonePoints = zonePoints.filter((_: any, index: any) => index < zoneIndex * 4 || index >= zoneIndex * 4 + 4); + setZonePoints(updatedzonePoints); + } + deleteZoneFromBackend(zoneUuid); + }; + + useEffect(() => { + if (!camera || !toggleView) return; + const canvasElement = gl.domElement; + + let drag = false; + let isLeftMouseDown = false; + + const onMouseDown = (evt: any) => { + if (evt.button === 0) { + isLeftMouseDown = true; + drag = false; + + raycaster.setFromCamera(pointer, camera); + const intersects = raycaster.intersectObjects(groupsRef.current.children, true); + + if (intersects.length > 0 && toolMode === "move") { + const clickedObject = intersects[0].object; + const sphereIndex = zonePoints.findIndex((point: any) => + point.equals(clickedObject.position) + ); + if (sphereIndex !== -1) { + (controls as any).enabled = false; + setDraggedSphere(zonePoints[sphereIndex]); + setIsDragging(true); + } + } + } + }; + + const onMouseUp = (evt: any) => { + if (evt.button === 0 && !drag && !isDragging && toolMode === 'Zone') { + isLeftMouseDown = false; + + if (!startPoint) { + raycaster.setFromCamera(pointer, camera); + const intersectionPoint = new THREE.Vector3(); + const point = raycaster.ray.intersectPlane(plane, intersectionPoint); + if (point) { + setStartPoint(point); + setEndPoint(null); + } + } else if (startPoint) { + raycaster.setFromCamera(pointer, camera); + const intersectionPoint = new THREE.Vector3(); + const point = raycaster.ray.intersectPlane(plane, intersectionPoint); + if (!point) return; + + const points = [ + [startPoint.x, 0.15, startPoint.z], + [point.x, 0.15, startPoint.z], + [point.x, 0.15, point.z], + [startPoint.x, 0.15, point.z], + [startPoint.x, 0.15, startPoint.z], + ] as [number, number, number][]; + + const zoneName = `Zone ${zones.length + 1}`; + const zoneUuid = THREE.MathUtils.generateUUID(); + const newZone = { + zoneUuid, + zoneName, + points: points, + layer: activeLayer, + }; + + const newZones = [...zones, newZone]; + + setZones(newZones); + + const newzonePoints = [ + new THREE.Vector3(startPoint.x, 0.15, startPoint.z), + new THREE.Vector3(point.x, 0.15, startPoint.z), + new THREE.Vector3(point.x, 0.15, point.z), + new THREE.Vector3(startPoint.x, 0.15, point.z), + ]; + + const updatedZonePoints = [...zonePoints, ...newzonePoints]; + setZonePoints(updatedZonePoints); + + addZoneToBackend(newZone); + setStartPoint(null); + setEndPoint(null); + } + } else if (evt.button === 0 && !drag && !isDragging && toolMode === '2D-Delete') { + raycaster.setFromCamera(pointer, camera); + const intersects = raycaster.intersectObjects( + groupsRef.current.children, + true + ); + + if (intersects.length > 0) { + const clickedObject = intersects[0].object; + + const sphereIndex = zonePoints.findIndex((point: any) => + point.equals(clickedObject.position) + ); + if (sphereIndex !== -1) { + const zoneIndex = Math.floor(sphereIndex / 4); + const zoneUuid = zones[zoneIndex].zoneUuid; + handleDeleteZone(zoneUuid); + return; + } + } + } + + if (evt.button === 0) { + if (isDragging && draggedSphere) { + setIsDragging(false); + setDraggedSphere(null); + + const sphereIndex = zonePoints.findIndex((point: any) => point === draggedSphere); + if (sphereIndex !== -1) { + const zoneIndex = Math.floor(sphereIndex / 4); + + if (zoneIndex !== -1 && zones[zoneIndex]) { + updateZoneToBackend(zones[zoneIndex]); + } + } + } + } + }; + + const onMouseMove = () => { + if (!groupsRef.current) return; + if (isLeftMouseDown) { + drag = true; + } + raycaster.setFromCamera(pointer, camera); + const intersects = raycaster.intersectObjects(groupsRef.current.children, true); + + if (intersects.length > 0 && intersects[0].object.name.includes("point")) { + gl.domElement.style.cursor = toolMode === "move" ? "pointer" : "default"; + } else { + gl.domElement.style.cursor = "default"; + } + if (isDragging && draggedSphere) { + raycaster.setFromCamera(pointer, camera); + const intersectionPoint = new THREE.Vector3(); + const point = raycaster.ray.intersectPlane(plane, intersectionPoint); + if (point) { + draggedSphere.set(point.x, 0.15, point.z); + + const sphereIndex = zonePoints.findIndex((point: any) => point === draggedSphere); + if (sphereIndex !== -1) { + const zoneIndex = Math.floor(sphereIndex / 4); + const cornerIndex = sphereIndex % 4; + + const updatedZones = zones.map((zone: any, index: number) => { + if (index === zoneIndex) { + const updatedPoints = [...zone.points]; + updatedPoints[cornerIndex] = [point.x, 0.15, point.z]; + updatedPoints[4] = updatedPoints[0]; + return { ...zone, points: updatedPoints }; + } + return zone; + }); + + setZones(updatedZones); + } + } + } + }; + + const onContext = (event: any) => { + event.preventDefault(); + setStartPoint(null); + setEndPoint(null); + }; + + if (toolMode === "Zone" || toolMode === '2D-Delete' || toolMode === "move") { + canvasElement.addEventListener("mousedown", onMouseDown); + canvasElement.addEventListener("mouseup", onMouseUp); + canvasElement.addEventListener("mousemove", onMouseMove); + canvasElement.addEventListener("contextmenu", onContext); + } + return () => { + canvasElement.removeEventListener("mousedown", onMouseDown); + canvasElement.removeEventListener("mouseup", onMouseUp); + canvasElement.removeEventListener("mousemove", onMouseMove); + canvasElement.removeEventListener("contextmenu", onContext); + }; + }, [gl, camera, startPoint, toggleView, scene, toolMode, zones, isDragging, zonePoints, draggedSphere, activeLayer, raycaster, pointer, controls, plane, setZones, setZonePoints, addZoneToBackend, handleDeleteZone, updateZoneToBackend,]); + + useFrame(() => { + if (!startPoint) return; raycaster.setFromCamera(pointer, camera); const intersectionPoint = new THREE.Vector3(); const point = raycaster.ray.intersectPlane(plane, intersectionPoint); if (point) { - draggedSphere.set(point.x, 0.15, point.z); - - const sphereIndex = zonePoints.findIndex( - (point: any) => point === draggedSphere - ); - if (sphereIndex !== -1) { - const zoneIndex = Math.floor(sphereIndex / 4); - const cornerIndex = sphereIndex % 4; - - const updatedZones = zones.map((zone: any, index: number) => { - if (index === zoneIndex) { - const updatedPoints = [...zone.points]; - updatedPoints[cornerIndex] = [point.x, 0.15, point.z]; - updatedPoints[4] = updatedPoints[0]; - return { ...zone, points: updatedPoints }; - } - return zone; - }); - - setZones(updatedZones); - } + setEndPoint(point); } - } - }; + }); - const onContext = (event: any) => { - event.preventDefault(); - setStartPoint(null); - setEndPoint(null); - }; + return ( + + + {zones.map((zone: any) => ( + + {zone.points + .slice(0, -1) + .map((point: [number, number, number], index: number) => { + const nextPoint = zone.points[index + 1]; - if (toolMode === "Zone" || deletePointOrLine || toolMode === "move") { - canvasElement.addEventListener("mousedown", onMouseDown); - canvasElement.addEventListener("mouseup", onMouseUp); - canvasElement.addEventListener("mousemove", onMouseMove); - canvasElement.addEventListener("contextmenu", onContext); - } - return () => { - canvasElement.removeEventListener("mousedown", onMouseDown); - canvasElement.removeEventListener("mouseup", onMouseUp); - canvasElement.removeEventListener("mousemove", onMouseMove); - canvasElement.removeEventListener("contextmenu", onContext); - }; - }, [ - gl, - camera, - startPoint, - toggleView, - scene, - toolMode, - zones, - isDragging, - deletePointOrLine, - zonePoints, - draggedSphere, - activeLayer, - raycaster, - pointer, - controls, - plane, - setZones, - setZonePoints, - addZoneToBackend, - handleDeleteZone, - updateZoneToBackend, - ]); + const point1 = new THREE.Vector3(point[0], point[1], point[2]); + const point2 = new THREE.Vector3( + nextPoint[0], + nextPoint[1], + nextPoint[2] + ); - useFrame(() => { - if (!startPoint) return; - raycaster.setFromCamera(pointer, camera); - const intersectionPoint = new THREE.Vector3(); - const point = raycaster.ray.intersectPlane(plane, intersectionPoint); - if (point) { - setEndPoint(point); - } - }); + const planeWidth = point1.distanceTo(point2); + const planeHeight = CONSTANTS.zoneConfig.height; - return ( - - - {zones.map((zone: any) => ( - - {zone.points - .slice(0, -1) - .map((point: [number, number, number], index: number) => { - const nextPoint = zone.points[index + 1]; + const midpoint = new THREE.Vector3( + (point1.x + point2.x) / 2, + CONSTANTS.zoneConfig.height / 2 + + (zone.layer - 1) * CONSTANTS.zoneConfig.height, + (point1.z + point2.z) / 2 + ); - const point1 = new THREE.Vector3(point[0], point[1], point[2]); - const point2 = new THREE.Vector3( - nextPoint[0], - nextPoint[1], - nextPoint[2] - ); + const angle = Math.atan2( + point2.z - point1.z, + point2.x - point1.x + ); - const planeWidth = point1.distanceTo(point2); - const planeHeight = CONSTANTS.zoneConfig.height; + return ( + + + + + ); + })} + {!toggleView && + (() => { + const points3D = zone.points || []; + const coords2D = points3D.map((p: any) => [p[0], p[2]]); - const midpoint = new THREE.Vector3( - (point1.x + point2.x) / 2, - CONSTANTS.zoneConfig.height / 2 + - (zone.layer - 1) * CONSTANTS.zoneConfig.height, - (point1.z + point2.z) / 2 - ); + // Ensure the polygon is closed + if ( + coords2D.length >= 4 && + (coords2D[0][0] !== coords2D[coords2D.length - 1][0] || + coords2D[0][1] !== coords2D[coords2D.length - 1][1]) + ) { + coords2D.push(coords2D[0]); + } + if (coords2D.length < 4) return null; - const angle = Math.atan2( - point2.z - point1.z, - point2.x - point1.x - ); + const polygon = turf.polygon([coords2D]); + const center2D = turf.center(polygon).geometry.coordinates; - return ( - - - sum + p[1], + 0 + ); + const avgY = points3D.length > 0 ? sumY / points3D.length : 0; + + const htmlPosition: [number, number, number] = [ + center2D[0], + avgY + (CONSTANTS.zoneConfig.height || 0) + 1.5, + center2D[1], + ]; + + return ( + +
{zone.zoneName}
+ + ); + })()} +
+ ))} +
+ + {zones + .filter((zone: any) => zone.layer === activeLayer) + .map((zone: any) => ( + { + e.stopPropagation(); + if (toolMode === '2D-Delete') { + handleDeleteZone(zone.zoneUuid); + } + }} + /> + ))} + + + {zones.map((zone: any, index: any) => { + if (!toggleView) return null; + const points3D = zone.points; + const coords2D = points3D.map((p: any) => [p[0], p[2]]); + + if ( + coords2D.length < 4 || + coords2D[0][0] !== coords2D[coords2D.length - 1][0] || + coords2D[0][1] !== coords2D[coords2D.length - 1][1] + ) { + coords2D.push(coords2D[0]); + } + if (coords2D.length < 4) return null; + + const polygon = turf.polygon([coords2D]); + const center2D = turf.center(polygon).geometry.coordinates; + + const sumY = points3D.reduce((sum: number, p: any) => sum + p[1], 0); + const avgY = sumY / points3D.length; + + const area = computeArea(points3D, "zone"); + const formattedArea = `${area.toFixed(2)} m²`; + + const htmlPosition: [number, number, number] = [ + center2D[0], + avgY + CONSTANTS.zoneConfig.height, + center2D[1], + ]; + return ( + +
+ {zone.zoneName} ({formattedArea}) +
+ + ); + })} +
+ + + {zones + .filter((zone: any) => zone.layer === activeLayer) + .flatMap((zone: any) => + zone.points.slice(0, 4).map((point: any, pointIndex: number) => ( + + + + )) + )} + + + {startPoint && endPoint && ( + - - ); - })} - {!toggleView && - (() => { - const points3D = zone.points || []; - const coords2D = points3D.map((p: any) => [p[0], p[2]]); - - // Ensure the polygon is closed - if ( - coords2D.length >= 4 && - (coords2D[0][0] !== coords2D[coords2D.length - 1][0] || - coords2D[0][1] !== coords2D[coords2D.length - 1][1]) - ) { - coords2D.push(coords2D[0]); - } - if (coords2D.length < 4) return null; - - const polygon = turf.polygon([coords2D]); - const center2D = turf.center(polygon).geometry.coordinates; - - // Calculate the average Y value - const sumY = points3D.reduce( - (sum: number, p: any) => sum + p[1], - 0 - ); - const avgY = points3D.length > 0 ? sumY / points3D.length : 0; - - const htmlPosition: [number, number, number] = [ - center2D[0], - avgY + (CONSTANTS.zoneConfig.height || 0) + 1.5, - center2D[1], - ]; - - return ( - -
{zone.zoneName}
- - ); - })()} -
- ))} -
- - {zones - .filter((zone: any) => zone.layer === activeLayer) - .map((zone: any) => ( - { - e.stopPropagation(); - if (deletePointOrLine) { - handleDeleteZone(zone.zoneUuid); - } - }} - /> - ))} - - - {zones.map((zone: any, index: any) => { - if (!toggleView) return null; - const points3D = zone.points; - const coords2D = points3D.map((p: any) => [p[0], p[2]]); - - if ( - coords2D.length < 4 || - coords2D[0][0] !== coords2D[coords2D.length - 1][0] || - coords2D[0][1] !== coords2D[coords2D.length - 1][1] - ) { - coords2D.push(coords2D[0]); - } - if (coords2D.length < 4) return null; - - const polygon = turf.polygon([coords2D]); - const center2D = turf.center(polygon).geometry.coordinates; - - const sumY = points3D.reduce((sum: number, p: any) => sum + p[1], 0); - const avgY = sumY / points3D.length; - - const area = computeArea(points3D, "zone"); - const formattedArea = `${area.toFixed(2)} m²`; - - const htmlPosition: [number, number, number] = [ - center2D[0], - avgY + CONSTANTS.zoneConfig.height, - center2D[1], - ]; - return ( - -
- {zone.zoneName} ({formattedArea}) -
- - ); - })} -
- - - {zones - .filter((zone: any) => zone.layer === activeLayer) - .flatMap((zone: any) => - zone.points.slice(0, 4).map((point: any, pointIndex: number) => ( - - - - )) - )} - - - {startPoint && endPoint && ( - - )} - -
- ); + )} +
+
+ ); }; export default ZoneGroup; diff --git a/app/src/modules/builder/point/point.tsx b/app/src/modules/builder/point/point.tsx index 6380ea1..c026f94 100644 --- a/app/src/modules/builder/point/point.tsx +++ b/app/src/modules/builder/point/point.tsx @@ -1,7 +1,7 @@ import * as THREE from 'three'; import * as Constants from '../../../types/world/worldConstants'; import { useRef, useState, useEffect, useMemo } from 'react'; -import { useDeletePointOrLine, useToolMode } from '../../../store/builder/store'; +import { useToolMode } from '../../../store/builder/store'; import { DragControls } from '@react-three/drei'; import { useAisleStore } from '../../../store/builder/useAisleStore'; import { useThree } from '@react-three/fiber'; @@ -24,7 +24,6 @@ function Point({ point }: { readonly point: Point }) { const { snapPosition } = useAislePointSnapping(point); const { checkSnapForAisle } = usePointSnapping({ uuid: point.pointUuid, pointType: point.pointType, position: point.position }); const { hoveredPoint, setHoveredPoint } = useBuilderStore(); - const { deletePointOrLine } = useDeletePointOrLine(); const { projectId } = useParams(); const boxScale: [number, number, number] = Constants.pointConfig.boxScale; const colors = getColor(point); @@ -64,12 +63,12 @@ function Point({ point }: { readonly point: Point }) { } useEffect(() => { - if (materialRef.current && (toolMode === 'move' || deletePointOrLine)) { + if (materialRef.current && (toolMode === 'move' || toolMode === '2D-Delete')) { let innerColor; let outerColor; if (isHovered) { - innerColor = deletePointOrLine ? colors.defaultDeleteColor : colors.defaultOuterColor; - outerColor = deletePointOrLine ? colors.defaultDeleteColor : colors.defaultOuterColor; + innerColor = toolMode === '2D-Delete' ? colors.defaultDeleteColor : colors.defaultOuterColor; + outerColor = toolMode === '2D-Delete' ? colors.defaultDeleteColor : colors.defaultOuterColor; } else { innerColor = colors.defaultInnerColor; outerColor = colors.defaultOuterColor; @@ -82,7 +81,7 @@ function Point({ point }: { readonly point: Point }) { materialRef.current.uniforms.uOuterColor.value.set(colors.defaultOuterColor); materialRef.current.uniformsNeedUpdate = true; } - }, [isHovered, colors.defaultInnerColor, colors.defaultOuterColor, colors.defaultDeleteColor, toolMode, deletePointOrLine]); + }, [isHovered, colors.defaultInnerColor, colors.defaultOuterColor, colors.defaultDeleteColor, toolMode]); const uniforms = useMemo(() => ({ uOuterColor: { value: new THREE.Color(colors.defaultOuterColor) }, @@ -114,7 +113,7 @@ function Point({ point }: { readonly point: Point }) { } const handleDragEnd = (point: Point) => { - if (deletePointOrLine) return; + if (toolMode === '2D-Delete') return; if (point.pointType === 'Aisle') { const updatedAisles = getAislesByPointId(point.pointUuid); if (updatedAisles.length > 0 && projectId) { @@ -128,7 +127,7 @@ function Point({ point }: { readonly point: Point }) { } const handlePointClick = (point: Point) => { - if (deletePointOrLine) { + if (toolMode === '2D-Delete') { if (point.pointType === 'Aisle') { const removedAisles = removeAislePoint(point.pointUuid); if (removedAisles.length > 0) { diff --git a/app/src/modules/collaboration/socket/socketResponses.dev.tsx b/app/src/modules/collaboration/socket/socketResponses.dev.tsx index fed9893..894fc50 100644 --- a/app/src/modules/collaboration/socket/socketResponses.dev.tsx +++ b/app/src/modules/collaboration/socket/socketResponses.dev.tsx @@ -40,16 +40,11 @@ export default function SocketResponses({ floorPlanGroup, lines, floorGroup, - floorGroupAisle, scene, onlyFloorlines, - itemsGroup, - isTempLoader, - tempLoader, currentLayerPoint, floorPlanGroupPoint, floorPlanGroupLine, - zoneGroup, dragPointControls, }: any) { const { socket } = useSocketStore(); diff --git a/app/src/modules/scene/controls/selectionControls/selectionControls.tsx b/app/src/modules/scene/controls/selectionControls/selectionControls.tsx index 2a9b5c8..2fbeaf3 100644 --- a/app/src/modules/scene/controls/selectionControls/selectionControls.tsx +++ b/app/src/modules/scene/controls/selectionControls/selectionControls.tsx @@ -3,7 +3,7 @@ import { useCallback, useEffect, useMemo, useRef, useState } from "react"; import { SelectionBox } from "three/examples/jsm/interactive/SelectionBox"; import { SelectionHelper } from "./selectionHelper"; import { useFrame, useThree } from "@react-three/fiber"; -import { useSelectedAssets, useSocketStore, useToggleView, } from "../../../../store/builder/store"; +import { useSelectedAssets, useSocketStore, useToggleView, useToolMode, } from "../../../../store/builder/store"; import BoundingBox from "./boundingBoxHelper"; // import { deleteFloorItem } from '../../../../services/factoryBuilder/assest/floorAsset/deleteFloorItemApi'; import * as Types from "../../../../types/world/worldTypes"; @@ -33,6 +33,7 @@ const SelectionControls: React.FC = () => { const { socket } = useSocketStore(); const { removeAsset } = useAssetsStore(); const selectionBox = useMemo(() => new SelectionBox(camera, scene), [camera, scene]); + const { toolMode } = useToolMode(); const { projectId } = useParams(); const isDragging = useRef(false); @@ -173,7 +174,7 @@ const SelectionControls: React.FC = () => { rightClickMoved.current = false; }; - if (!toggleView && activeModule === "builder") { + if (!toggleView && activeModule === "builder" && toolMode === 'cursor') { helper.enabled = true; canvasElement.addEventListener("pointermove", onPointerMove); canvasElement.addEventListener("pointerup", onPointerUp); @@ -194,7 +195,7 @@ const SelectionControls: React.FC = () => { helper.enabled = false; helper.dispose(); }; - }, [camera, controls, scene, toggleView, selectedAssets, copiedObjects, pastedObjects, duplicatedObjects, movedObjects, socket, rotatedObjects, activeModule,]); + }, [camera, controls, scene, toggleView, selectedAssets, copiedObjects, pastedObjects, duplicatedObjects, movedObjects, socket, rotatedObjects, activeModule, toolMode]); useEffect(() => { if (activeModule !== "builder") { diff --git a/app/src/modules/simulation/events/arrows/arrows.tsx b/app/src/modules/simulation/events/arrows/arrows.tsx index 951435e..59e56e2 100644 --- a/app/src/modules/simulation/events/arrows/arrows.tsx +++ b/app/src/modules/simulation/events/arrows/arrows.tsx @@ -1,7 +1,7 @@ import * as THREE from "three"; import { useMemo, useRef, useState } from "react"; import { useThree } from "@react-three/fiber"; -import { useDeleteTool } from "../../../../store/builder/store"; +import { useToolMode } from "../../../../store/builder/store"; interface ConnectionLine { id: string; @@ -14,7 +14,7 @@ export function Arrows({ connections }: { readonly connections: ConnectionLine[] const [hoveredLineKey, setHoveredLineKey] = useState(null); const groupRef = useRef(null); const { scene } = useThree(); - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const getWorldPositionFromScene = (uuid: string): THREE.Vector3 | null => { const obj = scene.getObjectByProperty("uuid", uuid); @@ -61,7 +61,7 @@ export function Arrows({ connections }: { readonly connections: ConnectionLine[] onPointerOut={() => setHoveredLineKey(null)} > setHoveredLineKey(null)} >
diff --git a/app/src/modules/simulation/events/points/creator/pointsCreator.tsx b/app/src/modules/simulation/events/points/creator/pointsCreator.tsx index 28e948a..467ffc0 100644 --- a/app/src/modules/simulation/events/points/creator/pointsCreator.tsx +++ b/app/src/modules/simulation/events/points/creator/pointsCreator.tsx @@ -11,6 +11,7 @@ import { usePlayButtonStore } from "../../../../../store/usePlayButtonStore"; import { upsertProductOrEventApi } from "../../../../../services/simulation/products/UpsertProductOrEventApi"; import { useProductContext } from "../../../products/productContext"; import { useParams } from "react-router-dom"; +import { useToolMode } from "../../../../../store/builder/store"; function PointsCreator() { const { gl, raycaster, scene, pointer, camera } = useThree(); @@ -26,7 +27,7 @@ function PointsCreator() { const { selectedEventSphere, setSelectedEventSphere, clearSelectedEventSphere, } = useSelectedEventSphere(); const { setSelectedEventData, clearSelectedEventData } = useSelectedEventData(); const { isPlaying } = usePlayButtonStore(); - + const { toolMode } = useToolMode(); const { projectId } = useParams(); const updateBackend = ( @@ -204,9 +205,11 @@ function PointsCreator() { ref={(el) => (sphereRefs.current[point.uuid] = el!)} onClick={(e) => { e.stopPropagation(); - setSelectedEventSphere( - sphereRefs.current[point.uuid] - ); + if (toolMode === 'cursor') { + setSelectedEventSphere( + sphereRefs.current[point.uuid] + ); + } }} key={`${index}-${point.uuid}`} position={new THREE.Vector3(...point.position)} @@ -235,9 +238,11 @@ function PointsCreator() { ref={(el) => (sphereRefs.current[point.uuid] = el!)} onClick={(e) => { e.stopPropagation(); - setSelectedEventSphere( - sphereRefs.current[point.uuid] - ); + if (toolMode === 'cursor') { + setSelectedEventSphere( + sphereRefs.current[point.uuid] + ); + } }} position={new THREE.Vector3(...point.position)} userData={{ @@ -264,9 +269,11 @@ function PointsCreator() { ref={(el) => (sphereRefs.current[point.uuid] = el!)} onClick={(e) => { e.stopPropagation(); - setSelectedEventSphere( - sphereRefs.current[point.uuid] - ); + if (toolMode === 'cursor') { + setSelectedEventSphere( + sphereRefs.current[point.uuid] + ); + } }} position={new THREE.Vector3(...point.position)} userData={{ @@ -293,9 +300,11 @@ function PointsCreator() { ref={(el) => (sphereRefs.current[point.uuid] = el!)} onClick={(e) => { e.stopPropagation(); - setSelectedEventSphere( - sphereRefs.current[point.uuid] - ); + if (toolMode === 'cursor') { + setSelectedEventSphere( + sphereRefs.current[point.uuid] + ); + } }} position={new THREE.Vector3(...point.position)} userData={{ @@ -322,9 +331,11 @@ function PointsCreator() { ref={(el) => (sphereRefs.current[point.uuid] = el!)} onClick={(e) => { e.stopPropagation(); - setSelectedEventSphere( - sphereRefs.current[point.uuid] - ); + if (toolMode === 'cursor') { + setSelectedEventSphere( + sphereRefs.current[point.uuid] + ); + } }} position={new THREE.Vector3(...point.position)} userData={{ diff --git a/app/src/modules/simulation/events/triggerConnections/triggerConnector.tsx b/app/src/modules/simulation/events/triggerConnections/triggerConnector.tsx index 894ec35..c63612a 100644 --- a/app/src/modules/simulation/events/triggerConnections/triggerConnector.tsx +++ b/app/src/modules/simulation/events/triggerConnections/triggerConnector.tsx @@ -8,11 +8,11 @@ import { useEventsStore } from "../../../../store/simulation/useEventsStore"; import { handleAddEventToProduct } from "../points/functions/handleAddEventToProduct"; import { QuadraticBezierLine } from "@react-three/drei"; import { upsertProductOrEventApi } from "../../../../services/simulation/products/UpsertProductOrEventApi"; -import { useDeleteTool } from "../../../../store/builder/store"; import { usePlayButtonStore } from "../../../../store/usePlayButtonStore"; import { ArrowOnQuadraticBezier, Arrows } from "../arrows/arrows"; import { useProductContext } from "../../products/productContext"; import { useParams } from "react-router-dom"; +import { useToolMode } from "../../../../store/builder/store"; interface ConnectionLine { id: string; @@ -32,7 +32,7 @@ function TriggerConnector() { const groupRefs = useRef>({}); const [helperlineColor, setHelperLineColor] = useState("red"); const [currentLine, setCurrentLine] = useState<{ start: THREE.Vector3; end: THREE.Vector3; mid: THREE.Vector3; } | null>(null); - const { deleteTool } = useDeleteTool(); + const { toolMode } = useToolMode(); const { isPlaying } = usePlayButtonStore(); const { selectedAction } = useSelectedAction(); const { projectId } = useParams(); @@ -344,7 +344,7 @@ function TriggerConnector() { } }; - if (subModule === 'mechanics' && !deleteTool && selectedAction.actionId && selectedAction.actionName) { + if (subModule === 'mechanics' && toolMode === 'cursor' && selectedAction.actionId && selectedAction.actionName) { canvasElement.addEventListener("mousedown", onMouseDown); canvasElement.addEventListener("mouseup", onMouseUp); canvasElement.addEventListener("mousemove", onMouseMove); @@ -360,7 +360,7 @@ function TriggerConnector() { canvasElement.removeEventListener('contextmenu', handleRightClick); }; - }, [gl, subModule, selectedProduct, firstSelectedPoint, deleteTool, selectedAction]); + }, [gl, subModule, selectedProduct, firstSelectedPoint, toolMode, selectedAction]); useFrame(() => { if (firstSelectedPoint) { @@ -477,15 +477,15 @@ function TriggerConnector() { start={startPoint.toArray()} end={endPoint.toArray()} mid={midPoint.toArray()} - color={deleteTool && hoveredLineKey === connection.id ? "red" : "#42a5f5"} + color={toolMode === '3D-Delete' && hoveredLineKey === connection.id ? "red" : "#42a5f5"} lineWidth={4} - dashed={deleteTool && hoveredLineKey === connection.id ? false : true} + dashed={toolMode === '3D-Delete' && hoveredLineKey === connection.id ? false : true} dashSize={0.75} dashScale={20} onPointerOver={() => setHoveredLineKey(connection.id)} onPointerOut={() => setHoveredLineKey(null)} onClick={() => { - if (deleteTool) { + if (toolMode === '3D-Delete') { setHoveredLineKey(null); setCurrentLine(null); removeConnection(connection); diff --git a/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx b/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx index 51f044d..e921bc0 100644 --- a/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx +++ b/app/src/modules/simulation/roboticArm/instances/armInstance/roboticArmInstance.tsx @@ -46,7 +46,7 @@ function RoboticArmInstance({ armBot }: { readonly armBot: ArmBotStatus }) { const animationFrameIdRef = useRef(null); const previousTimeRef = useRef(null); - const lastRemoved = useRef<{ type: string, materialId: string } | null>(null); + const lastRemoved = useRef<{ type: string, materialId: string, modelId: string } | null>(null); function firstFrame() { startTime = performance.now(); @@ -73,7 +73,7 @@ function RoboticArmInstance({ armBot }: { readonly armBot: ArmBotStatus }) { removeLastStorageMaterial(previousModel.modelUuid); updateCurrentLoad(previousModel.modelUuid, -1) } - lastRemoved.current = { type: previousModel.type, materialId: armBot.currentAction.materialId }; + lastRemoved.current = { type: previousModel.type, materialId: armBot.currentAction.materialId, modelId: previousModel.modelUuid }; } else { setIsVisible(armBot.currentAction.materialId, false); } @@ -105,13 +105,13 @@ function RoboticArmInstance({ armBot }: { readonly armBot: ArmBotStatus }) { removeCurrentAction(armBot.modelUuid) } - if (lastRemoved.current) { - if (lastRemoved.current.type === 'transfer') { - setIsPaused(lastRemoved.current.materialId, true) - } else { - setIsPaused(lastRemoved.current.materialId, false) - } - } + // if (lastRemoved.current) { + // if (lastRemoved.current.type === 'transfer') { + // setIsPaused(lastRemoved.current.materialId, true) + // } else { + // setIsPaused(lastRemoved.current.materialId, false) + // } + // } } } diff --git a/app/src/modules/simulation/simulator/simulator.tsx b/app/src/modules/simulation/simulator/simulator.tsx index f9e4714..5b2f8a8 100644 --- a/app/src/modules/simulation/simulator/simulator.tsx +++ b/app/src/modules/simulation/simulator/simulator.tsx @@ -15,7 +15,6 @@ function Simulator() { useEffect(() => { if (!isPlaying || isReset || !selectedProduct.productUuid) return; - console.log('selectedProduct: ', selectedProduct); const product = getProductById(selectedProduct.productUuid); if (!product) return; diff --git a/app/src/modules/simulation/triggers/triggerHandler/useTriggerHandler.ts b/app/src/modules/simulation/triggers/triggerHandler/useTriggerHandler.ts index 0989b89..5298c87 100644 --- a/app/src/modules/simulation/triggers/triggerHandler/useTriggerHandler.ts +++ b/app/src/modules/simulation/triggers/triggerHandler/useTriggerHandler.ts @@ -604,6 +604,7 @@ export function useTriggerHandler() { modelUuid: action.triggers[0]?.triggeredAsset?.triggeredModel.modelUuid, pointUuid: action.triggers[0]?.triggeredAsset?.triggeredPoint?.pointUuid, }) + setIsPaused(material.materialId, false); // New handleAction(action, material.materialId); } } else { diff --git a/app/src/store/builder/store.ts b/app/src/store/builder/store.ts index c384f20..6018694 100644 --- a/app/src/store/builder/store.ts +++ b/app/src/store/builder/store.ts @@ -197,10 +197,10 @@ export const useMenuVisible = create((set: any) => ({ setMenuVisible: (x: any) => set(() => ({ menuVisible: x })), })); -export const useDeleteTool = create((set: any) => ({ - deleteTool: false, - setDeleteTool: (x: any) => set(() => ({ deleteTool: x })), -})); +// export const useDeleteTool = create((set: any) => ({ +// deleteTool: false, +// setDeleteTool: (x: any) => set(() => ({ deleteTool: x })), +// })); export const useToolMode = create((set: any) => ({ toolMode: null, @@ -222,10 +222,10 @@ export const useMovePoint = create((set: any) => ({ setMovePoint: (x: any) => set(() => ({ movePoint: x })), })); -export const useDeletePointOrLine = create((set: any) => ({ - deletePointOrLine: false, - setDeletePointOrLine: (x: any) => set(() => ({ deletePointOrLine: x })), -})); +// export const useDeletePointOrLine = create((set: any) => ({ +// deletePointOrLine: false, +// setDeletePointOrLine: (x: any) => set(() => ({ deletePointOrLine: x })), +// })); export const useWallItems = create((set: any) => ({ wallItems: [], diff --git a/app/src/utils/shortcutkeys/handleShortcutKeys.ts b/app/src/utils/shortcutkeys/handleShortcutKeys.ts index 1e3d302..180129e 100644 --- a/app/src/utils/shortcutkeys/handleShortcutKeys.ts +++ b/app/src/utils/shortcutkeys/handleShortcutKeys.ts @@ -5,7 +5,6 @@ import { useActiveSubTool, useActiveTool, useAddAction, - useDeleteTool, useRenameModeStore, useSaveVersion, useSelectedFloorItem, @@ -32,7 +31,6 @@ const KeyPressListener: React.FC = () => { const { setToolMode } = useToolMode(); const { isPlaying, setIsPlaying } = usePlayButtonStore(); const { toggleView, setToggleView } = useToggleView(); - const { setDeleteTool } = useDeleteTool(); const { setAddAction } = useAddAction(); const { setSelectedWallItem } = useSelectedWallItem(); const { setActiveTool } = useActiveTool(); @@ -60,7 +58,6 @@ const KeyPressListener: React.FC = () => { }; const module = modules[keyCombination]; if (module && !toggleView) { - console.log("hi"); setActiveTool("cursor"); setActiveSubTool("cursor"); if (module === "market") setToggleUI(false, false); @@ -91,7 +88,6 @@ const KeyPressListener: React.FC = () => { setToggleUI(toggleTo2D, toggleTo2D); if (toggleTo2D) { setSelectedWallItem(null); - setDeleteTool(false); setAddAction(null); } setActiveTool("cursor"); -- 2.40.1 From 6bb2947e246298cfd6bb61eb1aa6c4b8e6817c71 Mon Sep 17 00:00:00 2001 From: Jerald-Golden-B Date: Wed, 11 Jun 2025 15:47:39 +0530 Subject: [PATCH 17/17] refactor: replace 'modelfileID' with 'assetId' across multiple modules for consistency --- .../IntialLoad/loadInitialWallItems.ts | 18 ++++++------ app/src/modules/builder/asset/assetsGroup.tsx | 6 ++-- .../builder/asset/functions/addAssetModel.ts | 10 +++---- .../builder/geomentries/lines/drawWall.ts | 2 -- .../builder/geomentries/walls/addWallItems.ts | 5 ++-- .../modules/builder/groups/wallItemsGroup.tsx | 4 +-- .../socket/socketResponses.dev.tsx | 28 ++++++++++--------- app/src/modules/market/CardsContainer.tsx | 4 +-- app/src/modules/market/FilterSearch.tsx | 2 +- app/src/modules/market/MarketPlace.tsx | 2 +- .../selectionControls/copyPasteControls.tsx | 12 ++++---- .../selectionControls/duplicationControls.tsx | 10 +++---- .../selectionControls/moveControls.tsx | 4 +-- .../selectionControls/rotateControls.tsx | 4 +-- .../transformControls/transformControls.tsx | 2 +- .../assest/floorAsset/getFloorItemsApi.ts | 2 +- .../assest/floorAsset/setFloorItemApi.ts | 4 +-- .../assest/wallAsset/getWallItemsApi.ts | 1 - .../webWorkers/gltfLoaderWorker.js | 8 +++--- app/src/types/world/worldTypes.d.ts | 4 +-- 20 files changed, 65 insertions(+), 67 deletions(-) diff --git a/app/src/modules/builder/IntialLoad/loadInitialWallItems.ts b/app/src/modules/builder/IntialLoad/loadInitialWallItems.ts index 5a7ea85..ec04968 100644 --- a/app/src/modules/builder/IntialLoad/loadInitialWallItems.ts +++ b/app/src/modules/builder/IntialLoad/loadInitialWallItems.ts @@ -7,7 +7,7 @@ import { retrieveGLTF, storeGLTF } from '../../../utils/indexDB/idbUtils'; async function loadInitialWallItems( setWallItems: Types.setWallItemSetState, - projectId?:string + projectId?: string ): Promise { try { const email = localStorage.getItem('email'); @@ -16,7 +16,7 @@ async function loadInitialWallItems( } const organization = email.split("@")[1].split(".")[0]; - const items = await getWallItems(organization,projectId); + const items = await getWallItems(organization, projectId); let url_Backend_dwinzo = `http://${process.env.REACT_APP_SERVER_MARKETPLACE_URL}`; @@ -34,33 +34,33 @@ async function loadInitialWallItems( const loadedWallItems = await Promise.all(items.map(async (item: Types.WallItem) => { // Check THREE.js cache first - const cachedModel = THREE.Cache.get(item.modelfileID!); + const cachedModel = THREE.Cache.get(item.assetId!); if (cachedModel) { return processModel(cachedModel, item); } // Check IndexedDB cache - const cachedModelBlob = await retrieveGLTF(item.modelfileID!); + const cachedModelBlob = await retrieveGLTF(item.assetId!); if (cachedModelBlob) { const blobUrl = URL.createObjectURL(cachedModelBlob); return new Promise((resolve) => { loader.load(blobUrl, (gltf) => { URL.revokeObjectURL(blobUrl); - THREE.Cache.add(item.modelfileID!, gltf); + THREE.Cache.add(item.assetId!, gltf); resolve(processModel(gltf, item)); }); }); } // Load from original URL if not cached - const modelUrl = `${url_Backend_dwinzo}/api/v2/AssetFile/${item.modelfileID!}`; + const modelUrl = `${url_Backend_dwinzo}/api/v2/AssetFile/${item.assetId!}`; return new Promise((resolve) => { loader.load(modelUrl, async (gltf) => { try { // Cache the model const modelBlob = await fetch(modelUrl).then((res) => res.blob()); - await storeGLTF(item.modelfileID!, modelBlob); - THREE.Cache.add(item.modelfileID!, gltf); + await storeGLTF(item.assetId!, modelBlob); + THREE.Cache.add(item.assetId!, gltf); resolve(processModel(gltf, item)); } catch (error) { console.error('Failed to cache model:', error); @@ -91,7 +91,7 @@ function processModel(gltf: GLTF, item: Types.WallItem): Types.WallItem { type: item.type, model: model, modelName: item.modelName, - modelfileID: item.modelfileID, + assetId: item.assetId, scale: item.scale, csgscale: item.csgscale, csgposition: item.csgposition, diff --git a/app/src/modules/builder/asset/assetsGroup.tsx b/app/src/modules/builder/asset/assetsGroup.tsx index c83eb64..c5aefb8 100644 --- a/app/src/modules/builder/asset/assetsGroup.tsx +++ b/app/src/modules/builder/asset/assetsGroup.tsx @@ -63,7 +63,7 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea getFloorAssets(organization, projectId).then((data) => { if (data.length > 0) { - const uniqueItems = (data as FloorItems).filter((item, index, self) => index === self.findIndex((t) => t.modelfileID === item.modelfileID)); + const uniqueItems = (data as FloorItems).filter((item, index, self) => index === self.findIndex((t) => t.assetId === item.assetId)); totalAssets = uniqueItems.length; if (totalAssets === 0) { updateLoadingProgress(100); @@ -96,7 +96,7 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea assets.push({ modelUuid: item.modelUuid, modelName: item.modelName, - assetId: item.modelfileID, + assetId: item.assetId, position: item.position, rotation: [item.rotation.x, item.rotation.y, item.rotation.z], isLocked: item.isLocked, @@ -236,7 +236,7 @@ function AssetsGroup({ floorGroup, plane }: { readonly floorGroup: RefGroup, rea assets.push({ modelUuid: item.modelUuid, modelName: item.modelName, - assetId: item.modelfileID, + assetId: item.assetId, position: item.position, rotation: [item.rotation.x, item.rotation.y, item.rotation.z], isLocked: item.isLocked, diff --git a/app/src/modules/builder/asset/functions/addAssetModel.ts b/app/src/modules/builder/asset/functions/addAssetModel.ts index 250d2bc..98a2116 100644 --- a/app/src/modules/builder/asset/functions/addAssetModel.ts +++ b/app/src/modules/builder/asset/functions/addAssetModel.ts @@ -136,7 +136,7 @@ async function handleModelLoad( // organization, // newFloorItem.modelUuid, // newFloorItem.modelName, - // newFloorItem.modelfileID, + // newFloorItem.assetId, // newFloorItem.position, // { x: 0, y: 0, z: 0 }, // false, @@ -352,7 +352,7 @@ async function handleModelLoad( organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.assetId, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: model.rotation.x, @@ -372,7 +372,7 @@ async function handleModelLoad( const asset: Asset = { modelUuid: completeData.modelUuid, modelName: completeData.modelName, - assetId: completeData.modelfileID, + assetId: completeData.assetId, position: completeData.position, rotation: [ completeData.rotation.x, @@ -392,7 +392,7 @@ async function handleModelLoad( organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.assetId, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: model.rotation.x, @@ -411,7 +411,7 @@ async function handleModelLoad( const asset = { modelUuid: data.modelUuid, modelName: data.modelName, - assetId: data.modelfileID, + assetId: data.assetId, position: data.position, rotation: [data.rotation.x, data.rotation.y, data.rotation.z] as [number, number, number], isLocked: data.isLocked, diff --git a/app/src/modules/builder/geomentries/lines/drawWall.ts b/app/src/modules/builder/geomentries/lines/drawWall.ts index 93dcdf7..3597ec2 100644 --- a/app/src/modules/builder/geomentries/lines/drawWall.ts +++ b/app/src/modules/builder/geomentries/lines/drawWall.ts @@ -95,7 +95,6 @@ async function drawWall( userId } - console.log('input: ', input); socket.emit('v1:Line:create', input); setNewLines([newLines[0], newLines[1], line.current]); @@ -158,7 +157,6 @@ async function drawWall( userId } - console.log('input: ', input); socket.emit('v1:Line:create', input); setNewLines([line.current]) diff --git a/app/src/modules/builder/geomentries/walls/addWallItems.ts b/app/src/modules/builder/geomentries/walls/addWallItems.ts index c861fe0..8801729 100644 --- a/app/src/modules/builder/geomentries/walls/addWallItems.ts +++ b/app/src/modules/builder/geomentries/walls/addWallItems.ts @@ -91,7 +91,7 @@ async function AddWallItems( type: selected.subCategory, model: model, modelName: selected.name, - modelfileID: selected.id, + assetId: selected.id, scale: [1, 1, 1] as [number, number, number], csgscale: csgscale, csgposition: csgposition, @@ -107,7 +107,7 @@ async function AddWallItems( organization: organization, modelUuid: model.uuid, modelName: newWallItem.modelName, - modelfileID: selected.id, + assetId: selected.id, type: selected.subCategory, csgposition: newWallItem.csgposition, csgscale: newWallItem.csgscale, @@ -119,7 +119,6 @@ async function AddWallItems( userId }; - // console.log('data: ', data); socket.emit('v1:wallItems:set', data); setWallItems((prevItems) => { diff --git a/app/src/modules/builder/groups/wallItemsGroup.tsx b/app/src/modules/builder/groups/wallItemsGroup.tsx index d4e1efa..bbbf859 100644 --- a/app/src/modules/builder/groups/wallItemsGroup.tsx +++ b/app/src/modules/builder/groups/wallItemsGroup.tsx @@ -130,7 +130,7 @@ const WallItemsGroup = ({ // organization, // currentItem?.model?.uuid, // currentItem.modelName, - // currentItem.modelfileID, + // currentItem.assetId, // currentItem.type!, // currentItem.csgposition!, // currentItem.csgscale!, @@ -144,7 +144,7 @@ const WallItemsGroup = ({ const data = { organization: organization, modelUuid: currentItem.model?.uuid!, - modelfileID: currentItem.modelfileID, + assetId: currentItem.assetId, modelName: currentItem.modelName!, type: currentItem.type!, csgposition: currentItem.csgposition!, diff --git a/app/src/modules/collaboration/socket/socketResponses.dev.tsx b/app/src/modules/collaboration/socket/socketResponses.dev.tsx index 894fc50..ca8cb7e 100644 --- a/app/src/modules/collaboration/socket/socketResponses.dev.tsx +++ b/app/src/modules/collaboration/socket/socketResponses.dev.tsx @@ -99,7 +99,7 @@ export default function SocketResponses({ const asset: Asset = { modelUuid: data.data.modelUuid, modelName: data.data.modelName, - assetId: data.data.modelfileID, + assetId: data.data.assetId, position: data.data.position, rotation: [data.data.rotation.x, data.data.rotation.y, data.data.rotation.z], isLocked: data.data.isLocked, @@ -120,7 +120,7 @@ export default function SocketResponses({ const asset: Asset = { modelUuid: data.data.modelUuid, modelName: data.data.modelName, - assetId: data.data.modelfileID, + assetId: data.data.assetId, position: data.data.position, rotation: [data.data.rotation.x, data.data.rotation.y, data.data.rotation.z], isLocked: data.data.isLocked, @@ -469,13 +469,14 @@ export default function SocketResponses({ let url_Backend_dwinzo = `http://${process.env.REACT_APP_SERVER_MARKETPLACE_URL}`; socket.on("v1:wallItem:Response:Delete", (data: any) => { + // console.log('data: ', data); if (socket.id === data.socketId) { return; } if (organization !== data.organization) { return; } - if (data.message === "wallitem deleted") { + if (data.message === "wall Item deleted successfully") { const deletedUUID = data.data.modelUuid; let WallItemsRef = wallItems; const Items = WallItemsRef.filter((item: any) => item.model?.uuid !== deletedUUID); @@ -499,6 +500,7 @@ export default function SocketResponses({ }); socket.on("v1:wallItems:Response:Update", (data: any) => { + // console.log('data: ', data); // if (socket.id === data.socketId) { return; @@ -506,7 +508,7 @@ export default function SocketResponses({ if (organization !== data.organization) { return; } - if (data.message === "wallIitem created") { + if (data.message === "wall Item created successfully") { const loader = new GLTFLoader(); const dracoLoader = new DRACOLoader(); @@ -514,20 +516,20 @@ export default function SocketResponses({ loader.setDRACOLoader(dracoLoader); // Check THREE.js cache first - const cachedModel = THREE.Cache.get(data.data.modelfileID); + const cachedModel = THREE.Cache.get(data.data.assetId); if (cachedModel) { handleModelLoad(cachedModel); return; } // Check IndexedDB cache - retrieveGLTF(data.data.modelfileID).then((cachedModelBlob) => { + retrieveGLTF(data.data.assetId).then((cachedModelBlob) => { if (cachedModelBlob) { const blobUrl = URL.createObjectURL(cachedModelBlob); loader.load(blobUrl, (gltf) => { URL.revokeObjectURL(blobUrl); THREE.Cache.remove(blobUrl); - THREE.Cache.add(data.data.modelfileID, gltf); + THREE.Cache.add(data.data.assetId, gltf); handleModelLoad(gltf); }); return; @@ -535,11 +537,11 @@ export default function SocketResponses({ }) // Load from backend if not in any cache - loader.load(`${url_Backend_dwinzo}/api/v2/AssetFile/${data.data.modelfileID}`, async (gltf) => { + loader.load(`${url_Backend_dwinzo}/api/v2/AssetFile/${data.data.assetId}`, async (gltf) => { try { - const modelBlob = await fetch(`${url_Backend_dwinzo}/api/v2/AssetFile/${data.data.modelfileID}`).then((res) => res.blob()); - await storeGLTF(data.data.modelfileID, modelBlob); - THREE.Cache.add(data.data.modelfileID, gltf); + const modelBlob = await fetch(`${url_Backend_dwinzo}/api/v2/AssetFile/${data.data.assetId}`).then((res) => res.blob()); + await storeGLTF(data.data.assetId, modelBlob); + THREE.Cache.add(data.data.assetId, gltf); await handleModelLoad(gltf); } catch (error) { @@ -562,7 +564,7 @@ export default function SocketResponses({ type: data.data.type, model: model, modelName: data.data.modelName, - modelfileID: data.data.modelfileID, + assetId: data.data.assetId, scale: data.data.scale, csgscale: data.data.csgscale, csgposition: data.data.csgposition, @@ -587,7 +589,7 @@ export default function SocketResponses({ }); } - } else if (data.message === "wallIitem updated") { + } else if (data.message === "Updated successfully") { const updatedUUID = data.data.modelUuid; setWallItems((prevItems: any) => { diff --git a/app/src/modules/market/CardsContainer.tsx b/app/src/modules/market/CardsContainer.tsx index 2afa576..aed033a 100644 --- a/app/src/modules/market/CardsContainer.tsx +++ b/app/src/modules/market/CardsContainer.tsx @@ -10,7 +10,7 @@ interface ModelData { description: string; filename: string; isArchieve: boolean; - modelfileID: string; + assetId: string; tags: string; thumbnail: string; uploadDate: number; @@ -65,7 +65,7 @@ const CardsContainer: React.FC = ({ models }) => { onSelectCard={handleCardSelect} AssetID={assetDetail.AssetID} image={assetDetail.thumbnail} - modelUrl={assetDetail.modelfileID} + modelUrl={assetDetail.assetId} description={assetDetail.description} /> diff --git a/app/src/modules/market/FilterSearch.tsx b/app/src/modules/market/FilterSearch.tsx index ebc6d3a..abf469a 100644 --- a/app/src/modules/market/FilterSearch.tsx +++ b/app/src/modules/market/FilterSearch.tsx @@ -10,7 +10,7 @@ interface ModelData { description: string; filename: string; isArchieve: boolean; - modelfileID: string; + assetId: string; tags: string; thumbnail: string; uploadDate: number; diff --git a/app/src/modules/market/MarketPlace.tsx b/app/src/modules/market/MarketPlace.tsx index ef2cd67..b02670f 100644 --- a/app/src/modules/market/MarketPlace.tsx +++ b/app/src/modules/market/MarketPlace.tsx @@ -10,7 +10,7 @@ interface ModelData { description: string; filename: string; isArchieve: boolean; - modelfileID: string; + assetId: string; tags: string; thumbnail: string; uploadDate: number; diff --git a/app/src/modules/scene/controls/selectionControls/copyPasteControls.tsx b/app/src/modules/scene/controls/selectionControls/copyPasteControls.tsx index 1e30d10..661e7ab 100644 --- a/app/src/modules/scene/controls/selectionControls/copyPasteControls.tsx +++ b/app/src/modules/scene/controls/selectionControls/copyPasteControls.tsx @@ -158,7 +158,7 @@ const CopyPasteControls = ({ const newFloorItem: Types.FloorItemType = { modelUuid: THREE.MathUtils.generateUUID(), modelName: obj.userData.modelName, - modelfileID: obj.userData.assetId, + assetId: obj.userData.assetId, position: [worldPosition.x, worldPosition.y, worldPosition.z], rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z, }, isLocked: false, @@ -352,7 +352,7 @@ const CopyPasteControls = ({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -368,7 +368,7 @@ const CopyPasteControls = ({ obj.userData = { name: newFloorItem.modelName, - modelId: newFloorItem.modelfileID, + modelId: newFloorItem.assetId, modelUuid: newFloorItem.modelUuid, eventData: JSON.parse(JSON.stringify(eventData)) }; @@ -376,7 +376,7 @@ const CopyPasteControls = ({ const asset: Asset = { modelUuid: data.modelUuid, modelName: data.modelName, - assetId: data.modelfileID, + assetId: data.assetId, position: data.position, rotation: [data.rotation.x, data.rotation.y, data.rotation.z], isLocked: data.isLocked, @@ -409,7 +409,7 @@ const CopyPasteControls = ({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -425,7 +425,7 @@ const CopyPasteControls = ({ const asset: Asset = { modelUuid: data.modelUuid, modelName: data.modelName, - assetId: data.modelfileID, + assetId: data.assetId, position: data.position, rotation: [data.rotation.x, data.rotation.y, data.rotation.z], isLocked: data.isLocked, diff --git a/app/src/modules/scene/controls/selectionControls/duplicationControls.tsx b/app/src/modules/scene/controls/selectionControls/duplicationControls.tsx index 8ef9e24..e444667 100644 --- a/app/src/modules/scene/controls/selectionControls/duplicationControls.tsx +++ b/app/src/modules/scene/controls/selectionControls/duplicationControls.tsx @@ -133,7 +133,7 @@ const DuplicationControls = ({ const newFloorItem: Types.FloorItemType = { modelUuid: THREE.MathUtils.generateUUID(), modelName: obj.userData.modelName, - modelfileID: obj.userData.assetId, + assetId: obj.userData.assetId, position: [worldPosition.x, worldPosition.y, worldPosition.z], rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z, }, isLocked: false, @@ -327,7 +327,7 @@ const DuplicationControls = ({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -344,7 +344,7 @@ const DuplicationControls = ({ const asset: Asset = { modelUuid: data.modelUuid, modelName: data.modelName, - assetId: data.modelfileID, + assetId: data.assetId, position: data.position, rotation: [data.rotation.x, data.rotation.y, data.rotation.z], isLocked: data.isLocked, @@ -378,7 +378,7 @@ const DuplicationControls = ({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -394,7 +394,7 @@ const DuplicationControls = ({ const asset: Asset = { modelUuid: data.modelUuid, modelName: data.modelName, - assetId: data.modelfileID, + assetId: data.assetId, position: data.position, rotation: [data.rotation.x, data.rotation.y, data.rotation.z], isLocked: data.isLocked, diff --git a/app/src/modules/scene/controls/selectionControls/moveControls.tsx b/app/src/modules/scene/controls/selectionControls/moveControls.tsx index f0eb5a5..0a4d8b8 100644 --- a/app/src/modules/scene/controls/selectionControls/moveControls.tsx +++ b/app/src/modules/scene/controls/selectionControls/moveControls.tsx @@ -237,7 +237,7 @@ function MoveControls({ const newFloorItem: Types.FloorItemType = { modelUuid: obj.userData.modelUuid, modelName: obj.userData.modelName, - modelfileID: obj.userData.assetId, + assetId: obj.userData.assetId, position: [worldPosition.x, worldPosition.y, worldPosition.z], rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -304,7 +304,7 @@ function MoveControls({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, diff --git a/app/src/modules/scene/controls/selectionControls/rotateControls.tsx b/app/src/modules/scene/controls/selectionControls/rotateControls.tsx index 6d78846..b2d7605 100644 --- a/app/src/modules/scene/controls/selectionControls/rotateControls.tsx +++ b/app/src/modules/scene/controls/selectionControls/rotateControls.tsx @@ -203,7 +203,7 @@ function RotateControls({ const newFloorItem: Types.FloorItemType = { modelUuid: obj.userData.modelUuid, modelName: obj.userData.modelName, - modelfileID: obj.userData.assetId, + assetId: obj.userData.assetId, position: [worldPosition.x, worldPosition.y, worldPosition.z], rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, @@ -263,7 +263,7 @@ function RotateControls({ organization, modelUuid: newFloorItem.modelUuid, modelName: newFloorItem.modelName, - modelfileID: newFloorItem.modelfileID, + assetId: newFloorItem.assetId, position: newFloorItem.position, rotation: { x: obj.rotation.x, y: obj.rotation.y, z: obj.rotation.z }, isLocked: false, diff --git a/app/src/modules/scene/controls/transformControls/transformControls.tsx b/app/src/modules/scene/controls/transformControls/transformControls.tsx index 17c2b3c..57dd707 100644 --- a/app/src/modules/scene/controls/transformControls/transformControls.tsx +++ b/app/src/modules/scene/controls/transformControls/transformControls.tsx @@ -124,7 +124,7 @@ export default function TransformControl() { organization, modelUuid: asset.modelUuid, modelName: asset.modelName, - modelfileID: asset.assetId, + assetId: asset.assetId, position: [selectedFloorItem.position.x, 0, selectedFloorItem.position.z] as [number, number, number], rotation: { x: selectedFloorItem.rotation.x, y: selectedFloorItem.rotation.y, z: selectedFloorItem.rotation.z }, isLocked: false, diff --git a/app/src/services/factoryBuilder/assest/floorAsset/getFloorItemsApi.ts b/app/src/services/factoryBuilder/assest/floorAsset/getFloorItemsApi.ts index ac96ba0..302c582 100644 --- a/app/src/services/factoryBuilder/assest/floorAsset/getFloorItemsApi.ts +++ b/app/src/services/factoryBuilder/assest/floorAsset/getFloorItemsApi.ts @@ -1,6 +1,6 @@ let url_Backend_dwinzo = `http://${process.env.REACT_APP_SERVER_REST_API_BASE_URL}`; -export const getFloorAssets = async (organization: string,projectId?:string) => { +export const getFloorAssets = async (organization: string, projectId?: string) => { try { const response = await fetch( `${url_Backend_dwinzo}/api/V1/floorAssets/${projectId}`, diff --git a/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts b/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts index d9e67e9..616c3c9 100644 --- a/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts +++ b/app/src/services/factoryBuilder/assest/floorAsset/setFloorItemApi.ts @@ -3,7 +3,7 @@ export const setFloorItemApi = async ( organization: string, modelUuid?: string, modelName?: string, - modelfileID?: string, + assetId?: string, position?: Object, rotation?: Object, isLocked?: boolean, @@ -16,7 +16,7 @@ export const setFloorItemApi = async ( modelName, position, rotation, - modelfileID, + assetId, isLocked, isVisible, }; diff --git a/app/src/services/factoryBuilder/assest/wallAsset/getWallItemsApi.ts b/app/src/services/factoryBuilder/assest/wallAsset/getWallItemsApi.ts index 096e928..e890efb 100644 --- a/app/src/services/factoryBuilder/assest/wallAsset/getWallItemsApi.ts +++ b/app/src/services/factoryBuilder/assest/wallAsset/getWallItemsApi.ts @@ -21,7 +21,6 @@ export const getWallItems = async (organization: string,projectId?:string) => { } const result = await response.json(); - // console.log('result: ', result); return result; } catch (error) { echo.error("Failed to get wall items"); diff --git a/app/src/services/factoryBuilder/webWorkers/gltfLoaderWorker.js b/app/src/services/factoryBuilder/webWorkers/gltfLoaderWorker.js index f98ad9b..66c9c81 100644 --- a/app/src/services/factoryBuilder/webWorkers/gltfLoaderWorker.js +++ b/app/src/services/factoryBuilder/webWorkers/gltfLoaderWorker.js @@ -13,14 +13,14 @@ onmessage = async (event) => { const { floorItems } = event.data; const uniqueItems = floorItems.filter((item, index, self) => - index === self.findIndex((t) => t.modelfileID === item.modelfileID) + index === self.findIndex((t) => t.assetId === item.assetId) ); for (const item of uniqueItems) { - if(item.modelfileID === null || item.modelfileID === undefined) { - continue; // Skip items without a valid modelfileID + if(item.assetId === null || item.assetId === undefined) { + continue; // Skip items without a valid assetId } - const modelID = item.modelfileID; + const modelID = item.assetId; const indexedDBModel = await retrieveGLTF(modelID); let modelBlob; diff --git a/app/src/types/world/worldTypes.d.ts b/app/src/types/world/worldTypes.d.ts index a84eb5e..da92fd9 100644 --- a/app/src/types/world/worldTypes.d.ts +++ b/app/src/types/world/worldTypes.d.ts @@ -193,7 +193,7 @@ export type FloorItemType = { modelName: string; position: [number, number, number]; rotation: { x: number; y: number; z: number }; - modelfileID: string; + assetId: string; isLocked: boolean; isVisible: boolean; eventData?: { @@ -224,7 +224,7 @@ interface WallItem { type: "fixed-move" | "free-move" | undefined; model?: THREE.Group; modelUuid?: string; - modelfileID: string; + assetId: string; modelName?: string; scale?: [number, number, number]; csgscale?: [number, number, number]; -- 2.40.1