Hello!
I am facing a challenge with user interactions and model positioning in my Three.js application, and I am seeking your guidance to resolve this issue.
Here is the scenario:
- I load a obj model into the scene, and it renders perfectly at the center of the screen with an appropriate size.
- The user can interact with the model, including repositioning it using a mouse right-click drag.
- After the user repositions the model, if they select a different model or reload the current model, the new or reloaded model appears at the last position set by the user, instead of being reset to the original central position.
What I want to achieve is to have the model always load or reload at its initial position, regardless of any previous user interactions. I want the model to appear at the center of the screen with the appropriate size every time it is loaded or reloaded.
I have tried resetting the camera position to its initial state, and while this works for the camera, it does not affect the position of the model.
Here is a snippet of my code for loading the OBJ model:
// Change ObjModel
const selectWork = (_work: Work) => {
worksStore.selectWork(_work);
meshChecked = false;
checkedQuestions = [];
resetCameraToInitialState();
removeAllObjectsFromScene();
};
function resetCameraToInitialState() {
camera.position.copy(initialCameraState.position);
camera.rotation.copy(initialCameraState.rotation);
camera.zoom = initialCameraState.zoom;
camera.position.z = 70;
camera.updateProjectionMatrix();
}
function removeAllObjectsFromScene() {
const objectsToRemove = [...scene.children];
for (const object of objectsToRemove) {
scene.remove(object);
}
const ambientLight: THREE.AmbientLight = new THREE.AmbientLight(0x404040);
scene.add(ambientLight);
const directionalLight: THREE.DirectionalLight = new THREE.DirectionalLight(
0xffffff,
0.5
);
directionalLight.position.set(0, 1, 1);
scene.add(directionalLight);
}
// render Obj model
function loadObj(scene: THREE.Scene): void {
const objLoader: OBJLoader = new OBJLoader();
objLoader.load($mesh_url, (object: THREE.Object3D) => {
object.traverse((e) => e.isMesh && (e.material.side = THREE));
const box: THREE.Box3 = new THREE.Box3().setFromObject(object);
const size = box.getSize(new THREE.Vector3());
const center = box.getCenter(new THREE.Vector3());
object.position.x += object.position.x - center.x;
object.position.y += object.position.y - center.y;
object.position.z += object.position.z - center.z;
const maxDim = Math.max(size.x, size.y, size.z);
const fov = camera.fov * (Math.PI / 180);
let cameraZ = Math.abs((maxDim / 2) * Math.tan(fov * 2));
cameraZ *= 1.1;
const minZ = box.min.z;
const cameraToFarEdge = minZ < 0 ? -minZ + cameraZ : cameraZ - minZ;
const far = camera.position.z + cameraToFarEdge * 3;
camera.far = far;
camera.updateProjectionMatrix();
scene.add(object);
updateCameraAndRenderer();
});
}
Could you please provide guidance on how to reset the model’s position after user interactions, so that it always appears at its initial central position when loaded or reloaded?
Thank you in advance for your help!