You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React点击删除按钮后弹窗组件重复渲染问题求助

问题:删除按钮触发弹窗多次渲染

我正在开发一个带多字段的搜索功能,搜索后展示结果表格,每行都有删除按钮。点击删除按钮时需要弹出确认弹窗,询问是否确认删除并根据响应执行后续操作。

确认删除弹窗

目前点击删除按钮时,弹窗组件会被多次调用(打印的日志次数与当前可见结果数量相关)。

DataTable组件代码

function DataTable(props) {
    const [searchedData, setsearchedData] = useState({});
    const [openPopup, setOpenPopup] = useState(false);
    const keys = ["Customer Name", "Contact Number", "Contract Number", "Liscence Key"];

    useEffect(() => {
        // getting the data from API and storing in searchData state
    }, [props.data]);

    function popupResponse(value) {
        setOpenPopup(false);
        if (value) {
            console.log("value is true");
        } else {
            console.log("value is false");
        }
    }

    const deleteKey = useCallback(() => {
        setOpenPopup(true);
        console.log("in delete key");
    }, [setOpenPopup]);

    return (
        <div className="data-table ">
            { Object.keys(searchedData).length > 0 ?
                <div>
                    <table className="data-table__table">
                        <thead>
                            <tr>
                                {keys.map((heading, key) => {
                                    return (
                                        <th key={key + heading}>{heading}</th>
                                    );
                                })}
                            </tr>
                        </thead>
                        <tbody>
                            {searchedData.map((data, key) => <RowData rowData={data} key={key} uniqueKey={key} openPopup={openPopup} deleteLiscense={deleteKey}/>)}
                        </tbody>
                    </table>

                    {/* triggering the popup */}
                    {openPopup && <PopUp className="data-table__popup" open={openPopup} close={popupResponse}/>}
                </div>
                : <div className="data-table__no-results">No results found.</div>
            }
        </div>
    );
}

RowData组件(调用deleteLiscense函数打开弹窗)

const RowData = ({rowData, uniqueKey, deleteLiscense}) => {
    const values = Object.values(rowData);

    return (
        <>
            <tr key={uniqueKey}>
                {values.map((value) => <td className="" key={uniqueKey + value}>{value}</td>)}
                <td className="" key={uniqueKey}>
                    <button key={uniqueKey} type="button" onClick={() => deleteLiscense}>Delete key</button>
                </td>
            </tr>
        </>
    );
}

PopUp组件

function PopUp ({open, close}) {
    if (!open) return null;

    const response = (value) => {
        close(value)
    }

    console.log("in popup");

    return (
        <div className="data-table__popup-container">
            <div className="data-table__popup-container--heading"> Are you sure you want to delete the Liscence Key?</div>
            <div className="data-table__popup-container--button-wrapper">
                <button className="button-yes" onClick={() => response(true)}>Yes</button>
                <button className="button-no" onClick={() => response(false)}>No</button>
            </div>
        </div>
    );
}

export default PopUp;

已尝试的解决方法

  • 为deleteKey函数使用useCallback钩子,试图避免每行删除按钮重新定义函数导致多次触发弹窗,但问题未解决。

补充观察

第二次点击任意删除按钮时,不再打印弹窗日志。


内容的提问来源于stack exchange,提问作者Gautam Goyal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 14:42:02