Merge remote-tracking branch 'origin/main' into rtViz
This commit is contained in:
@@ -1,43 +1,29 @@
|
||||
import { useFloorItems } from '../../../store/store';
|
||||
import { useFloorItems, useSimulationPaths } from '../../../store/store';
|
||||
import * as THREE from 'three';
|
||||
import * as Types from '../../../types/world/worldTypes';
|
||||
import { useEffect } from 'react';
|
||||
|
||||
interface Path {
|
||||
modeluuid: string;
|
||||
modelName: string;
|
||||
points: {
|
||||
uuid: string;
|
||||
position: [number, number, number];
|
||||
rotation: [number, number, number];
|
||||
actions: { uuid: string; name: string; type: string; material: string; delay: number | string; spawnInterval: number | string; isUsed: boolean }[] | [];
|
||||
triggers: { uuid: string; name: string; type: string; isUsed: boolean }[] | [];
|
||||
connections: { source: { pathUUID: string; pointUUID: string }; targets: { pathUUID: string; pointUUID: string }[] };
|
||||
}[];
|
||||
pathPosition: [number, number, number];
|
||||
pathRotation: [number, number, number];
|
||||
speed: number;
|
||||
}
|
||||
|
||||
function Behaviour({ setSimulationPaths }: { setSimulationPaths: any }) {
|
||||
function Behaviour() {
|
||||
const { setSimulationPaths } = useSimulationPaths();
|
||||
const { floorItems } = useFloorItems();
|
||||
|
||||
useEffect(() => {
|
||||
const newPaths: Path[] = [];
|
||||
const newPaths: (Types.ConveyorEventsSchema | Types.VehicleEventsSchema)[] = [];
|
||||
|
||||
floorItems.forEach((item: Types.FloorItemType) => {
|
||||
if (item.modelfileID === "6633215057b31fe671145959") {
|
||||
const point1Position = new THREE.Vector3(0, 1.25, 3.3);
|
||||
const middlePointPosition = new THREE.Vector3(0, 1.25, 0);
|
||||
const point2Position = new THREE.Vector3(0, 1.25, -3.3);
|
||||
if (item.modelfileID === "672a090f80d91ac979f4d0bd") {
|
||||
const point1Position = new THREE.Vector3(0, 0.85, 2.2);
|
||||
const middlePointPosition = new THREE.Vector3(0, 0.85, 0);
|
||||
const point2Position = new THREE.Vector3(0, 0.85, -2.2);
|
||||
|
||||
const point1UUID = THREE.MathUtils.generateUUID();
|
||||
const middlePointUUID = THREE.MathUtils.generateUUID();
|
||||
const point2UUID = THREE.MathUtils.generateUUID();
|
||||
|
||||
const newPath: Path = {
|
||||
const newPath: Types.ConveyorEventsSchema = {
|
||||
modeluuid: item.modeluuid,
|
||||
modelName: item.modelname,
|
||||
type: 'Conveyor',
|
||||
points: [
|
||||
{
|
||||
uuid: point1UUID,
|
||||
@@ -64,12 +50,32 @@ function Behaviour({ setSimulationPaths }: { setSimulationPaths: any }) {
|
||||
connections: { source: { pathUUID: item.modeluuid, pointUUID: point2UUID }, targets: [] },
|
||||
},
|
||||
],
|
||||
pathPosition: [...item.position],
|
||||
pathRotation: [item.rotation.x, item.rotation.y, item.rotation.z],
|
||||
assetPosition: [...item.position],
|
||||
assetRotation: [item.rotation.x, item.rotation.y, item.rotation.z],
|
||||
speed: 1,
|
||||
};
|
||||
|
||||
newPaths.push(newPath);
|
||||
} else if (item.modelfileID === "67e3da19c2e8f37134526e6a") {
|
||||
const pointUUID = THREE.MathUtils.generateUUID();
|
||||
const pointPosition = new THREE.Vector3(0, 1.3, 0);
|
||||
|
||||
const newVehiclePath: Types.VehicleEventsSchema = {
|
||||
modeluuid: item.modeluuid,
|
||||
modelName: item.modelname,
|
||||
type: 'Vehicle',
|
||||
point: {
|
||||
uuid: pointUUID,
|
||||
position: [pointPosition.x, pointPosition.y, pointPosition.z],
|
||||
actions: [{ uuid: THREE.MathUtils.generateUUID(), name: 'Action 1', type: 'Start', start: THREE.MathUtils.generateUUID(), hitCount: 1, end: THREE.MathUtils.generateUUID(), buffer: 0, isUsed: false }],
|
||||
triggers: [],
|
||||
connections: { source: { pathUUID: item.modeluuid, pointUUID: pointUUID }, targets: [] },
|
||||
},
|
||||
assetPosition: [...item.position],
|
||||
speed: 2,
|
||||
};
|
||||
|
||||
newPaths.push(newVehiclePath);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { useFrame, useThree } from '@react-three/fiber';
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import * as THREE from 'three';
|
||||
import * as Types from '../../../types/world/worldTypes';
|
||||
import { QuadraticBezierLine } from '@react-three/drei';
|
||||
import { useIsConnecting, useSimulationPaths } from '../../../store/store';
|
||||
import useModuleStore from '../../../store/useModuleStore';
|
||||
@@ -27,61 +28,113 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
toPointUUID: string
|
||||
) => {
|
||||
const updatedPaths = simulationPaths.map(path => {
|
||||
if (path.modeluuid === fromPathUUID) {
|
||||
return {
|
||||
...path,
|
||||
points: path.points.map(point => {
|
||||
if (point.uuid === fromPointUUID) {
|
||||
const newTarget = {
|
||||
pathUUID: toPathUUID,
|
||||
pointUUID: toPointUUID
|
||||
};
|
||||
const existingTargets = point.connections.targets || [];
|
||||
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === newTarget.pathUUID &&
|
||||
target.pointUUID === newTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...point,
|
||||
connections: {
|
||||
...point.connections,
|
||||
targets: [...existingTargets, newTarget]
|
||||
}
|
||||
if (path.type === 'Conveyor') {
|
||||
if (path.modeluuid === fromPathUUID) {
|
||||
return {
|
||||
...path,
|
||||
points: path.points.map(point => {
|
||||
if (point.uuid === fromPointUUID) {
|
||||
const newTarget = {
|
||||
pathUUID: toPathUUID,
|
||||
pointUUID: toPointUUID
|
||||
};
|
||||
const existingTargets = point.connections.targets || [];
|
||||
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === newTarget.pathUUID &&
|
||||
target.pointUUID === newTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...point,
|
||||
connections: {
|
||||
...point.connections,
|
||||
targets: [...existingTargets, newTarget]
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
return point;
|
||||
})
|
||||
};
|
||||
return point;
|
||||
})
|
||||
};
|
||||
}
|
||||
else if (path.modeluuid === toPathUUID) {
|
||||
return {
|
||||
...path,
|
||||
points: path.points.map(point => {
|
||||
if (point.uuid === toPointUUID) {
|
||||
const reverseTarget = {
|
||||
pathUUID: fromPathUUID,
|
||||
pointUUID: fromPointUUID
|
||||
};
|
||||
const existingTargets = point.connections.targets || [];
|
||||
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === reverseTarget.pathUUID &&
|
||||
target.pointUUID === reverseTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...point,
|
||||
connections: {
|
||||
...point.connections,
|
||||
targets: [...existingTargets, reverseTarget]
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
return point;
|
||||
})
|
||||
};
|
||||
}
|
||||
}
|
||||
else if (path.modeluuid === toPathUUID) {
|
||||
return {
|
||||
...path,
|
||||
points: path.points.map(point => {
|
||||
if (point.uuid === toPointUUID) {
|
||||
const reverseTarget = {
|
||||
pathUUID: fromPathUUID,
|
||||
pointUUID: fromPointUUID
|
||||
};
|
||||
const existingTargets = point.connections.targets || [];
|
||||
else if (path.type === 'Vehicle') {
|
||||
// Handle outgoing connections from Vehicle
|
||||
if (path.modeluuid === fromPathUUID && path.point.uuid === fromPointUUID) {
|
||||
const newTarget = {
|
||||
pathUUID: toPathUUID,
|
||||
pointUUID: toPointUUID
|
||||
};
|
||||
const existingTargets = path.point.connections.targets || [];
|
||||
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === reverseTarget.pathUUID &&
|
||||
target.pointUUID === reverseTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...point,
|
||||
connections: {
|
||||
...point.connections,
|
||||
targets: [...existingTargets, reverseTarget]
|
||||
}
|
||||
};
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === newTarget.pathUUID &&
|
||||
target.pointUUID === newTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...path,
|
||||
point: {
|
||||
...path.point,
|
||||
connections: {
|
||||
...path.point.connections,
|
||||
targets: [...existingTargets, newTarget]
|
||||
}
|
||||
}
|
||||
}
|
||||
return point;
|
||||
})
|
||||
};
|
||||
};
|
||||
}
|
||||
}
|
||||
// Handle incoming connections to Vehicle
|
||||
else if (path.modeluuid === toPathUUID && path.point.uuid === toPointUUID) {
|
||||
const reverseTarget = {
|
||||
pathUUID: fromPathUUID,
|
||||
pointUUID: fromPointUUID
|
||||
};
|
||||
const existingTargets = path.point.connections.targets || [];
|
||||
|
||||
if (!existingTargets.some(target =>
|
||||
target.pathUUID === reverseTarget.pathUUID &&
|
||||
target.pointUUID === reverseTarget.pointUUID
|
||||
)) {
|
||||
return {
|
||||
...path,
|
||||
point: {
|
||||
...path.point,
|
||||
connections: {
|
||||
...path.point.connections,
|
||||
targets: [...existingTargets, reverseTarget]
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
return path;
|
||||
});
|
||||
@@ -126,25 +179,43 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
if (intersects.length > 0) {
|
||||
const intersected = intersects[0].object;
|
||||
|
||||
if (intersected.name.includes("action-sphere")) {
|
||||
if (intersected.name.includes("events-sphere")) {
|
||||
const pathUUID = intersected.userData.path.modeluuid;
|
||||
const sphereUUID = intersected.uuid;
|
||||
const worldPosition = new THREE.Vector3();
|
||||
intersected.getWorldPosition(worldPosition);
|
||||
|
||||
const isStartOrEnd = intersected.userData.path.points.length > 0 && (
|
||||
sphereUUID === intersected.userData.path.points[0].uuid ||
|
||||
sphereUUID === intersected.userData.path.points[intersected.userData.path.points.length - 1].uuid
|
||||
);
|
||||
let isStartOrEnd = false;
|
||||
|
||||
if (intersected.userData.path.points) {
|
||||
isStartOrEnd = intersected.userData.path.points.length > 0 && (
|
||||
sphereUUID === intersected.userData.path.points[0].uuid ||
|
||||
sphereUUID === intersected.userData.path.points[intersected.userData.path.points.length - 1].uuid
|
||||
);
|
||||
} else if (intersected.userData.path.point) {
|
||||
isStartOrEnd = sphereUUID === intersected.userData.path.point.uuid;
|
||||
}
|
||||
|
||||
if (pathUUID) {
|
||||
// Check if sphere is already connected
|
||||
const isAlreadyConnected = simulationPaths.some(path =>
|
||||
path.points.some(point =>
|
||||
point.uuid === sphereUUID &&
|
||||
point.connections.targets.length > 0
|
||||
)
|
||||
);
|
||||
const firstPath = simulationPaths.find(p => p.modeluuid === firstSelected?.pathUUID);
|
||||
const secondPath = simulationPaths.find(p => p.modeluuid === pathUUID);
|
||||
|
||||
if (firstPath && secondPath && firstPath.type === 'Vehicle' && secondPath.type === 'Vehicle') {
|
||||
console.log("Cannot connect two vehicle paths together");
|
||||
return;
|
||||
}
|
||||
const isAlreadyConnected = simulationPaths.some(path => {
|
||||
if (path.type === 'Conveyor') {
|
||||
return path.points.some(point =>
|
||||
point.uuid === sphereUUID &&
|
||||
point.connections.targets.length > 0
|
||||
);
|
||||
} else if (path.type === 'Vehicle') {
|
||||
return path.point.uuid === sphereUUID &&
|
||||
path.point.connections.targets.length > 0;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
if (isAlreadyConnected) {
|
||||
console.log("Sphere is already connected. Ignoring.");
|
||||
@@ -211,6 +282,7 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
raycaster.setFromCamera(pointer, camera);
|
||||
const intersects = raycaster.intersectObjects(scene.children, true).filter((intersect) =>
|
||||
!intersect.object.name.includes("Roof") &&
|
||||
!intersect.object.name.includes("agv-collider") &&
|
||||
!intersect.object.name.includes("MeasurementReference") &&
|
||||
!intersect.object.userData.isPathObject &&
|
||||
!(intersect.object.type === "GridHelper")
|
||||
@@ -229,7 +301,7 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
}
|
||||
|
||||
const sphereIntersects = raycaster.intersectObjects(pathsGroupRef.current.children, true).filter((obj) =>
|
||||
obj.object.name.includes("action-sphere")
|
||||
obj.object.name.includes("events-sphere")
|
||||
);
|
||||
|
||||
if (sphereIntersects.length > 0) {
|
||||
@@ -237,27 +309,45 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
const sphereUUID = sphere.uuid;
|
||||
const spherePosition = new THREE.Vector3();
|
||||
sphere.getWorldPosition(spherePosition);
|
||||
const pathUUID = sphere.userData.path.modeluuid;
|
||||
const pathData = sphere.userData.path;
|
||||
const pathUUID = pathData.modeluuid;
|
||||
|
||||
const isStartOrEnd = sphere.userData.path.points.length > 0 && (
|
||||
sphereUUID === sphere.userData.path.points[0].uuid ||
|
||||
sphereUUID === sphere.userData.path.points[sphere.userData.path.points.length - 1].uuid
|
||||
);
|
||||
const firstPath = simulationPaths.find(p => p.modeluuid === firstSelected.pathUUID);
|
||||
const secondPath = simulationPaths.find(p => p.modeluuid === pathUUID);
|
||||
const isVehicleToVehicle = firstPath?.type === 'Vehicle' && secondPath?.type === 'Vehicle';
|
||||
|
||||
const isAlreadyConnected = simulationPaths.some(path =>
|
||||
path.points.some(point =>
|
||||
point.uuid === sphereUUID &&
|
||||
point.connections.targets.length > 0
|
||||
)
|
||||
);
|
||||
const isConnectable = (pathData.type === 'Vehicle' ||
|
||||
(pathData.points.length > 0 && (
|
||||
sphereUUID === pathData.points[0].uuid ||
|
||||
sphereUUID === pathData.points[pathData.points.length - 1].uuid
|
||||
))) && !isVehicleToVehicle;
|
||||
|
||||
const isAlreadyConnected = simulationPaths.some(path => {
|
||||
if (path.type === 'Conveyor') {
|
||||
return path.points.some(point =>
|
||||
point.uuid === sphereUUID &&
|
||||
point.connections.targets.length > 0
|
||||
);
|
||||
} else if (path.type === 'Vehicle') {
|
||||
return path.point.uuid === sphereUUID &&
|
||||
path.point.connections.targets.length > 0;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
if (
|
||||
!isAlreadyConnected &&
|
||||
!isVehicleToVehicle &&
|
||||
firstSelected.sphereUUID !== sphereUUID &&
|
||||
firstSelected.pathUUID !== pathUUID &&
|
||||
(firstSelected.isCorner || isStartOrEnd)
|
||||
(firstSelected.isCorner || isConnectable)
|
||||
) {
|
||||
snappedSphere = { sphereUUID, position: spherePosition, pathUUID, isCorner: isStartOrEnd };
|
||||
snappedSphere = {
|
||||
sphereUUID,
|
||||
position: spherePosition,
|
||||
pathUUID,
|
||||
isCorner: isConnectable
|
||||
};
|
||||
} else {
|
||||
isInvalidConnection = true;
|
||||
}
|
||||
@@ -281,8 +371,13 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
end: point,
|
||||
mid: midPoint,
|
||||
});
|
||||
console.log({
|
||||
start: firstSelected.position,
|
||||
end: point,
|
||||
mid: midPoint,
|
||||
});
|
||||
|
||||
setIsConnecting(true);
|
||||
// setIsConnecting(true);
|
||||
|
||||
if (sphereIntersects.length > 0) {
|
||||
setHelperLineColor(isInvalidConnection ? 'red' : '#6cf542');
|
||||
@@ -299,13 +394,53 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
}
|
||||
});
|
||||
|
||||
// Render connections from simulationPaths
|
||||
return (
|
||||
<>
|
||||
{simulationPaths.flatMap(path =>
|
||||
path.points.flatMap(point =>
|
||||
point.connections.targets.map((target, index) => {
|
||||
const fromSphere = pathsGroupRef.current?.getObjectByProperty('uuid', point.uuid);
|
||||
{simulationPaths.flatMap(path => {
|
||||
if (path.type === 'Conveyor') {
|
||||
return path.points.flatMap(point =>
|
||||
point.connections.targets.map((target, index) => {
|
||||
const targetPath = simulationPaths.find(p => p.modeluuid === target.pathUUID);
|
||||
if (targetPath?.type === 'Vehicle') return null;
|
||||
|
||||
const fromSphere = pathsGroupRef.current?.getObjectByProperty('uuid', point.uuid);
|
||||
const toSphere = pathsGroupRef.current?.getObjectByProperty('uuid', target.pointUUID);
|
||||
|
||||
if (fromSphere && toSphere) {
|
||||
const fromWorldPosition = new THREE.Vector3();
|
||||
const toWorldPosition = new THREE.Vector3();
|
||||
fromSphere.getWorldPosition(fromWorldPosition);
|
||||
toSphere.getWorldPosition(toWorldPosition);
|
||||
|
||||
const distance = fromWorldPosition.distanceTo(toWorldPosition);
|
||||
const heightFactor = Math.max(0.5, distance * 0.2);
|
||||
|
||||
const midPoint = new THREE.Vector3(
|
||||
(fromWorldPosition.x + toWorldPosition.x) / 2,
|
||||
Math.max(fromWorldPosition.y, toWorldPosition.y) + heightFactor,
|
||||
(fromWorldPosition.z + toWorldPosition.z) / 2
|
||||
);
|
||||
|
||||
return (
|
||||
<QuadraticBezierLine
|
||||
key={`${point.uuid}-${target.pointUUID}-${index}`}
|
||||
start={fromWorldPosition.toArray()}
|
||||
end={toWorldPosition.toArray()}
|
||||
mid={midPoint.toArray()}
|
||||
color="white"
|
||||
lineWidth={4}
|
||||
dashed
|
||||
dashSize={0.75}
|
||||
dashScale={20}
|
||||
/>
|
||||
);
|
||||
}
|
||||
return null;
|
||||
})
|
||||
);
|
||||
} else if (path.type === 'Vehicle') {
|
||||
return path.point.connections.targets.map((target, index) => {
|
||||
const fromSphere = pathsGroupRef.current?.getObjectByProperty('uuid', path.point.uuid);
|
||||
const toSphere = pathsGroupRef.current?.getObjectByProperty('uuid', target.pointUUID);
|
||||
|
||||
if (fromSphere && toSphere) {
|
||||
@@ -325,22 +460,23 @@ function PathConnector({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObjec
|
||||
|
||||
return (
|
||||
<QuadraticBezierLine
|
||||
key={`${point.uuid}-${target.pointUUID}-${index}`}
|
||||
key={`${path.point.uuid}-${target.pointUUID}-${index}`}
|
||||
start={fromWorldPosition.toArray()}
|
||||
end={toWorldPosition.toArray()}
|
||||
mid={midPoint.toArray()}
|
||||
color="white"
|
||||
color="orange"
|
||||
lineWidth={4}
|
||||
dashed
|
||||
dashSize={1}
|
||||
dashSize={0.75}
|
||||
dashScale={20}
|
||||
/>
|
||||
);
|
||||
}
|
||||
return null;
|
||||
})
|
||||
)
|
||||
)}
|
||||
});
|
||||
}
|
||||
return [];
|
||||
})}
|
||||
|
||||
{currentLine && (
|
||||
<QuadraticBezierLine
|
||||
|
||||
@@ -4,10 +4,12 @@ import { Sphere, TransformControls } from '@react-three/drei';
|
||||
import { useIsConnecting, useRenderDistance, useSelectedActionSphere, useSelectedPath, useSimulationPaths } from '../../../store/store';
|
||||
import { useFrame, useThree } from '@react-three/fiber';
|
||||
import { useSubModuleStore } from '../../../store/useModuleStore';
|
||||
import { point } from '@turf/helpers';
|
||||
|
||||
interface Path {
|
||||
interface ConveyorEventsSchema {
|
||||
modeluuid: string;
|
||||
modelName: string;
|
||||
type: 'Conveyor';
|
||||
points: {
|
||||
uuid: string;
|
||||
position: [number, number, number];
|
||||
@@ -16,8 +18,8 @@ interface Path {
|
||||
triggers: { uuid: string; name: string; type: string; isUsed: boolean }[] | [];
|
||||
connections: { source: { pathUUID: string; pointUUID: string }; targets: { pathUUID: string; pointUUID: string }[] };
|
||||
}[];
|
||||
pathPosition: [number, number, number];
|
||||
pathRotation: [number, number, number];
|
||||
assetPosition: [number, number, number];
|
||||
assetRotation: [number, number, number];
|
||||
speed: number;
|
||||
}
|
||||
|
||||
@@ -63,99 +65,154 @@ function PathCreation({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObject
|
||||
const updateSimulationPaths = () => {
|
||||
if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths: Path[] = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
position: [
|
||||
selectedActionSphere.point.position.x,
|
||||
selectedActionSphere.point.position.y,
|
||||
selectedActionSphere.point.position.z,
|
||||
],
|
||||
rotation: [
|
||||
selectedActionSphere.point.rotation.x,
|
||||
selectedActionSphere.point.rotation.y,
|
||||
selectedActionSphere.point.rotation.z,
|
||||
]
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
const updatedPaths = simulationPaths.map((path) => {
|
||||
if (path.type === "Conveyor") {
|
||||
return {
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
position: [
|
||||
selectedActionSphere.point.position.x,
|
||||
selectedActionSphere.point.position.y,
|
||||
selectedActionSphere.point.position.z,
|
||||
],
|
||||
rotation: [
|
||||
selectedActionSphere.point.rotation.x,
|
||||
selectedActionSphere.point.rotation.y,
|
||||
selectedActionSphere.point.rotation.z,
|
||||
]
|
||||
}
|
||||
: point
|
||||
),
|
||||
};
|
||||
}
|
||||
return path;
|
||||
}) as ConveyorEventsSchema[];
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
|
||||
|
||||
return (
|
||||
<group name='simulation-simulationPaths-group' ref={pathsGroupRef} >
|
||||
<group name='simulation-simulationPaths-group' ref={pathsGroupRef}>
|
||||
{simulationPaths.map((path) => {
|
||||
const points = path.points.map(point => new THREE.Vector3(...point.position));
|
||||
if (path.type === 'Conveyor') {
|
||||
const points = path.points.map(point => new THREE.Vector3(...point.position));
|
||||
|
||||
return (
|
||||
<group
|
||||
name={`${path.modeluuid}-event-path`}
|
||||
key={path.modeluuid}
|
||||
ref={el => (groupRefs.current[path.modeluuid] = el!)}
|
||||
position={path.pathPosition}
|
||||
rotation={path.pathRotation}
|
||||
onClick={(e) => {
|
||||
if (isConnecting) return;
|
||||
e.stopPropagation();
|
||||
setSelectedPath({ path, group: groupRefs.current[path.modeluuid] });
|
||||
setSelectedActionSphere(null);
|
||||
setTransformMode(null);
|
||||
setSubModule('mechanics');
|
||||
}}
|
||||
onPointerMissed={() => {
|
||||
setSelectedPath(null);
|
||||
setSubModule('properties');
|
||||
}}
|
||||
>
|
||||
{path.points.map((point, index) => (
|
||||
return (
|
||||
<group
|
||||
name={`${path.modeluuid}-event-path`}
|
||||
key={path.modeluuid}
|
||||
ref={el => (groupRefs.current[path.modeluuid] = el!)}
|
||||
position={path.assetPosition}
|
||||
rotation={path.assetRotation}
|
||||
onClick={(e) => {
|
||||
if (isConnecting) return;
|
||||
e.stopPropagation();
|
||||
setSelectedPath({ path, group: groupRefs.current[path.modeluuid] });
|
||||
setSelectedActionSphere(null);
|
||||
setTransformMode(null);
|
||||
setSubModule('mechanics');
|
||||
}}
|
||||
onPointerMissed={() => {
|
||||
setSelectedPath(null);
|
||||
setSubModule('properties');
|
||||
}}
|
||||
>
|
||||
{path.points.map((point, index) => (
|
||||
<Sphere
|
||||
key={point.uuid}
|
||||
uuid={point.uuid}
|
||||
position={point.position}
|
||||
args={[0.15, 32, 32]}
|
||||
name='events-sphere'
|
||||
ref={el => (sphereRefs.current[point.uuid] = el!)}
|
||||
onClick={(e) => {
|
||||
if (isConnecting) return;
|
||||
e.stopPropagation();
|
||||
setSelectedActionSphere({
|
||||
path,
|
||||
point: sphereRefs.current[point.uuid]
|
||||
});
|
||||
setSubModule('mechanics');
|
||||
setSelectedPath(null);
|
||||
}}
|
||||
userData={{ point, path }}
|
||||
onPointerMissed={() => {
|
||||
setSubModule('properties');
|
||||
setSelectedActionSphere(null);
|
||||
}}
|
||||
>
|
||||
<meshStandardMaterial
|
||||
color={index === 0 ? 'orange' : index === path.points.length - 1 ? 'blue' : 'green'}
|
||||
/>
|
||||
</Sphere>
|
||||
))}
|
||||
|
||||
{points.slice(0, -1).map((point, index) => {
|
||||
const nextPoint = points[index + 1];
|
||||
const segmentCurve = new THREE.CatmullRomCurve3([point, nextPoint]);
|
||||
const tubeGeometry = new THREE.TubeGeometry(segmentCurve, 20, 0.1, 16, false);
|
||||
|
||||
return (
|
||||
<mesh name='event-connection-tube' key={`tube-${index}`} geometry={tubeGeometry}>
|
||||
<meshStandardMaterial transparent opacity={0.9} color="red" />
|
||||
</mesh>
|
||||
);
|
||||
})}
|
||||
</group>
|
||||
);
|
||||
} else if (path.type === 'Vehicle') {
|
||||
return (
|
||||
<group
|
||||
name={`${path.modeluuid}-vehicle-path`}
|
||||
key={path.modeluuid}
|
||||
ref={el => (groupRefs.current[path.modeluuid] = el!)}
|
||||
position={path.assetPosition}
|
||||
onClick={(e) => {
|
||||
if (isConnecting) return;
|
||||
e.stopPropagation();
|
||||
setSelectedPath({ path, group: groupRefs.current[path.modeluuid] });
|
||||
setSelectedActionSphere(null);
|
||||
setTransformMode(null);
|
||||
setSubModule('mechanics');
|
||||
}}
|
||||
onPointerMissed={() => {
|
||||
setSelectedPath(null);
|
||||
setSubModule('properties');
|
||||
}}
|
||||
>
|
||||
<Sphere
|
||||
key={point.uuid}
|
||||
uuid={point.uuid}
|
||||
position={point.position}
|
||||
key={path.point.uuid}
|
||||
uuid={path.point.uuid}
|
||||
position={path.point.position}
|
||||
args={[0.15, 32, 32]}
|
||||
name='action-sphere'
|
||||
ref={el => (sphereRefs.current[point.uuid] = el!)}
|
||||
name='events-sphere'
|
||||
ref={el => (sphereRefs.current[path.point.uuid] = el!)}
|
||||
onClick={(e) => {
|
||||
if (isConnecting) return;
|
||||
e.stopPropagation();
|
||||
setSelectedActionSphere({
|
||||
path,
|
||||
point: sphereRefs.current[point.uuid]
|
||||
point: sphereRefs.current[path.point.uuid]
|
||||
});
|
||||
setSubModule('mechanics');
|
||||
setSelectedPath(null);
|
||||
}}
|
||||
userData={{ point, path }}
|
||||
userData={{ point: path.point, path }}
|
||||
onPointerMissed={() => {
|
||||
setSubModule('properties');
|
||||
setSelectedActionSphere(null)
|
||||
setSelectedActionSphere(null);
|
||||
}}
|
||||
>
|
||||
<meshStandardMaterial
|
||||
color={index === 0 ? 'orange' : index === path.points.length - 1 ? 'blue' : 'green'}
|
||||
/>
|
||||
<meshStandardMaterial color="purple" />
|
||||
</Sphere>
|
||||
))}
|
||||
|
||||
{points.slice(0, -1).map((point, index) => {
|
||||
const nextPoint = points[index + 1];
|
||||
const segmentCurve = new THREE.CatmullRomCurve3([point, nextPoint]);
|
||||
const tubeGeometry = new THREE.TubeGeometry(segmentCurve, 20, 0.1, 16, false);
|
||||
|
||||
return (
|
||||
<mesh name='event-connection-tube' key={`tube-${index}`} geometry={tubeGeometry}>
|
||||
<meshStandardMaterial transparent opacity={0.9} color="red" />
|
||||
</mesh>
|
||||
);
|
||||
})}
|
||||
</group>
|
||||
);
|
||||
</group>
|
||||
);
|
||||
}
|
||||
return null;
|
||||
})}
|
||||
|
||||
{selectedActionSphere && transformMode && (
|
||||
@@ -163,7 +220,7 @@ function PathCreation({ pathsGroupRef }: { pathsGroupRef: React.MutableRefObject
|
||||
ref={transformRef}
|
||||
object={selectedActionSphere.point}
|
||||
mode={transformMode}
|
||||
onObjectChange={updateSimulationPaths}
|
||||
onMouseUp={updateSimulationPaths}
|
||||
/>
|
||||
)}
|
||||
</group>
|
||||
|
||||
@@ -31,7 +31,7 @@ function Simulation() {
|
||||
|
||||
return (
|
||||
<>
|
||||
<Behaviour setSimulationPaths={setSimulationPaths} />
|
||||
<Behaviour/>
|
||||
{activeModule === 'simulation' && (
|
||||
<>
|
||||
<PathCreation pathsGroupRef={pathsGroupRef} />
|
||||
|
||||
@@ -1,409 +1,409 @@
|
||||
import { useMemo, useState } from 'react';
|
||||
import { useSelectedActionSphere, useToggleView, useSimulationPaths, useSelectedPath, useStartSimulation, useDrawMaterialPath } from '../../store/store';
|
||||
import * as THREE from 'three';
|
||||
import useModuleStore from '../../store/useModuleStore';
|
||||
// import { useMemo, useState } from 'react';
|
||||
// import { useSelectedActionSphere, useToggleView, useSimulationPaths, useSelectedPath, useStartSimulation, useDrawMaterialPath } from '../../store/store';
|
||||
// import * as THREE from 'three';
|
||||
// import useModuleStore from '../../store/useModuleStore';
|
||||
|
||||
function SimulationUI() {
|
||||
const { ToggleView } = useToggleView();
|
||||
const { activeModule } = useModuleStore();
|
||||
const { startSimulation, setStartSimulation } = useStartSimulation();
|
||||
const { selectedActionSphere } = useSelectedActionSphere();
|
||||
const { selectedPath, setSelectedPath } = useSelectedPath();
|
||||
const { simulationPaths, setSimulationPaths } = useSimulationPaths();
|
||||
const { drawMaterialPath, setDrawMaterialPath } = useDrawMaterialPath();
|
||||
const [activeButton, setActiveButton] = useState<string | null>(null);
|
||||
// function SimulationUI() {
|
||||
// const { ToggleView } = useToggleView();
|
||||
// const { activeModule } = useModuleStore();
|
||||
// const { startSimulation, setStartSimulation } = useStartSimulation();
|
||||
// const { selectedActionSphere } = useSelectedActionSphere();
|
||||
// const { selectedPath, setSelectedPath } = useSelectedPath();
|
||||
// const { simulationPaths, setSimulationPaths } = useSimulationPaths();
|
||||
// const { drawMaterialPath, setDrawMaterialPath } = useDrawMaterialPath();
|
||||
// const [activeButton, setActiveButton] = useState<string | null>(null);
|
||||
|
||||
const handleAddAction = () => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleAddAction = () => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) => {
|
||||
if (point.uuid === selectedActionSphere.point.uuid) {
|
||||
const actionIndex = point.actions.length;
|
||||
const newAction = {
|
||||
uuid: THREE.MathUtils.generateUUID(),
|
||||
name: `Action ${actionIndex + 1}`, // Assign action name based on index
|
||||
type: 'Inherit',
|
||||
material: 'Inherit',
|
||||
delay: 'Inherit',
|
||||
spawnInterval: 'Inherit',
|
||||
isUsed: false
|
||||
};
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) => {
|
||||
// if (point.uuid === selectedActionSphere.point.uuid) {
|
||||
// const actionIndex = point.actions.length;
|
||||
// const newAction = {
|
||||
// uuid: THREE.MathUtils.generateUUID(),
|
||||
// name: `Action ${actionIndex + 1}`, // Assign action name based on index
|
||||
// type: 'Inherit',
|
||||
// material: 'Inherit',
|
||||
// delay: 'Inherit',
|
||||
// spawnInterval: 'Inherit',
|
||||
// isUsed: false
|
||||
// };
|
||||
|
||||
return { ...point, actions: [...point.actions, newAction] };
|
||||
}
|
||||
return point;
|
||||
}),
|
||||
}));
|
||||
// return { ...point, actions: [...point.actions, newAction] };
|
||||
// }
|
||||
// return point;
|
||||
// }),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleDeleteAction = (uuid: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleDeleteAction = (uuid: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? { ...point, actions: point.actions.filter(action => action.uuid !== uuid) }
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? { ...point, actions: point.actions.filter(action => action.uuid !== uuid) }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleActionSelect = (uuid: string, actionType: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleActionSelect = (uuid: string, actionType: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
actions: point.actions.map((action) =>
|
||||
action.uuid === uuid ? { ...action, type: actionType } : action
|
||||
),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// actions: point.actions.map((action) =>
|
||||
// action.uuid === uuid ? { ...action, type: actionType } : action
|
||||
// ),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleMaterialSelect = (uuid: string, material: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleMaterialSelect = (uuid: string, material: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
actions: point.actions.map((action) =>
|
||||
action.uuid === uuid ? { ...action, material } : action
|
||||
),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// actions: point.actions.map((action) =>
|
||||
// action.uuid === uuid ? { ...action, material } : action
|
||||
// ),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleDelayChange = (uuid: string, delay: number | string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleDelayChange = (uuid: string, delay: number | string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
actions: point.actions.map((action) =>
|
||||
action.uuid === uuid ? { ...action, delay } : action
|
||||
),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// actions: point.actions.map((action) =>
|
||||
// action.uuid === uuid ? { ...action, delay } : action
|
||||
// ),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleSpawnIntervalChange = (uuid: string, spawnInterval: number | string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleSpawnIntervalChange = (uuid: string, spawnInterval: number | string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
actions: point.actions.map((action) =>
|
||||
action.uuid === uuid ? { ...action, spawnInterval } : action
|
||||
),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// actions: point.actions.map((action) =>
|
||||
// action.uuid === uuid ? { ...action, spawnInterval } : action
|
||||
// ),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleSpeedChange = (speed: number) => {
|
||||
if (!selectedPath) return;
|
||||
// const handleSpeedChange = (speed: number) => {
|
||||
// if (!selectedPath) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) =>
|
||||
path.modeluuid === selectedPath.path.modeluuid ? { ...path, speed } : path
|
||||
);
|
||||
// const updatedPaths = simulationPaths.map((path) =>
|
||||
// path.modeluuid === selectedPath.path.modeluuid ? { ...path, speed } : path
|
||||
// );
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
setSelectedPath({ ...selectedPath, path: { ...selectedPath.path, speed } });
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// setSelectedPath({ ...selectedPath, path: { ...selectedPath.path, speed } });
|
||||
// };
|
||||
|
||||
const handleAddTrigger = () => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleAddTrigger = () => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) => {
|
||||
if (point.uuid === selectedActionSphere.point.uuid) {
|
||||
const triggerIndex = point.triggers.length;
|
||||
const newTrigger = {
|
||||
uuid: THREE.MathUtils.generateUUID(),
|
||||
name: `Trigger ${triggerIndex + 1}`, // Assign name based on index
|
||||
type: '',
|
||||
isUsed: false
|
||||
};
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) => {
|
||||
// if (point.uuid === selectedActionSphere.point.uuid) {
|
||||
// const triggerIndex = point.triggers.length;
|
||||
// const newTrigger = {
|
||||
// uuid: THREE.MathUtils.generateUUID(),
|
||||
// name: `Trigger ${triggerIndex + 1}`, // Assign name based on index
|
||||
// type: '',
|
||||
// isUsed: false
|
||||
// };
|
||||
|
||||
return { ...point, triggers: [...point.triggers, newTrigger] };
|
||||
}
|
||||
return point;
|
||||
}),
|
||||
}));
|
||||
// return { ...point, triggers: [...point.triggers, newTrigger] };
|
||||
// }
|
||||
// return point;
|
||||
// }),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleDeleteTrigger = (uuid: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleDeleteTrigger = (uuid: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? { ...point, triggers: point.triggers.filter(trigger => trigger.uuid !== uuid) }
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? { ...point, triggers: point.triggers.filter(trigger => trigger.uuid !== uuid) }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleTriggerSelect = (uuid: string, triggerType: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleTriggerSelect = (uuid: string, triggerType: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
triggers: point.triggers.map((trigger) =>
|
||||
trigger.uuid === uuid ? { ...trigger, type: triggerType } : trigger
|
||||
),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// triggers: point.triggers.map((trigger) =>
|
||||
// trigger.uuid === uuid ? { ...trigger, type: triggerType } : trigger
|
||||
// ),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleResetPath = () => {
|
||||
if (!selectedPath) return;
|
||||
// const handleResetPath = () => {
|
||||
// if (!selectedPath) return;
|
||||
|
||||
};
|
||||
// };
|
||||
|
||||
|
||||
const handleActionToggle = (uuid: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleActionToggle = (uuid: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
actions: point.actions.map((action) => ({
|
||||
...action,
|
||||
isUsed: action.uuid === uuid ? !action.isUsed : false,
|
||||
})),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// actions: point.actions.map((action) => ({
|
||||
// ...action,
|
||||
// isUsed: action.uuid === uuid ? !action.isUsed : false,
|
||||
// })),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const handleTriggerToggle = (uuid: string) => {
|
||||
if (!selectedActionSphere) return;
|
||||
// const handleTriggerToggle = (uuid: string) => {
|
||||
// if (!selectedActionSphere) return;
|
||||
|
||||
const updatedPaths = simulationPaths.map((path) => ({
|
||||
...path,
|
||||
points: path.points.map((point) =>
|
||||
point.uuid === selectedActionSphere.point.uuid
|
||||
? {
|
||||
...point,
|
||||
triggers: point.triggers.map((trigger) => ({
|
||||
...trigger,
|
||||
isUsed: trigger.uuid === uuid ? !trigger.isUsed : false,
|
||||
})),
|
||||
}
|
||||
: point
|
||||
),
|
||||
}));
|
||||
// const updatedPaths = simulationPaths.map((path) => ({
|
||||
// ...path,
|
||||
// points: path.points.map((point) =>
|
||||
// point.uuid === selectedActionSphere.point.uuid
|
||||
// ? {
|
||||
// ...point,
|
||||
// triggers: point.triggers.map((trigger) => ({
|
||||
// ...trigger,
|
||||
// isUsed: trigger.uuid === uuid ? !trigger.isUsed : false,
|
||||
// })),
|
||||
// }
|
||||
// : point
|
||||
// ),
|
||||
// }));
|
||||
|
||||
setSimulationPaths(updatedPaths);
|
||||
};
|
||||
// setSimulationPaths(updatedPaths);
|
||||
// };
|
||||
|
||||
const selectedPoint = useMemo(() => {
|
||||
if (!selectedActionSphere) return null;
|
||||
return simulationPaths.flatMap((path) => path.points).find((point) => point.uuid === selectedActionSphere.point.uuid);
|
||||
}, [selectedActionSphere, simulationPaths]);
|
||||
// const selectedPoint = useMemo(() => {
|
||||
// if (!selectedActionSphere) return null;
|
||||
// return simulationPaths.flatMap((path) => path.points).find((point) => point.uuid === selectedActionSphere.point.uuid);
|
||||
// }, [selectedActionSphere, simulationPaths]);
|
||||
|
||||
const createPath = () => {
|
||||
setActiveButton(activeButton !== 'addMaterialPath' ? 'addMaterialPath' : null);
|
||||
setDrawMaterialPath(!drawMaterialPath);
|
||||
}
|
||||
// const createPath = () => {
|
||||
// setActiveButton(activeButton !== 'addMaterialPath' ? 'addMaterialPath' : null);
|
||||
// setDrawMaterialPath(!drawMaterialPath);
|
||||
// }
|
||||
|
||||
return (
|
||||
<>
|
||||
{activeModule === "simulation" && (
|
||||
<div style={{ zIndex: 10, position: "fixed", width: '260px' }}>
|
||||
{!ToggleView && (
|
||||
<>
|
||||
<button
|
||||
onClick={() => setStartSimulation(!startSimulation)}
|
||||
style={{
|
||||
marginTop: "10px",
|
||||
background: startSimulation ? '#ff320e' : '',
|
||||
padding: "10px",
|
||||
borderRadius: "5px"
|
||||
}}
|
||||
>
|
||||
{startSimulation ? 'Stop Simulation' : 'Start Simulation'}
|
||||
</button>
|
||||
// return (
|
||||
// <>
|
||||
// {activeModule === "simulation" && (
|
||||
// <div style={{ zIndex: 10, position: "fixed", width: '260px' }}>
|
||||
// {!ToggleView && (
|
||||
// <>
|
||||
// <button
|
||||
// onClick={() => setStartSimulation(!startSimulation)}
|
||||
// style={{
|
||||
// marginTop: "10px",
|
||||
// background: startSimulation ? '#ff320e' : '',
|
||||
// padding: "10px",
|
||||
// borderRadius: "5px"
|
||||
// }}
|
||||
// >
|
||||
// {startSimulation ? 'Stop Simulation' : 'Start Simulation'}
|
||||
// </button>
|
||||
|
||||
<div style={{ zIndex: "10", position: "relative" }}>
|
||||
{!ToggleView && <button onClick={createPath} style={{ marginTop: "10px", background: activeButton === 'addMaterialPath' ? '#ff320e' : '' }}> Add Material Path</button>}
|
||||
</div>
|
||||
// <div style={{ zIndex: "10", position: "relative" }}>
|
||||
// {!ToggleView && <button onClick={createPath} style={{ marginTop: "10px", background: activeButton === 'addMaterialPath' ? '#ff320e' : '' }}> Add Material Path</button>}
|
||||
// </div>
|
||||
|
||||
{selectedPath && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<label>Path Speed:</label>
|
||||
<input
|
||||
style={{ width: '50px' }}
|
||||
type="number"
|
||||
value={selectedPath.path.speed}
|
||||
min="0.1"
|
||||
step="0.1"
|
||||
onChange={(e) => handleSpeedChange(parseFloat(e.target.value))}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
// {selectedPath && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <label>Path Speed:</label>
|
||||
// <input
|
||||
// style={{ width: '50px' }}
|
||||
// type="number"
|
||||
// value={selectedPath.path.speed}
|
||||
// min="0.1"
|
||||
// step="0.1"
|
||||
// onChange={(e) => handleSpeedChange(parseFloat(e.target.value))}
|
||||
// />
|
||||
// </div>
|
||||
// )}
|
||||
|
||||
{selectedActionSphere && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<button onClick={handleAddAction}>Add Action</button>
|
||||
<button onClick={handleAddTrigger}>Add Trigger</button>
|
||||
// {selectedActionSphere && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <button onClick={handleAddAction}>Add Action</button>
|
||||
// <button onClick={handleAddTrigger}>Add Trigger</button>
|
||||
|
||||
{selectedPoint?.actions.map((action) => (
|
||||
<div key={action.uuid} style={{ marginTop: "10px" }}>
|
||||
<select value={action.type} onChange={(e) => handleActionSelect(action.uuid, e.target.value)}>
|
||||
<option value="Inherit">Inherit</option>
|
||||
<option value="Spawn">Spawn Point</option>
|
||||
<option value="Swap">Swap Material</option>
|
||||
<option value="Despawn">Despawn Point</option>
|
||||
<option value="Delay">Delay</option>
|
||||
</select>
|
||||
<button onClick={() => handleDeleteAction(action.uuid)}>Delete Action</button>
|
||||
<label>
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={action.isUsed}
|
||||
onChange={() => handleActionToggle(action.uuid)}
|
||||
/>
|
||||
</label>
|
||||
// {selectedPoint?.actions.map((action) => (
|
||||
// <div key={action.uuid} style={{ marginTop: "10px" }}>
|
||||
// <select value={action.type} onChange={(e) => handleActionSelect(action.uuid, e.target.value)}>
|
||||
// <option value="Inherit">Inherit</option>
|
||||
// <option value="Spawn">Spawn Point</option>
|
||||
// <option value="Swap">Swap Material</option>
|
||||
// <option value="Despawn">Despawn Point</option>
|
||||
// <option value="Delay">Delay</option>
|
||||
// </select>
|
||||
// <button onClick={() => handleDeleteAction(action.uuid)}>Delete Action</button>
|
||||
// <label>
|
||||
// <input
|
||||
// type="checkbox"
|
||||
// checked={action.isUsed}
|
||||
// onChange={() => handleActionToggle(action.uuid)}
|
||||
// />
|
||||
// </label>
|
||||
|
||||
{(action.type === 'Spawn' || action.type === 'Swap') && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<select value={action.material} onChange={(e) => handleMaterialSelect(action.uuid, e.target.value)}>
|
||||
<option value="Inherit">Inherit</option>
|
||||
<option value="Crate">Crate</option>
|
||||
<option value="Box">Box</option>
|
||||
</select>
|
||||
</div>
|
||||
)}
|
||||
// {(action.type === 'Spawn' || action.type === 'Swap') && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <select value={action.material} onChange={(e) => handleMaterialSelect(action.uuid, e.target.value)}>
|
||||
// <option value="Inherit">Inherit</option>
|
||||
// <option value="Crate">Crate</option>
|
||||
// <option value="Box">Box</option>
|
||||
// </select>
|
||||
// </div>
|
||||
// )}
|
||||
|
||||
{action.type === 'Delay' && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<label>Delay Time:</label>
|
||||
<input
|
||||
style={{ width: '50px' }}
|
||||
type="text"
|
||||
value={isNaN(Number(action.delay)) || action.delay === "Inherit" ? "Inherit" : action.delay}
|
||||
min="1"
|
||||
onChange={(e) => handleDelayChange(action.uuid, parseInt(e.target.value) || 'Inherit')}
|
||||
/>
|
||||
// {action.type === 'Delay' && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <label>Delay Time:</label>
|
||||
// <input
|
||||
// style={{ width: '50px' }}
|
||||
// type="text"
|
||||
// value={isNaN(Number(action.delay)) || action.delay === "Inherit" ? "Inherit" : action.delay}
|
||||
// min="1"
|
||||
// onChange={(e) => handleDelayChange(action.uuid, parseInt(e.target.value) || 'Inherit')}
|
||||
// />
|
||||
|
||||
</div>
|
||||
)}
|
||||
// </div>
|
||||
// )}
|
||||
|
||||
{action.type === 'Spawn' && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<label>Spawn Interval:</label>
|
||||
<input
|
||||
style={{ width: '50px' }}
|
||||
type="text"
|
||||
value={isNaN(Number(action.spawnInterval)) || action.spawnInterval === "Inherit" ? "Inherit" : action.spawnInterval}
|
||||
min="1"
|
||||
onChange={(e) => handleSpawnIntervalChange(action.uuid, parseInt(e.target.value) || 'Inherit')}
|
||||
/>
|
||||
// {action.type === 'Spawn' && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <label>Spawn Interval:</label>
|
||||
// <input
|
||||
// style={{ width: '50px' }}
|
||||
// type="text"
|
||||
// value={isNaN(Number(action.spawnInterval)) || action.spawnInterval === "Inherit" ? "Inherit" : action.spawnInterval}
|
||||
// min="1"
|
||||
// onChange={(e) => handleSpawnIntervalChange(action.uuid, parseInt(e.target.value) || 'Inherit')}
|
||||
// />
|
||||
|
||||
</div>
|
||||
)}
|
||||
<hr style={{ margin: "10px 0", borderColor: "#ccc" }} />
|
||||
</div>
|
||||
))}
|
||||
// </div>
|
||||
// )}
|
||||
// <hr style={{ margin: "10px 0", borderColor: "#ccc" }} />
|
||||
// </div>
|
||||
// ))}
|
||||
|
||||
<hr style={{ margin: "10px 0", border: "1px solid black" }} />
|
||||
// <hr style={{ margin: "10px 0", border: "1px solid black" }} />
|
||||
|
||||
{selectedPoint?.triggers.map((trigger) => (
|
||||
<div key={trigger.uuid} style={{ marginTop: "10px" }}>
|
||||
<select value={trigger.type} onChange={(e) => handleTriggerSelect(trigger.uuid, e.target.value)}>
|
||||
<option value="">Select Trigger Type</option>
|
||||
<option value="On-Hit">On Hit</option>
|
||||
<option value="Buffer">Buffer</option>
|
||||
</select>
|
||||
<button onClick={() => handleDeleteTrigger(trigger.uuid)}>Delete Trigger</button>
|
||||
<label>
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={trigger.isUsed}
|
||||
onChange={() => handleTriggerToggle(trigger.uuid)}
|
||||
/>
|
||||
</label>
|
||||
<hr style={{ margin: "10px 0", borderColor: "#ccc" }} />
|
||||
</div>
|
||||
))}
|
||||
// {selectedPoint?.triggers.map((trigger) => (
|
||||
// <div key={trigger.uuid} style={{ marginTop: "10px" }}>
|
||||
// <select value={trigger.type} onChange={(e) => handleTriggerSelect(trigger.uuid, e.target.value)}>
|
||||
// <option value="">Select Trigger Type</option>
|
||||
// <option value="On-Hit">On Hit</option>
|
||||
// <option value="Buffer">Buffer</option>
|
||||
// </select>
|
||||
// <button onClick={() => handleDeleteTrigger(trigger.uuid)}>Delete Trigger</button>
|
||||
// <label>
|
||||
// <input
|
||||
// type="checkbox"
|
||||
// checked={trigger.isUsed}
|
||||
// onChange={() => handleTriggerToggle(trigger.uuid)}
|
||||
// />
|
||||
// </label>
|
||||
// <hr style={{ margin: "10px 0", borderColor: "#ccc" }} />
|
||||
// </div>
|
||||
// ))}
|
||||
|
||||
|
||||
</div>
|
||||
)}
|
||||
// </div>
|
||||
// )}
|
||||
|
||||
{selectedPath && (
|
||||
<div style={{ marginTop: "10px" }}>
|
||||
<button
|
||||
onClick={handleResetPath}
|
||||
style={{ padding: "10px", borderRadius: "5px", background: "#ff0000", color: "#fff" }}
|
||||
>
|
||||
Reset Path
|
||||
</button>
|
||||
</div>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}
|
||||
// {selectedPath && (
|
||||
// <div style={{ marginTop: "10px" }}>
|
||||
// <button
|
||||
// onClick={handleResetPath}
|
||||
// style={{ padding: "10px", borderRadius: "5px", background: "#ff0000", color: "#fff" }}
|
||||
// >
|
||||
// Reset Path
|
||||
// </button>
|
||||
// </div>
|
||||
// )}
|
||||
// </>
|
||||
// )}
|
||||
// </div>
|
||||
// )}
|
||||
// </>
|
||||
// );
|
||||
// }
|
||||
|
||||
export default SimulationUI;
|
||||
// export default SimulationUI;
|
||||
Reference in New Issue
Block a user