Как заменить модель в three js react?
Основной код работы со сценой помещен в useEffect, туда же приходит массив объектов, которые нужно отобразить на сцене. Методом перебора я добавляю их на сцену. Но при изменении значений в массиве объектов, мне рисуется отдельная сцена, а я хочу менять выбранную модель и вместо нее загружать новую. Help please)
const Test = ({ project }) => {
const { surfaces } = project;
const ref = useRef();
useEffect(() => {
main();
function main() {
initM();
animate();
}
function initM() {
initScene();
initCamera();
initLights();
initRenderer();
initControls();
addObjectsFromStore();
initDragControls();
ref.current.appendChild(renderer.domElement);
}
// добавляем модели
function addObjectsFromStore() {
surfaces.map((el) => {
if (el.type === "model") {
let root;
const gltfLoader = new GLTFLoader();
gltfLoader.load(`${el.url}`, (gltf) => {
root = gltf.scene;
root.position.set(el.dots.x, el.dots.y, el.dots.z);
root.userData.name = el.name;
root.userData.id = el.id;
root.userData.currentPosition = new THREE.Vector3();
root.userData.startPosition = {
x: el.dots.x,
y: el.dots.y,
z: el.dots.z,
};
combinePartsOfModel(root);
});
}
return el;
});
}
// эта функция должна срабатывать при изменении массива surfaces где лежат актуальные модели
function replaceModel(prevModel, nextModel) {
const gltfLoader = new GLTFLoader();
gltfLoader.load(`${nextModel.url}`, (gltf) => {
let root = gltf.scene;
root.position.x = 2;
root.position.y = 0.7;
root.position.z = 3;
scene.add(root);
scene.remove(prevModel);
root.userData.currentPosition = new THREE.Vector3();
});
}
function initControls() {
orbit = new OrbitControls(cameraPersp, renderer.domElement);
orbit.update();
orbit.addEventListener("change", render);
}
function initRenderer() {
renderer = new THREE.WebGLRenderer({ alpha: true });
renderer.setPixelRatio(window.devicePixelRatio);
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.shadowMap.enabled = true;
renderer.shadowMapSort = true;
}
function initControls() {
orbit = new OrbitControls(cameraPersp, renderer.domElement);
orbit.update();
orbit.addEventListener("change", render);
}
function render() {
renderer.render(scene, cameraPersp);
}
function animate() {
requestAnimationFrame(animate);
render();
}
return () => {
// Callback to cleanup three js, cancel animationFrame, etc
};
},[]);
return (
<>
<div ref={ref} />
</>
);
};