added 2d point select delete and move
This commit is contained in:
@@ -0,0 +1,341 @@
|
|||||||
|
import * as THREE from "three";
|
||||||
|
import { useCallback, useEffect, useMemo, useState } from "react";
|
||||||
|
import { useFrame, useThree } from "@react-three/fiber";
|
||||||
|
import { useSocketStore, useToggleView, useToolMode, } from "../../../../../store/builder/store";
|
||||||
|
import { detectModifierKeys } from "../../../../../utils/shortcutkeys/detectModifierKeys";
|
||||||
|
import { useParams } from "react-router-dom";
|
||||||
|
import { getUserData } from "../../../../../functions/getUserData";
|
||||||
|
import { useSceneContext } from "../../../sceneContext";
|
||||||
|
import { useVersionContext } from "../../../../builder/version/versionContext";
|
||||||
|
import { useSelectedPoints } from "../../../../../store/simulation/useSimulationStore";
|
||||||
|
import useModuleStore from "../../../../../store/useModuleStore";
|
||||||
|
|
||||||
|
// import { upsertAisleApi } from "../../../../../services/factoryBuilder/aisle/upsertAisleApi";
|
||||||
|
// import { upsertWallApi } from "../../../../../services/factoryBuilder/wall/upsertWallApi";
|
||||||
|
// import { upsertFloorApi } from "../../../../../services/factoryBuilder/floor/upsertFloorApi";
|
||||||
|
// import { upsertZoneApi } from "../../../../../services/factoryBuilder/zone/upsertZoneApi";
|
||||||
|
|
||||||
|
function MoveControls2D({
|
||||||
|
movedObjects,
|
||||||
|
setMovedObjects,
|
||||||
|
pastedObjects,
|
||||||
|
setpastedObjects,
|
||||||
|
duplicatedObjects,
|
||||||
|
setDuplicatedObjects,
|
||||||
|
rotatedObjects,
|
||||||
|
setRotatedObjects,
|
||||||
|
}: any) {
|
||||||
|
const { camera, controls, gl, scene, pointer, raycaster } = useThree();
|
||||||
|
const plane = useMemo(() => new THREE.Plane(new THREE.Vector3(0, 1, 0), 0), []);
|
||||||
|
const { toolMode } = useToolMode();
|
||||||
|
const { toggleView } = useToggleView();
|
||||||
|
const { activeModule } = useModuleStore();
|
||||||
|
const { selectedPoints, clearSelectedPoints } = useSelectedPoints();
|
||||||
|
const { socket } = useSocketStore();
|
||||||
|
const { userId, organization } = getUserData();
|
||||||
|
const { projectId } = useParams();
|
||||||
|
const { selectedVersionStore } = useVersionContext();
|
||||||
|
const { selectedVersion } = selectedVersionStore();
|
||||||
|
const { aisleStore, wallStore, floorStore, zoneStore } = useSceneContext();
|
||||||
|
const { setPosition: setAislePosition, getAislesByPointId } = aisleStore();
|
||||||
|
const { setPosition: setWallPosition, getWallsByPointId } = wallStore();
|
||||||
|
const { setPosition: setFloorPosition, getFloorsByPointId } = floorStore();
|
||||||
|
const { setPosition: setZonePosition, getZonesByPointId } = zoneStore();
|
||||||
|
const [dragOffset, setDragOffset] = useState<THREE.Vector3 | null>(null);
|
||||||
|
const [initialPositions, setInitialPositions] = useState<Record<string, THREE.Vector3>>({});
|
||||||
|
const [initialStates, setInitialStates] = useState<Record<string, { position: THREE.Vector3; rotation?: THREE.Euler; }>>({});
|
||||||
|
const [isMoving, setIsMoving] = useState(false);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (!camera || !scene || !toggleView) return;
|
||||||
|
|
||||||
|
const canvasElement = gl.domElement;
|
||||||
|
canvasElement.tabIndex = 0;
|
||||||
|
|
||||||
|
let isMoving = false;
|
||||||
|
|
||||||
|
const onPointerDown = () => {
|
||||||
|
isMoving = false;
|
||||||
|
};
|
||||||
|
|
||||||
|
const onPointerMove = () => {
|
||||||
|
isMoving = true;
|
||||||
|
};
|
||||||
|
|
||||||
|
const onPointerUp = (event: PointerEvent) => {
|
||||||
|
if (!isMoving && movedObjects.length > 0 && event.button === 0) {
|
||||||
|
event.preventDefault();
|
||||||
|
placeMovedAssets();
|
||||||
|
}
|
||||||
|
if (!isMoving && movedObjects.length > 0 && event.button === 2) {
|
||||||
|
event.preventDefault();
|
||||||
|
|
||||||
|
clearSelection();
|
||||||
|
setMovedObjects([]);
|
||||||
|
resetToInitialPositions();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const onKeyDown = (event: KeyboardEvent) => {
|
||||||
|
const keyCombination = detectModifierKeys(event);
|
||||||
|
|
||||||
|
if (pastedObjects.length > 0 || duplicatedObjects.length > 0 || rotatedObjects.length > 0) return;
|
||||||
|
|
||||||
|
if (keyCombination === "G") {
|
||||||
|
if (selectedPoints.length > 0) {
|
||||||
|
moveAssets();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (keyCombination === "ESCAPE") {
|
||||||
|
event.preventDefault();
|
||||||
|
|
||||||
|
clearSelection();
|
||||||
|
setMovedObjects([]);
|
||||||
|
resetToInitialPositions();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (toggleView && selectedPoints.length > 0) {
|
||||||
|
canvasElement.addEventListener("pointerdown", onPointerDown);
|
||||||
|
canvasElement.addEventListener("pointermove", onPointerMove);
|
||||||
|
canvasElement.addEventListener("pointerup", onPointerUp);
|
||||||
|
canvasElement.addEventListener("keydown", onKeyDown);
|
||||||
|
}
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
canvasElement.removeEventListener("pointerdown", onPointerDown);
|
||||||
|
canvasElement.removeEventListener("pointermove", onPointerMove);
|
||||||
|
canvasElement.removeEventListener("pointerup", onPointerUp);
|
||||||
|
canvasElement.removeEventListener("keydown", onKeyDown);
|
||||||
|
};
|
||||||
|
}, [camera, controls, scene, toggleView, selectedPoints, socket, pastedObjects, duplicatedObjects, movedObjects, rotatedObjects]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (toolMode !== 'move' || !toggleView) {
|
||||||
|
if (movedObjects.length > 0) {
|
||||||
|
resetToInitialPositions();
|
||||||
|
}
|
||||||
|
clearSelection();
|
||||||
|
}
|
||||||
|
}, [activeModule, toolMode, toggleView, movedObjects]);
|
||||||
|
|
||||||
|
useFrame(() => {
|
||||||
|
if (!isMoving || movedObjects.length === 0 || !dragOffset) return;
|
||||||
|
|
||||||
|
raycaster.setFromCamera(pointer, camera);
|
||||||
|
const intersectionPoint = new THREE.Vector3();
|
||||||
|
const hit = raycaster.ray.intersectPlane(plane, intersectionPoint);
|
||||||
|
|
||||||
|
if (hit) {
|
||||||
|
const baseNewPosition = new THREE.Vector3().addVectors(hit, dragOffset);
|
||||||
|
|
||||||
|
movedObjects.forEach((movedPoint: THREE.Object3D) => {
|
||||||
|
if (movedPoint.userData.pointUuid) {
|
||||||
|
const point: Point = movedPoint.userData as Point;
|
||||||
|
const initialPosition = initialPositions[movedPoint.uuid];
|
||||||
|
|
||||||
|
if (initialPosition) {
|
||||||
|
const relativeOffset = new THREE.Vector3().subVectors(
|
||||||
|
initialPosition,
|
||||||
|
initialPositions[movedObjects[0].uuid]
|
||||||
|
);
|
||||||
|
|
||||||
|
const newPosition = new THREE.Vector3().addVectors(baseNewPosition, relativeOffset);
|
||||||
|
const positionArray: [number, number, number] = [newPosition.x, newPosition.y, newPosition.z];
|
||||||
|
|
||||||
|
if (point.pointType === 'Aisle') {
|
||||||
|
setAislePosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Wall') {
|
||||||
|
setWallPosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Floor') {
|
||||||
|
setFloorPosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Zone') {
|
||||||
|
setZonePosition(point.pointUuid, positionArray);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
const calculateDragOffset = useCallback((point: THREE.Object3D, hitPoint: THREE.Vector3) => {
|
||||||
|
const pointPosition = new THREE.Vector3().copy(point.position);
|
||||||
|
return new THREE.Vector3().subVectors(pointPosition, hitPoint);
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
const moveAssets = useCallback(() => {
|
||||||
|
if (selectedPoints.length === 0) return;
|
||||||
|
|
||||||
|
const states: Record<string, { position: THREE.Vector3; rotation?: THREE.Euler; }> = {};
|
||||||
|
|
||||||
|
selectedPoints.forEach((point: THREE.Object3D) => {
|
||||||
|
states[point.uuid] = {
|
||||||
|
position: new THREE.Vector3().copy(point.position),
|
||||||
|
rotation: point.rotation ? new THREE.Euler().copy(point.rotation) : undefined
|
||||||
|
};
|
||||||
|
});
|
||||||
|
setInitialStates(states);
|
||||||
|
|
||||||
|
const positions: Record<string, THREE.Vector3> = {};
|
||||||
|
selectedPoints.forEach((point: THREE.Object3D) => { positions[point.uuid] = new THREE.Vector3().copy(point.position); });
|
||||||
|
setInitialPositions(positions);
|
||||||
|
|
||||||
|
raycaster.setFromCamera(pointer, camera);
|
||||||
|
const intersectionPoint = new THREE.Vector3();
|
||||||
|
const hit = raycaster.ray.intersectPlane(plane, intersectionPoint);
|
||||||
|
|
||||||
|
if (hit && selectedPoints[0]) {
|
||||||
|
const offset = calculateDragOffset(selectedPoints[0], hit);
|
||||||
|
setDragOffset(offset);
|
||||||
|
}
|
||||||
|
|
||||||
|
setMovedObjects(selectedPoints);
|
||||||
|
setIsMoving(true);
|
||||||
|
}, [selectedPoints, camera, pointer, plane, raycaster, calculateDragOffset]);
|
||||||
|
|
||||||
|
const resetToInitialPositions = useCallback(() => {
|
||||||
|
setTimeout(() => {
|
||||||
|
movedObjects.forEach((movedPoint: THREE.Object3D) => {
|
||||||
|
if (movedPoint.userData.pointUuid && initialStates[movedPoint.uuid]) {
|
||||||
|
const point: Point = movedPoint.userData as Point;
|
||||||
|
const initialState = initialStates[movedPoint.uuid];
|
||||||
|
const positionArray: [number, number, number] = [
|
||||||
|
initialState.position.x,
|
||||||
|
initialState.position.y,
|
||||||
|
initialState.position.z
|
||||||
|
];
|
||||||
|
|
||||||
|
if (point.pointType === 'Aisle') {
|
||||||
|
setAislePosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Wall') {
|
||||||
|
setWallPosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Floor') {
|
||||||
|
setFloorPosition(point.pointUuid, positionArray);
|
||||||
|
} else if (point.pointType === 'Zone') {
|
||||||
|
setZonePosition(point.pointUuid, positionArray);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}, 0)
|
||||||
|
}, [movedObjects, initialStates, setAislePosition, setWallPosition, setFloorPosition, setZonePosition]);
|
||||||
|
|
||||||
|
const placeMovedAssets = () => {
|
||||||
|
if (movedObjects.length === 0) return;
|
||||||
|
|
||||||
|
movedObjects.forEach((movedObject: THREE.Object3D) => {
|
||||||
|
if (movedObject.userData.pointUuid) {
|
||||||
|
const point: Point = movedObject.userData as Point;
|
||||||
|
|
||||||
|
if (point.pointType === 'Aisle') {
|
||||||
|
const updatedAisles = getAislesByPointId(point.pointUuid);
|
||||||
|
if (updatedAisles.length > 0 && projectId) {
|
||||||
|
updatedAisles.forEach((updatedAisle) => {
|
||||||
|
|
||||||
|
// API
|
||||||
|
|
||||||
|
// upsertAisleApi(updatedAisle.aisleUuid, updatedAisle.points, updatedAisle.type, projectId, selectedVersion?.versionId || '');
|
||||||
|
|
||||||
|
// SOCKET
|
||||||
|
|
||||||
|
socket.emit('v1:model-aisle:add', {
|
||||||
|
projectId: projectId,
|
||||||
|
versionId: selectedVersion?.versionId || '',
|
||||||
|
userId: userId,
|
||||||
|
organization: organization,
|
||||||
|
aisleUuid: updatedAisle.aisleUuid,
|
||||||
|
points: updatedAisle.points,
|
||||||
|
type: updatedAisle.type
|
||||||
|
})
|
||||||
|
})
|
||||||
|
}
|
||||||
|
} else if (point.pointType === 'Wall') {
|
||||||
|
const updatedWalls = getWallsByPointId(point.pointUuid);
|
||||||
|
if (updatedWalls && updatedWalls.length > 0 && projectId) {
|
||||||
|
updatedWalls.forEach((updatedWall) => {
|
||||||
|
|
||||||
|
// API
|
||||||
|
|
||||||
|
// upsertWallApi(projectId, selectedVersion?.versionId || '', updatedWall);
|
||||||
|
|
||||||
|
// SOCKET
|
||||||
|
|
||||||
|
const data = {
|
||||||
|
wallData: updatedWall,
|
||||||
|
projectId: projectId,
|
||||||
|
versionId: selectedVersion?.versionId || '',
|
||||||
|
userId: userId,
|
||||||
|
organization: organization
|
||||||
|
}
|
||||||
|
|
||||||
|
socket.emit('v1:model-Wall:add', data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} else if (point.pointType === 'Floor') {
|
||||||
|
const updatedFloors = getFloorsByPointId(point.pointUuid);
|
||||||
|
if (updatedFloors && updatedFloors.length > 0 && projectId) {
|
||||||
|
updatedFloors.forEach((updatedFloor) => {
|
||||||
|
|
||||||
|
// API
|
||||||
|
|
||||||
|
// upsertFloorApi(projectId, selectedVersion?.versionId || '', updatedFloor);
|
||||||
|
|
||||||
|
// SOCKET
|
||||||
|
|
||||||
|
const data = {
|
||||||
|
floorData: updatedFloor,
|
||||||
|
projectId: projectId,
|
||||||
|
versionId: selectedVersion?.versionId || '',
|
||||||
|
userId: userId,
|
||||||
|
organization: organization
|
||||||
|
}
|
||||||
|
|
||||||
|
socket.emit('v1:model-Floor:add', data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} else if (point.pointType === 'Zone') {
|
||||||
|
const updatedZones = getZonesByPointId(point.pointUuid);
|
||||||
|
if (updatedZones && updatedZones.length > 0 && projectId) {
|
||||||
|
updatedZones.forEach((updatedZone) => {
|
||||||
|
|
||||||
|
// API
|
||||||
|
|
||||||
|
// upsertZoneApi(projectId, selectedVersion?.versionId || '', updatedZone);
|
||||||
|
|
||||||
|
// SOCKET
|
||||||
|
|
||||||
|
const data = {
|
||||||
|
zoneData: updatedZone,
|
||||||
|
projectId: projectId,
|
||||||
|
versionId: selectedVersion?.versionId || '',
|
||||||
|
userId: userId,
|
||||||
|
organization: organization
|
||||||
|
}
|
||||||
|
|
||||||
|
socket.emit('v1:zone:add', data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
echo.success("Object moved!");
|
||||||
|
|
||||||
|
clearSelection();
|
||||||
|
};
|
||||||
|
|
||||||
|
const clearSelection = () => {
|
||||||
|
setpastedObjects([]);
|
||||||
|
setDuplicatedObjects([]);
|
||||||
|
setMovedObjects([]);
|
||||||
|
setRotatedObjects([]);
|
||||||
|
clearSelectedPoints();
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export default MoveControls2D;
|
||||||
@@ -14,6 +14,7 @@ import { useProductContext } from "../../../../simulation/products/productContex
|
|||||||
import { useSocketStore, useToggleView, useToolMode, } from "../../../../../store/builder/store";
|
import { useSocketStore, useToggleView, useToolMode, } from "../../../../../store/builder/store";
|
||||||
import { useSelectedPoints } from "../../../../../store/simulation/useSimulationStore";
|
import { useSelectedPoints } from "../../../../../store/simulation/useSimulationStore";
|
||||||
import { useBuilderStore } from "../../../../../store/builder/useBuilderStore";
|
import { useBuilderStore } from "../../../../../store/builder/useBuilderStore";
|
||||||
|
import MoveControls2D from "./moveControls2D";
|
||||||
|
|
||||||
// import { deleteAisleApi } from "../../../../../services/factoryBuilder/aisle/deleteAisleApi";
|
// import { deleteAisleApi } from "../../../../../services/factoryBuilder/aisle/deleteAisleApi";
|
||||||
// import { deleteWallApi } from "../../../../../services/factoryBuilder/wall/deleteWallApi";
|
// import { deleteWallApi } from "../../../../../services/factoryBuilder/wall/deleteWallApi";
|
||||||
@@ -24,7 +25,6 @@ import { useBuilderStore } from "../../../../../store/builder/useBuilderStore";
|
|||||||
|
|
||||||
const SelectionControls2D: React.FC = () => {
|
const SelectionControls2D: React.FC = () => {
|
||||||
const { camera, controls, gl, scene, raycaster, pointer } = useThree();
|
const { camera, controls, gl, scene, raycaster, pointer } = useThree();
|
||||||
const selectionGroup = useRef() as Types.RefGroup;
|
|
||||||
const { toggleView } = useToggleView();
|
const { toggleView } = useToggleView();
|
||||||
const { selectedPoints, setSelectedPoints, clearSelectedPoints } = useSelectedPoints();
|
const { selectedPoints, setSelectedPoints, clearSelectedPoints } = useSelectedPoints();
|
||||||
const [movedObjects, setMovedObjects] = useState<THREE.Object3D[]>([]);
|
const [movedObjects, setMovedObjects] = useState<THREE.Object3D[]>([]);
|
||||||
@@ -32,22 +32,19 @@ const SelectionControls2D: React.FC = () => {
|
|||||||
const [copiedObjects, setCopiedObjects] = useState<THREE.Object3D[]>([]);
|
const [copiedObjects, setCopiedObjects] = useState<THREE.Object3D[]>([]);
|
||||||
const [pastedObjects, setpastedObjects] = useState<THREE.Object3D[]>([]);
|
const [pastedObjects, setpastedObjects] = useState<THREE.Object3D[]>([]);
|
||||||
const [duplicatedObjects, setDuplicatedObjects] = useState<THREE.Object3D[]>([]);
|
const [duplicatedObjects, setDuplicatedObjects] = useState<THREE.Object3D[]>([]);
|
||||||
const boundingBoxRef = useRef<THREE.Mesh>();
|
|
||||||
const { activeModule } = useModuleStore();
|
const { activeModule } = useModuleStore();
|
||||||
const { socket } = useSocketStore();
|
const { socket } = useSocketStore();
|
||||||
const selectionBox = useMemo(() => new SelectionBox(camera, scene), [camera, scene]);
|
const selectionBox = useMemo(() => new SelectionBox(camera, scene), [camera, scene]);
|
||||||
const { toolMode } = useToolMode();
|
const { toolMode } = useToolMode();
|
||||||
const { selectedVersionStore } = useVersionContext();
|
const { selectedVersionStore } = useVersionContext();
|
||||||
const { selectedVersion } = selectedVersionStore();
|
const { selectedVersion } = selectedVersionStore();
|
||||||
const { selectedProductStore } = useProductContext();
|
|
||||||
const { selectedProduct } = selectedProductStore();
|
|
||||||
const { projectId } = useParams();
|
const { projectId } = useParams();
|
||||||
const { hoveredLine, hoveredPoint } = useBuilderStore();
|
const { hoveredLine, hoveredPoint } = useBuilderStore();
|
||||||
const { aisleStore, wallStore, floorStore, zoneStore } = useSceneContext();
|
const { aisleStore, wallStore, floorStore, zoneStore } = useSceneContext();
|
||||||
const { setPosition: setAislePosition, removePoint: removeAislePoint, getAislesByPointId } = aisleStore();
|
const { removePoint: removeAislePoint } = aisleStore();
|
||||||
const { setPosition: setWallPosition, removePoint: removeWallPoint, getWallsByPointId } = wallStore();
|
const { removePoint: removeWallPoint } = wallStore();
|
||||||
const { setPosition: setFloorPosition, removePoint: removeFloorPoint, getFloorsByPointId } = floorStore();
|
const { removePoint: removeFloorPoint } = floorStore();
|
||||||
const { setPosition: setZonePosition, removePoint: removeZonePoint, getZonesByPointId } = zoneStore();
|
const { removePoint: removeZonePoint } = zoneStore();
|
||||||
|
|
||||||
const isDragging = useRef(false);
|
const isDragging = useRef(false);
|
||||||
const isLeftMouseDown = useRef(false);
|
const isLeftMouseDown = useRef(false);
|
||||||
@@ -178,12 +175,6 @@ const SelectionControls2D: React.FC = () => {
|
|||||||
}
|
}
|
||||||
}, [activeModule, toolMode, toggleView]);
|
}, [activeModule, toolMode, toggleView]);
|
||||||
|
|
||||||
useFrame(() => {
|
|
||||||
if (pastedObjects.length === 0 && duplicatedObjects.length === 0 && movedObjects.length === 0 && rotatedObjects.length === 0) {
|
|
||||||
selectionGroup.current.position.set(0, 0, 0);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
const selectAssets = useCallback(() => {
|
const selectAssets = useCallback(() => {
|
||||||
selectionBox.endPoint.set(pointer.x, pointer.y, 0);
|
selectionBox.endPoint.set(pointer.x, pointer.y, 0);
|
||||||
if (controls) (controls as any).enabled = true;
|
if (controls) (controls as any).enabled = true;
|
||||||
@@ -226,9 +217,6 @@ const SelectionControls2D: React.FC = () => {
|
|||||||
}, [selectionBox, pointer, controls, selectedPoints, setSelectedPoints]);
|
}, [selectionBox, pointer, controls, selectedPoints, setSelectedPoints]);
|
||||||
|
|
||||||
const clearSelection = () => {
|
const clearSelection = () => {
|
||||||
selectionGroup.current.children = [];
|
|
||||||
selectionGroup.current.position.set(0, 0, 0);
|
|
||||||
selectionGroup.current.rotation.set(0, 0, 0);
|
|
||||||
setpastedObjects([]);
|
setpastedObjects([]);
|
||||||
setDuplicatedObjects([]);
|
setDuplicatedObjects([]);
|
||||||
clearSelectedPoints();
|
clearSelectedPoints();
|
||||||
@@ -237,7 +225,7 @@ const SelectionControls2D: React.FC = () => {
|
|||||||
const deleteSelection = () => {
|
const deleteSelection = () => {
|
||||||
if (selectedPoints.length > 0 && duplicatedObjects.length === 0) {
|
if (selectedPoints.length > 0 && duplicatedObjects.length === 0) {
|
||||||
|
|
||||||
selectedPoints.map((selectedPoint) => {
|
selectedPoints.forEach((selectedPoint) => {
|
||||||
if (selectedPoint.userData.pointUuid) {
|
if (selectedPoint.userData.pointUuid) {
|
||||||
const point: Point = selectedPoint.userData as Point;
|
const point: Point = selectedPoint.userData as Point;
|
||||||
if (point.pointType === 'Aisle') {
|
if (point.pointType === 'Aisle') {
|
||||||
@@ -394,9 +382,7 @@ const SelectionControls2D: React.FC = () => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<group name="SelectionGroup-3D">
|
<MoveControls2D movedObjects={movedObjects} setMovedObjects={setMovedObjects} pastedObjects={pastedObjects} setpastedObjects={setpastedObjects} duplicatedObjects={duplicatedObjects} setDuplicatedObjects={setDuplicatedObjects} rotatedObjects={rotatedObjects} setRotatedObjects={setRotatedObjects} />
|
||||||
<group ref={selectionGroup} name="selectionAssetGroup-3D" />
|
|
||||||
</group>
|
|
||||||
|
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -254,7 +254,7 @@ const SelectionControls3D: React.FC = () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
if (Objects.size === 0) {
|
if (Objects.size === 0) {
|
||||||
clearSelection();
|
// clearSelection();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -103,9 +103,21 @@ export function Arrows({ connections }: { readonly connections: ConnectionLine[]
|
|||||||
return (
|
return (
|
||||||
<group
|
<group
|
||||||
key={key}
|
key={key}
|
||||||
onPointerOver={() => setHoveredArrowTrigger(trigger.triggerUuid)}
|
onPointerOver={() => {
|
||||||
onPointerOut={() => setHoveredArrowTrigger(null)}
|
if (toolMode === '3D-Delete') {
|
||||||
onClick={() => { removeConnection(trigger) }}
|
setHoveredArrowTrigger(trigger.triggerUuid)
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
onPointerOut={() => {
|
||||||
|
if (toolMode === '3D-Delete') {
|
||||||
|
setHoveredArrowTrigger(null)
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
onClick={() => {
|
||||||
|
if (toolMode === '3D-Delete') {
|
||||||
|
removeConnection(trigger)
|
||||||
|
}
|
||||||
|
}}
|
||||||
>
|
>
|
||||||
<mesh
|
<mesh
|
||||||
geometry={shaftGeometry}
|
geometry={shaftGeometry}
|
||||||
|
|||||||
Reference in New Issue
Block a user