繁体   English   中英

如何在反应钩子中有条件

[英]How to have a condition in react hooks

我试图在页面加载时加载引导模式,除非按下取消按钮。 该功能应该工作的方式是,一旦页面加载,等待 2 秒并显示模式,除非按下取消按钮,在这种情况下,模式不应该显示,但是无论按下取消按钮,模式都会显示,

const Call = ({ t, i18n }) => {
  const [modalShow, setModalShow] = useState(false);
  const [cancelCall, setCancelCall] = useState(false);

  useEffect(() => {
     if (cancelCall) {
       return;
     } else {
       setTimeout(() => {
         setModalShow(true);
       }, 2000);
     }
  }, [setModalShow, cancelCall]);

  const handleCancelCall = e => {
    setCancelCall(true);
    console.log("cancel call pressed!");
  };

return (
    <Fragment>
      <CallModal show={modalShow} onHide={() => setModalShow(false)} />

    <button
            type="button"
            className="ml-4 btn btn-light"
            onClick={e => handleCancelCall()}
          >
            Cancel
          </button>
      </Fragment>
  );
};

任何帮助,将不胜感激。

这是因为,在页面加载时,您的cancelCall将始终为 false,因此您将注册一个超时事件。

发布该用户单击按钮但注册的事件也需要删除。 尝试:

const Call = ({ t, i18n }) => {
  const [modalShow, setModalShow] = useState(false);
  const [cancelCall, setCancelCall] = useState(false);

  // Save the timer id in state
  const [timer, setTimer] = useState(null);

  useEffect(() => {
     if (cancelCall) {
       return;
     } else {
       const timer = setTimeout(() => {
         setModalShow(true);
       }, 2000);
       setTimer(timer)
     }
  }, [setModalShow, cancelCall]);

  const handleCancelCall = e => {
    setCancelCall(true);

    // On cancel, check if timer is not null. If not clear the timer from queue
    !!timer && window.clearTimeout(timer);
    setTimer(null)
    console.log("cancel call pressed!");
  };

return (
    <Fragment>
      <CallModal show={modalShow} onHide={() => setModalShow(false)} />

    <button
            type="button"
            className="ml-4 btn btn-light"
            onClick={e => handleCancelCall()}
          >
            Cancel
          </button>
      </Fragment>
  );
};

尽管@Rajesh 的回答有效,但它会导致 2 次不必要的重新渲染(调用setTimer )。 我建议您只需使用ref来跟踪计时器

const [modalShow, setModalShow] = useState(false);
const modalTimer = useRef(null);

useEffect(() => {
  // the if (cancelCall) part in here was pointless 
  // because initial state is always false
  modalTimer.current = setTimeout(() => setModalShow(true), 2000);
}, []);

const handleCancelCall = e => {
  // on cancel, simply clear the timer
  modalTimer.current && clearTimeout(modalTimer.current);
};

上面还删除了一些冗余代码 & state。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM