NYcake 2024-02-21 11:24 采纳率: 80%
浏览 5
已结题

关于react-hook组件用函数控制是否渲染的及时性问题。

关于react-hook组件用函数控制是否渲染的及时性问题。
需要大家帮看看用 findOverAllVisible && 这种形式控制的怎么让其创建,然后我要操作组件里面的属性或方法。


import React, { useEffect, useState, useRef, createRef } from 'react';
import ProfessionLayer from '../ProfessionLayer';
import FindOverAll from '../FindOverAll';

const MenuPanel: React.FC<Props> = (props) => {
  const childRef = useRef(null);
  const childRefPl = useRef(null);
  const [findOverAllVisible,setFindOverAllVisible] = useState(false); // 全局查询显示开关
  const onSearchv2 = (v: string) => {
    setFindOverAllVisible(()=>{return true})
    if (childRef.current) { //这个current没法找到,我查了文档是没有渲染,这里需要怎么处理?
      childRef.current.handleChild(v);
    }
  }

  const closeFindOverAll = () =>{
    setFindOverAllVisible(()=>{return false})
    if (childRefPl.current) { //这个current没法找到,我查了文档是没有渲染,这里需要怎么处理?
      childRefPl.current.handleChild();
    }
  }
  return (
    <div className={styles.container}>
          <div className={styles.containerTwo}>
            <Search placeholder="综合查询" onSearch={onSearchv2} />
          </div>
          {!findOverAllVisible &&
            <ProfessionLayer ref={childRefPl} treeChange={treeChange}></ProfessionLayer>

          }
          {findOverAllVisible &&
            <div>
              <Button onClick={closeFindOverAll} > 返回</Button>
              <FindOverAll ref={childRef}></FindOverAll> 
            </div>
          }
    </div>
  );
};
  • 写回答

17条回答 默认 最新

  • 专家-赤兔[在线] 优质创作者: 编程框架技术领域 2024-02-21 11:37
    关注
    获得0.45元问题酬金

    引自免费微信小程序:皆我百晓生

    在React中,使用useState Hook来控制组件的渲染时机,你遇到的问题在于尝试在状态更新后立即访问和操作未渲染组件的引用(ref)。由于React的状态更新是异步的,因此在setFindOverAllVisible之后直接调用子组件的方法可能无法获取到正确的当前实例。

    为了确保在findOverAllVisible变为true时正确创建并操作子组件,你需要利用useEffect Hook监听这个状态变化,并在它变化时执行你的逻辑。以下是修复问题后的代码:

    import React, { useEffect, useState, useRef } from 'react';
    import ProfessionLayer from '../ProfessionLayer';
    import FindOverAll from '../FindOverAll';
    
    const MenuPanel: React.FC<Props> = (props) => {
      const childRef = useRef(null);
      const childRefPl = useRef(null);
      const [findOverAllVisible, setFindOverAllVisible] = useState(false); // 全局查询显示开关
    
      useEffect(() => {
        if (findOverAllVisible && childRef.current) {
          // 当全局查询显示且子组件已渲染时处理
          childRef.current.handleChild(v);
        }
        
        if (!findOverAllVisible && childRefPl.current) {
          // 当全局查询关闭且 ProfessionLayer 组件已渲染时处理
          childRefPl.current.handleChild();
        }
      }, [findOverAllVisible]); // 注意依赖数组,当 findOverAllVisible 改变时重新运行此效应
    
      const onSearchv2 = (v: string) => {
        setFindOverAllVisible(true);
      };
    
      const closeFindOverAll = () => {
        setFindOverAllVisible(false);
      };
    
      return (
        <div className={styles.container}>
          <div className={styles.containerTwo}>
            <Search placeholder="综合查询" onSearch={onSearchv2} />
          </div>
          {!findOverAllVisible &&
            <ProfessionLayer ref={childRefPl} treeChange={treeChange} />
          }
          {findOverAllVisible &&
            <div>
              <Button onClick={closeFindOverAll}> 返回</Button>
              <FindOverAll ref={childRef} />
            </div>
          }
        </div>
      );
    };
    

    这样,当findOverAllVisible状态发生变化时,useEffect会触发并在DOM更新完成后执行回调函数,此时子组件已经渲染完成,可以安全地通过current属性访问它们的实例。注意将需要的操作移动到了useEffect中,并将其添加为依赖项。

    评论 编辑记录

报告相同问题?

问题事件

  • 系统已结题 2月29日
  • 赞助了问题酬金15元 2月21日
  • 创建了问题 2月21日