每次滚动时对象都会重新加载

问题描述 投票:0回答:1

我有一个3D冰箱模型,加载成功。我试图在用户滚动时让它在屏幕上拖动,并且移动 div 可以工作,但是 3d 对象本身会刷新。请观看随附的视频,看看它如何不断刷新。

每当初始化模型时,是否需要在画布中指定特殊设置?我尝试浏览多个论坛,但找不到解决我的问题的方法。

https://youtu.be/MxHXLc-C3i4

代码:

import React from 'react'
import Navbar from '../components/Navbar';

import {useRef, useEffect} from 'react';
import {useGLTF, Stage, PresentationControls, OrbitControls, useScroll} from '@react-three/drei';
import {Canvas} from '@react-three/fiber';
import { useLoader, useFrame, useThree } from '@react-three/fiber'
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { Suspense } from 'react'
import ModelViewer from '../components/ModelViewer';
import * as THREE from 'three';

function Model(props){
  const {scene} = useGLTF("model.glb");

  useThree(({camera}) => {

    camera.position.set(-180, 20, -160);

  });

  // let model = useLoader(GLTFLoader, "model.glb");

  scene.traverse(child => {
    if (child.isMesh) {
        child.castShadow = true
        child.receiveShadow = true
    }
  });



  return <primitive object={scene} {...props} />;
}



export default function Home(props) {

  const groupRef = useRef();

  const [scrollY, setScrollY] = React.useState(0);

  useEffect(() => {
    const handleScroll = () => {
      setScrollY(window.scrollY);
    };
    handleScroll();

    window.addEventListener("scroll", handleScroll);
    return () => {
      window.removeEventListener("scroll", handleScroll);
    };
  });

  useEffect(() => {

    // as the user scrolls, the "fridge" div will move to center of screen
    let fridge = document.getElementById('fridge');

    window.addEventListener('scroll', () => {

      // make it smooth 
      //       fridge.style.transform = "translateX(" + -midScreenX + "px)";
      // for every scrollY, move the fridge to the left by 1px
      for(let i = 0; i < scrollY; i++){
        fridge.style.transform = "translateX(" + -i + "px)";
      }
    });

  });

  return (
    
    <section className="">
        <Navbar />
        
        <div className="flex items-center justify-center">
        <div className="flex flex-col md:flex-row w-9/12 justify-center items-center h-screen">
          <div className="flex items-center bg-gray-300 w-full">
            <div className="flex flex-col">
                <h1 className="font-CreteRoundRegular text-5xl text-center md:text-left">KitchIN</h1>
                <p className="font-CreteRoundRegular text-xl text-center md:text-left">A smart fridge that helps you keep track of your food.</p>
            </div>
          </div>
          <div className="md:w-1/2 w-full h-5/6 bg-red-200" id="fridge">
            <Canvas>
              {/* <Suspense fallback={null}>
                <Stage>
                  <Model />
                      <OrbitControls enableZoom={false} />
                </Stage>
              </Suspense> */}
              <Suspense fallback={null}>
                <Stage>
                <Model />
                <OrbitControls enableZoom={false} />
                </Stage>
                
              </Suspense> 
            </Canvas>
          </div>
          </div>

        </div>
        <div className="flex h-screen">
            <h1>Hello</h1>
          </div>
    </section>
  )
}

useGLTF.preload("modern_fridge.glb");



javascript reactjs three.js gltf react-fiber
1个回答
0
投票

可能是因为您在 useEffect 中使用滚动,所以每次位置更改时,您的冰箱 div 都会被一次又一次调用,而不是使用 windows.scrollY 您应该考虑使用三/纤维 drei 中的 useScroll 钩子,它会给您当前的滚动偏移量,增量,曲线等,您可以直接输入值来移动和缩放网格,

检查文档中的useScroll pmndrs

使用Scroll的示例

© www.soinside.com 2019 - 2024. All rights reserved.