首页 > 解决方案 > 反应:删除事件侦听器“beforeunload”不起作用

问题描述

当用户离开页面而不保存时,我正在尝试添加提示。

这是我的代码:

    componentDidUpdate() {
        if (!this.props.data.get('is_data_saved')) {
            window.addEventListener('beforeunload', function(e) {
                e.returnValue = 'Data may not be saved'
            }, true);
        } else {
            window.removeEventListener('beforeunload', function(e) {
                e.returnValue = 'Data may not be saved'
            }, true);
            console.log('REMOVED')
        }
    }

我在控制台中得到了“已删除”,但即使保存了表单,也总是弹出提示。是不是因为我把事件监听器放在了错误的组件中?

标签: javascriptreactjs

解决方案


我看到的基本问题是您正在添加和删除不同的功能。

您需要使用对现有方法的引用,而不是重写相同的代码。

beforeUnloadHandler(e){
    e.returnValue = 'Data may not be saved';
}
componentDidUpdate() {
    if (!this.props.data.get('is_data_saved')) {
        window.addEventListener('beforeunload', this.beforeUnloadHandler, true);
    } else {
        window.removeEventListener('beforeunload', this.beforeUnloadHandler, true);
        console.log('REMOVED')
    }
}

但是,如果该组件以其他方式更新,它最终可能会添加多个事件处理程序。为避免这种情况,如果设置了事件处理程序,您也可以设置一个标志,或者更具防御性,始终首先删除处理程序并在需要时重新添加它。

就像是

beforeUnloadHandler(e){
    e.returnValue = 'Data may not be saved';
}
componentDidUpdate() {
    // always remove the handler
    window.removeEventListener('beforeunload', this.beforeUnloadHandler, true);
    // if required add it back
    if (!this.props.data.get('is_data_saved')) {
        window.addEventListener('beforeunload', this.beforeUnloadHandler, true);
    }
}

推荐阅读