React函数式组件如何实现Products到Navbar的购物车数量同步传值
解决方案
你遇到的问题根源是Navbar和Products属于平级组件,没有直接父子关系,无法直接通过Props跨组件传值,我们可以通过状态提升的方式,把购物车数量状态放到两个组件的公共父组件Router.jsx中统一管理,就能实现数据同步。
步骤1:修改Router.jsx
首先在Router组件中定义购物车数量状态,同时向两个子组件传递对应参数:
// Router.jsx 完整代码 import React, { useState } from 'react' import { BrowserRouter, Switch, Route, Link } from "react-router-dom"; import Home from './components/Home'; import Navbar from './components/Navbar'; import Products from './components/Products'; import Cart from './components/Cart'; // React组件名必须大写开头,把原小写的router改为Router function Router() { // 定义购物车数量状态,初始值为0 const [cartCount, setCartCount] = useState(0) return ( <> <BrowserRouter> {/* 把购物车数量传递给Navbar */} <Navbar cartCount={cartCount}/> <Switch> <Route exact path='/' component={Home}/> <Route exact path='/cart' component={Cart}/> {/* 给Products传递修改购物车数量的方法,路由组件传参用render属性 */} <Route exact path="/products" render={() => <Products setCartCount={setCartCount} />}/> </Switch> </BrowserRouter> </> ) } export default Router
步骤2:修改Products.jsx
接收修改购物车数量的方法,给加购按钮绑定点击事件:
// Products.jsx 完整代码 import React from 'react' // 删掉原代码中多余的import Router、import Navbar,无实际作用 function Products(props) { return ( <div> <h1>PRODUCTS</h1> {/* 绑定点击事件,每次点击购物车数量+1 */} <button className="btn btn-success" onClick={() => props.setCartCount(prevCount => prevCount + 1)} > ADD TO CART </button> </div> ) } export default Products
步骤3:修改Navbar.jsx
接收购物车数量参数并展示:
// Navbar.jsx 完整代码 import React from 'react' import { Link } from 'react-router-dom' function Navbar(props) { return ( <div> <div className="d-flex bg-primary flex-row justify-content-between text-light "> <div className="left d-flex"> <li className="my-2"><Link className="text-light p-3 py-2" to="/">HOME</Link></li> <li className="my-2"><Link className="text-light p-3 py-2" to="/products">PRODUCTS</Link></li> <li className="my-2"><Link className="text-light p-3 py-2" to="/cart">CART</Link></li> </div> <div className="right d-flex align-items-center"> <p className="m-0">CART is:</p><p className="mx-2 h3 m-0">{props.cartCount}</p> </div> </div> </div> ) } export default Navbar
可选优化:刷新页面不丢失购物车数量
因为你是无后端项目,可以把购物车数量存在浏览器localStorage中,仅修改Router.jsx的状态定义即可实现:
// Router.jsx 中修改useState初始化逻辑 const [cartCount, setCartCount] = useState(() => { // 初始化时从localStorage取值,无存储值则返回0 return Number(localStorage.getItem('cartCount')) || 0 }) // 封装修改方法,每次更新同步存储到localStorage const updateCartCount = (newVal) => { setCartCount(newVal) localStorage.setItem('cartCount', newVal) } // 最后给Products传递updateCartCount代替原来的setCartCount即可
内容的提问来源于stack exchange,提问作者Keerthan Achar
相关产品推荐
相关产品推荐

