Merge remote-tracking branch 'origin/main-dev' into main-demo
This commit is contained in:
@@ -39,7 +39,7 @@ const CopyPasteControls3D = () => {
|
||||
rotatedObjects,
|
||||
setRotatedObjects,
|
||||
} = assetStore();
|
||||
const { updateAssetInScene } = useAssetResponseHandler();
|
||||
const { updateAssetInScene, removeAssetFromScene } = useAssetResponseHandler();
|
||||
const { selectedVersion } = versionStore();
|
||||
const { userId, organization } = getUserData();
|
||||
|
||||
@@ -502,56 +502,58 @@ const CopyPasteControls3D = () => {
|
||||
projectId,
|
||||
};
|
||||
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
removeAssetFromScene(data.modelUuid, () => {
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, 0, position.z],
|
||||
rotation: { x: pastedAsset.rotation.x, y: pastedAsset.rotation.y, z: pastedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
eventData: eventData,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
eventData: data.data.eventData,
|
||||
};
|
||||
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Pasted asset: ${model.modelName}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, 0, position.z],
|
||||
rotation: { x: pastedAsset.rotation.x, y: pastedAsset.rotation.y, z: pastedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
eventData: eventData,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
eventData: data.data.eventData,
|
||||
};
|
||||
|
||||
builderSocket.emit("v1:model-asset:copy", data);
|
||||
}
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Pasted asset: ${model.modelName}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
|
||||
builderSocket.emit("v1:model-asset:copy", data);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
const data = {
|
||||
organization,
|
||||
@@ -568,54 +570,56 @@ const CopyPasteControls3D = () => {
|
||||
userId,
|
||||
};
|
||||
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
removeAssetFromScene(data.modelUuid, () => {
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, 0, position.z],
|
||||
rotation: { x: pastedAsset.rotation.x, y: pastedAsset.rotation.y, z: pastedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
};
|
||||
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Pasted asset: ${model.modelUuid}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, 0, position.z],
|
||||
rotation: { x: pastedAsset.rotation.x, y: pastedAsset.rotation.y, z: pastedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
};
|
||||
|
||||
builderSocket.emit("v1:model-asset:copy", data);
|
||||
}
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Pasted asset: ${model.modelUuid}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error pasting asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
|
||||
builderSocket.emit("v1:model-asset:copy", data);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
assetsToCopy.push({
|
||||
|
||||
@@ -38,7 +38,7 @@ const DuplicationControls3D = () => {
|
||||
rotatedObjects,
|
||||
setRotatedObjects,
|
||||
} = assetStore();
|
||||
const { updateAssetInScene } = useAssetResponseHandler();
|
||||
const { updateAssetInScene, removeAssetFromScene } = useAssetResponseHandler();
|
||||
const { selectedVersion } = versionStore();
|
||||
const { userId, organization } = getUserData();
|
||||
|
||||
@@ -93,9 +93,7 @@ const DuplicationControls3D = () => {
|
||||
if (!isPointerMoving && duplicatedObjects.length > 0 && event.button === 2) {
|
||||
event.preventDefault();
|
||||
clearSelection();
|
||||
duplicatedObjects.forEach((obj: THREE.Object3D) => {
|
||||
removeAsset(obj.userData.modelUuid);
|
||||
});
|
||||
clearDuplication();
|
||||
}
|
||||
setKeyEvent("");
|
||||
};
|
||||
@@ -130,9 +128,7 @@ const DuplicationControls3D = () => {
|
||||
if (keyCombination === "ESCAPE" && duplicatedObjects.length > 0) {
|
||||
event.preventDefault();
|
||||
clearSelection();
|
||||
duplicatedObjects.forEach((obj: THREE.Object3D) => {
|
||||
removeAsset(obj.userData.modelUuid);
|
||||
});
|
||||
clearDuplication();
|
||||
}
|
||||
};
|
||||
|
||||
@@ -233,6 +229,12 @@ const DuplicationControls3D = () => {
|
||||
}
|
||||
}, [axisConstraint, camera, duplicatedObjects]);
|
||||
|
||||
const clearDuplication = useCallback(() => {
|
||||
duplicatedObjects.forEach((obj: THREE.Object3D) => {
|
||||
removeAsset(obj.userData.modelUuid);
|
||||
});
|
||||
}, [duplicatedObjects, removeAsset]);
|
||||
|
||||
const duplicateSelection = useCallback(() => {
|
||||
if (selectedAssets.length > 0 && duplicatedObjects.length === 0) {
|
||||
const positions: Record<string, THREE.Vector3> = {};
|
||||
@@ -564,56 +566,58 @@ const DuplicationControls3D = () => {
|
||||
projectId,
|
||||
};
|
||||
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
removeAssetFromScene(data.modelUuid, () => {
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, position.y, position.z],
|
||||
rotation: { x: duplicatedAsset.rotation.x, y: duplicatedAsset.rotation.y, z: duplicatedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
eventData: eventData,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
eventData: data.data.eventData,
|
||||
};
|
||||
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Duplicated asset: ${model.modelName}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, position.y, position.z],
|
||||
rotation: { x: duplicatedAsset.rotation.x, y: duplicatedAsset.rotation.y, z: duplicatedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
eventData: eventData,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
eventData: data.data.eventData,
|
||||
};
|
||||
|
||||
builderSocket.emit("v1:model-asset:duplicate", data);
|
||||
}
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Duplicated asset: ${model.modelName}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
|
||||
builderSocket.emit("v1:model-asset:duplicate", data);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
const data = {
|
||||
organization,
|
||||
@@ -630,54 +634,56 @@ const DuplicationControls3D = () => {
|
||||
userId,
|
||||
};
|
||||
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
removeAssetFromScene(data.modelUuid, () => {
|
||||
if (!builderSocket?.connected) {
|
||||
// REST
|
||||
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, position.y, position.z],
|
||||
rotation: { x: duplicatedAsset.rotation.x, y: duplicatedAsset.rotation.y, z: duplicatedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
};
|
||||
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Duplicated asset: ${model.modelUuid}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
setAssetsApi({
|
||||
modelUuid: newFloorItem.modelUuid,
|
||||
modelName: newFloorItem.modelName,
|
||||
assetId: newFloorItem.assetId,
|
||||
position: [position.x, position.y, position.z],
|
||||
rotation: { x: duplicatedAsset.rotation.x, y: duplicatedAsset.rotation.y, z: duplicatedAsset.rotation.z },
|
||||
isLocked: false,
|
||||
isVisible: true,
|
||||
versionId: selectedVersion?.versionId || "",
|
||||
projectId: projectId,
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
return;
|
||||
}
|
||||
if (data.message === "Model created successfully" && data.data) {
|
||||
const model: Asset = {
|
||||
modelUuid: data.data.modelUuid,
|
||||
modelName: data.data.modelName,
|
||||
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,
|
||||
isCollidable: true,
|
||||
isVisible: data.data.isVisible,
|
||||
opacity: 1,
|
||||
};
|
||||
|
||||
builderSocket.emit("v1:model-asset:duplicate", data);
|
||||
}
|
||||
updateAssetInScene(model, () => {
|
||||
echo.log(`Duplicated asset: ${model.modelUuid}`);
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
}
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error duplicating asset: ${newFloorItem.modelUuid}`);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
// SOCKET
|
||||
|
||||
builderSocket.emit("v1:model-asset:duplicate", data);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
assetsToDuplicate.push({
|
||||
|
||||
@@ -221,6 +221,36 @@ function MoveControls3D({ boundingBoxRef }: any) {
|
||||
}, 50);
|
||||
}, [movedObjects, initialStates, updateAsset]);
|
||||
|
||||
const resetToInitialPosition = useCallback(
|
||||
(modelUuid: string, callBack?: () => void) => {
|
||||
setTimeout(() => {
|
||||
const movedObject = movedObjects.find((obj: THREE.Object3D) => obj.userData.modelUuid === modelUuid);
|
||||
|
||||
if (!movedObject) return;
|
||||
|
||||
const initialState = initialStates[movedObject.uuid];
|
||||
if (!initialState) return;
|
||||
|
||||
const positionArray: [number, number, number] = [initialState.position.x, initialState.position.y, initialState.position.z];
|
||||
|
||||
updateAsset(modelUuid, {
|
||||
position: positionArray,
|
||||
rotation: [initialState.rotation?.x || 0, initialState.rotation?.y || 0, initialState.rotation?.z || 0],
|
||||
});
|
||||
|
||||
movedObject.position.copy(initialState.position);
|
||||
if (initialState.rotation) {
|
||||
movedObject.rotation.copy(initialState.rotation);
|
||||
}
|
||||
|
||||
setAxisConstraint(null);
|
||||
|
||||
if (callBack) callBack();
|
||||
}, 50);
|
||||
},
|
||||
[movedObjects, initialStates, updateAsset]
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
if (movedObjects.length > 0) {
|
||||
const intersectionPoint = new THREE.Vector3();
|
||||
@@ -413,7 +443,7 @@ function MoveControls3D({ boundingBoxRef }: any) {
|
||||
.then((data) => {
|
||||
if (!data.message || !data.data) {
|
||||
echo.error(`Error moving asset: ${newFloorItem.modelUuid}`);
|
||||
resetToInitialPositions();
|
||||
resetToInitialPosition(newFloorItem.modelUuid);
|
||||
clearSelection();
|
||||
return;
|
||||
}
|
||||
@@ -437,13 +467,13 @@ function MoveControls3D({ boundingBoxRef }: any) {
|
||||
});
|
||||
} else {
|
||||
echo.error(`Error moving asset: ${newFloorItem.modelUuid}`);
|
||||
resetToInitialPositions();
|
||||
resetToInitialPosition(newFloorItem.modelUuid);
|
||||
clearSelection();
|
||||
}
|
||||
})
|
||||
.catch(() => {
|
||||
echo.error(`Error moving asset: ${newFloorItem.modelUuid}`);
|
||||
resetToInitialPositions();
|
||||
resetToInitialPosition(newFloorItem.modelUuid);
|
||||
clearSelection();
|
||||
});
|
||||
} else {
|
||||
|
||||
@@ -202,6 +202,34 @@ function RotateControls3D() {
|
||||
}, 50);
|
||||
}, [rotatedObjects, initialRotations, initialPositions, updateAsset]);
|
||||
|
||||
const resetToInitialRotation = useCallback(
|
||||
(modelUuid: string) => {
|
||||
setTimeout(() => {
|
||||
const obj = rotatedObjects.find((o: THREE.Object3D) => o.userData.modelUuid === modelUuid);
|
||||
|
||||
if (!obj) return;
|
||||
|
||||
const uuid = obj.uuid;
|
||||
const initialRotation = initialRotations[uuid];
|
||||
const initialPosition = initialPositions[uuid];
|
||||
|
||||
if (initialRotation && initialPosition) {
|
||||
const rotationArray: [number, number, number] = [initialRotation.x, initialRotation.y, initialRotation.z];
|
||||
const positionArray: [number, number, number] = [initialPosition.x, initialPosition.y, initialPosition.z];
|
||||
|
||||
updateAsset(modelUuid, {
|
||||
rotation: rotationArray,
|
||||
position: positionArray,
|
||||
});
|
||||
|
||||
obj.rotation.copy(initialRotation);
|
||||
obj.position.copy(initialPosition);
|
||||
}
|
||||
}, 50);
|
||||
},
|
||||
[rotatedObjects, initialRotations, initialPositions, updateAsset]
|
||||
);
|
||||
|
||||
useFrame(() => {
|
||||
if (!isRotating || rotatedObjects.length === 0) return;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user