点击打开模态框按钮时React Context未更新的问题排查
问题原因
你用useRef存储模态框的显示状态是错误的——useRef的.current属性变化不会触发组件重渲染。这就导致:
- 调用
openDemoModal后,showModal.current确实变成了true,但ModalProvider不会重新渲染 - Context Provider的
value始终是初始的showModal: false,子组件拿不到更新后的状态 Modal组件的show属性也不会更新,所以模态框始终不显示
解决方案
把useRef替换成useState,useState的状态更新会触发组件重渲染,从而更新Context的value和Modal的显示状态。
修改后的ModalProvider代码:
import { type FC, type PropsWithChildren, createContext, useContext, useState } from 'react' import Modal from '@/components/modal/Modal' type ContextValue = { showModal: boolean openDemoModal: () => void closeDemoModal: () => void } const INITIAL_STATE: ContextValue = { showModal: false, openDemoModal: () => {}, closeDemoModal: () => {}, } export const ModalContext = createContext(INITIAL_STATE) export const ModalProvider: FC<PropsWithChildren> = ({ children }) => { const [showModal, setShowModal] = useState(INITIAL_STATE.showModal) const openDemoModal = () => { setShowModal(true) } const closeDemoModal = () => { setShowModal(false) } return ( <ModalContext.Provider value={{ showModal, openDemoModal, closeDemoModal }}> {children} <Modal show={showModal} setShow={setShowModal} /> </ModalContext.Provider> ) } export function useModal() { const context = useContext(ModalContext) if (!context) { throw new Error('useModal must be used within a ModalProvider') } return context }
额外说明
- 不需要修改
Instructions组件的代码,它调用openDemoModal的逻辑是正确的 - 新增
closeDemoModal方法是为了后续关闭模态框时能直接调用,你可以根据Modal组件的需求调整setShow的用法 - 用
useState管理状态后,每次状态变化都会触发ModalProvider重渲染,Context的value会同步更新,所有依赖这个Context的组件都会拿到最新的showModal值
内容的提问来源于stack exchange,提问作者Robert Carmichael
相关产品推荐
相关产品推荐

