MERN栈React项目如何用useState实现model-viewer 3D模型点击切换
方案说明
完全可以通过useState实现该需求,你当前代码的问题主要出在useEffect执行顺序错误、多余的srcOptions状态定义、按钮渲染逻辑错误三个点,以下是完整修正方案:
1. 修正后组件完整代码
import {useEffect, useState} from "react"; import {useSelector, useDispatch} from "react-redux"; // Actions import {getProductDetails} from "../redux/actions/productActions"; const ProductScreen = ({match}) => { const dispatch = useDispatch(); // 仅保留当前模型地址状态即可 const [currentSrc, setCurrentSrc] = useState(""); const productDetails = useSelector((state) => state.getProductDetails); const {loading, error, product} = productDetails; // 第一个effect:监听商品ID变化,拉取对应商品详情 useEffect(() => { if (match.params.id !== product?._id) { dispatch(getProductDetails(match.params.id)); } }, [dispatch, match.params.id, product?._id]); // 第二个effect:商品详情加载完成后,初始化默认显示的模型地址 useEffect(() => { if (product) { setCurrentSrc(product.src); } }, [product]); return ( <div className="productcreen"> {loading ? ( <h2>加载中...</h2> ) : error ? ( <h2>{error}</h2> ) : ( <> <div className='sizebuttons'> {/* 直接遍历三个模型配置生成按钮,无需多余的map逻辑 */} {[ {src: product.src, size: product.size}, {src: product.src2, size: product.size2}, {src: product.src3, size: product.size3} ].map((item, index) => ( <button key={index} onClick={() => setCurrentSrc(item.src)}> {item.size} </button> ))} </div> <div className="productscreen__right"> <model-viewer id="model-viewer" src={currentSrc} alt={product.name} ar ar-modes="scene-viewer quick-look" ar-placement="floor" shadow-intensity="1" camera-controls min-camera-orbit={product.mincameraorbit} max-camera-orbit={product.maxcameraorbit} interaction-prompt="none" > <button slot="ar-button" className="ar-button"> 在你的空间中查看 </button> </model-viewer> </div> </> )} </div> ) };
2. 改动说明
- 移除了不必要的
srcOptions状态:因为你的模型地址和对应尺寸是单独存储在MongoDB的三个独立字段中,不需要额外维护数组状态,直接通过临时配置数组遍历生成按钮即可 - 拆分了useEffect逻辑:避免了请求未完成就给状态赋值旧数据的问题,保证状态更新时机准确
- 修正了按钮渲染逻辑:点击按钮时直接将对应模型地址赋值给
currentSrc,状态更新后会触发组件重渲染,model-viewer的src属性会自动更新,自动加载新的3D模型
3. 依赖补充
如果还未引入model-viewer依赖,需要在项目public/index.html的head标签中加入引入代码即可:
<script type="module" src="https://unpkg.com/@google/model-viewer/dist/model-viewer.min.js"></script>
你原本编写的Redux请求逻辑不需要做任何修改,只要确保MongoDB中存储的src/src2/src3字段为正确的模型文件地址即可。
内容的提问来源于stack exchange,提问作者Wade Morrison
相关产品推荐
相关产品推荐

