我正在从事电子商务项目(MERN)。所以我得到了Molla电子商务React模板更好的UX/UI。
在我的根函数中,我使用redux获取所有产品并存储它们,像这样:
const updateStore = () => {
store.dispatch( getAllProducts() );
}
一切工作正常,直到我发现,如果我尝试访问产品页面第一次(与空localstorage在隐身模式),我什么也没有得到,产品对象是未定义的,如果我刷新页面,那么它工作正常。
问题是,当我试图访问产品页面与空的redux存储,它不等待或渲染时存储数据。我试图使用useEffect()
等待产品更改来渲染,但它不起作用。这是我的产品页面代码:
function SingleProduct( props ) {
let productLink= props.match.params.link;
const {product} = props;
const [productLoaded,setProductLoaded] = useState(false);
useEffect( () => {
if(productLoaded){
productGallery();
document.querySelector( '.skel-pro-single' ).classList.remove( 'loaded' );
let imgLoad = imagesLoaded( ".product-main-image", { background: true } );
imgLoad.on( 'done', function ( instance, image ) {
document.querySelector( '.skel-pro-single' ).classList.add( 'loaded' );
} );
}
}, [ productLink ] )
useEffect(()=>{
if(product){
setProductLoaded(true);
}
},[product])
return (
productLoaded ?
<>
<Helmet>
<title></title>
</Helmet>
<h1 className="d-none"></h1>
<div className="main">
<div className="page-content">
<div className="container">
<div className="product-details-top skeleton-body">
<div className="row skel-pro-single">
<div className="col-md-6">
<div className="skel-product-gallery">
</div>
<MediaOne link={ productLink } />
</div>
<div className="col-md-6">
<div className="entry-summary row">
<div className="col-md-12">
<div className="entry-summary1"></div>
</div>
<div className="col-md-12">
<div className="entry-summary2"></div>
</div>
</div>
<ProductDetailOne link={ productLink } />
</div>
</div>
</div>
<DescOne link={ productLink } />
<h2 className="title text-center mb-4">You May Also Like</h2>
<RelatedProducts />
</div>
</div>
<StickyBar link={ productLink } />
<QuickView />
</div>
</>
:
<></>
)
}
function mapStateToProps( state, props ) {
return {
product: state.data.products.filter( product => product.link == props.link )[ 0 ]
}
}
export default connect(mapStateToProps)(SingleProduct);
我尝试使用useEffect和productLoaded状态等待产品更改,因为它在第一页渲染时未定义,但它仍然显示未定义。
'product'变量,我认为,是一个对象,注意如果你使用useEffect可能会发生什么
const a = {a:123};
const b = {a:123};
(a === b) === false
如果可能的话,查看id或字符串/数字是否更改
第一个useEffect将在第二个之前运行,所以当它运行时,它将把productLoaded设置为false。
尝试从props中获得productLoaded(你不需要管理useEffect的异步性)。
假设产品在加载前未定义
const productLoaded = !!product;
useEffect( () => {
if(productLoaded){
..."do here what you need"
}
}, [ productLink, productLoaded ] )
也许你可以在CSS类
中实现改变<div className={`row skel-pro-single ${productLoaded?"loaded":""}`}>
作为一个建议,尝试使用react作为一个模板,在返回的jsx中带有变量,请不要混合js dom交互和react交互,它们可能会相互干扰(react会尝试报告他管理的dom的一部分到他计算的状态,所以可以覆盖你的更改
document.querySelector( '.skel-pro-single' ).classList.remove