【问题标题】:Make a alert message disappear after x time in React functional component在 React 功能组件中使警报消息在 x 时间后消失
【发布时间】:2020-08-10 07:49:30
【问题描述】:

我制作了一个过期组件,它允许其中的内容在 x 秒后消失。它通过使用 state 和 setTimeout 来工作。

import React, { useEffect, useState } from 'react';

function Expire(props)
{
    const [isVisible, setIsVisible] = useState(true);

    useEffect(() =>
    {
        setTimer(props.delay);
    }, []);


    const setTimer = (delay) =>
    {
        setTimeout(() => setIsVisible(false), delay);
    };

    return (
        isVisible
            ? <div>{props.children}</div>
            : <span />
    );
}

export default Expire;

我是这样用的:

<Expire delay="5000">
    <Alert type={alertMsgState} size="col-md-10" />
</Expire>

但我遇到的问题是,在 5 秒后消失一次后,再次更改 alertMsgState [例如。再次提交表单,所以我想再次显示警报],消息不会重新呈现并在 5 秒后消失,就像它应该的那样。在检查时,我只看到 &lt;span /&gt; 元素。

请仅使用功能组件和钩子回答。

【问题讨论】:

    标签: javascript reactjs react-hooks


    【解决方案1】:

    您不会做任何会重新触发再次显示警报组件的操作。

    例如,一种解决方案是使用整数键,当您想再次显示它时,请执行以下操作:

    // inside parent
    const [key, setKey] = useState(0);
    
    // Say from a click handler when you again want to show your component, do:
    let onClick=()=>{
      setKey(key+1);
    }
    
    //...
    
    <Expire delay="5000" key={key}>
        <Alert type={alertMsgState} size="col-md-10" />
    </Expire>
    

    当在不同的渲染之间,react 遇到具有不同键的组件时,它将卸载旧组件并再次安装它 - 因此您将获得所需的行为。

    【讨论】:

    • 谢谢!您的解决方案有效。但是请问您可以提供替代方案吗?我想将 expire 组件的所有代码保留在 expire 组件中,而不是让我的父组件被键和东西弄脏。
    • @Haris 首先问自己:您希望什么时候重新绘制 Expire 组件?
    • 每当孩子改变时,至少在这种情况下。
    • @Haris 您能否在问题中举例说明您希望如何使用 Expire 组件?如果当您想再次显示 Expire 组件时需要给它一个不同的孩子,它会很容易使用吗?
    • 我已经在问题中展示了,我现在将它与警报组件一起使用。用户提交表单时更新警报组件alertMsgState 是从服务器接收到的表单提交的消息。
    【解决方案2】:

    您可以做的一件事是将 useEffect 绑定到 props.children,因此,每当发生更改时,您都会重置消息、恢复可见性并再次开始超时:

    function Expire(props)
    {
        const [isVisible, setIsVisible] = useState(true);
        const [children, setChildren] = useState(props.children)
    
        useEffect(() =>
        {
            setChildren(props.children)
            setIsVisible(true)
            setTimer(props.delay);
        }, [props.children]);
    
    
        const setTimer = (delay) =>
        {
            setTimeout(() => setIsVisible(false), delay);
        };
    
        return (
            isVisible
                ? <div>{children}</div>
                : <span />
        );
    }
    

    【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2022-01-21
    • 1970-01-01
    • 2023-03-29
    • 2015-05-11
    • 2021-09-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多