在Gatsby中如何更新组件本地状态实现通知条点击关闭功能?
问题原因
- React 组件的
props是只读属性,直接修改传入的showNotification参数不会触发组件重渲染,因此界面不会同步更新 - 只有通过 React 官方提供的状态更新 API 修改响应式状态,才会触发组件的重新渲染,更新 DOM 表现
解决方案
场景1:通知显隐状态由 Layout 组件内部管理
直接用 useState 钩子将通知显隐标记声明为组件内部的响应式状态即可,修改后代码如下:
// layout.js import * as React from 'react' import { useState } from 'react' const Layout = ({initialShowNotification = true}) => { // 声明响应式状态 const [showNotification, setShowNotification] = useState(initialShowNotification) return ( <div> <header>HEADER</header> {showNotification ? <div style={{display: "flex"}}> NOTIFICATION <span onClick={() => setShowNotification(false)}> DISMISS </span> </div> : null} <main>MAIN CONTENT</main> <footer>FOOTER</footer> </div> ) } export default Layout
说明:这里把props参数重命名为initialShowNotification避免歧义,仅作为状态的初始值使用
场景2:通知显隐状态需要被父组件控制
如果通知的显示/隐藏需要在父组件或者其他组件中触发,就需要把状态提升到父组件维护,修改方式如下:
Layout 组件修改
// layout.js import * as React from 'react' // 接收父组件传入的状态和关闭回调 const Layout = ({showNotification = true, onDismiss}) => <div> <header>HEADER</header> {showNotification ? <div style={{display: "flex"}}> NOTIFICATION <span onClick={onDismiss}> DISMISS </span> </div> : null} <main>MAIN CONTENT</main> <footer>FOOTER</footer> </div> export default Layout
父组件使用示例
// 父组件代码 import { useState } from 'react' import Layout from './layout' function App() { const [showNotification, setShowNotification] = useState(true) return ( <Layout showNotification={showNotification} onDismiss={() => setShowNotification(false)} /> ) }
内容的提问来源于stack exchange,提问作者Captain Stack
相关产品推荐
相关产品推荐

