One way to handle this would be to give the child window some time to close before the parent window is closed. You can use the setTimeout function to delay the closing of the parent window for a short period of time, such as 100ms. This would give the childWindow.close() method enough time to execute and close the child window before the parent window is closed.
@HostListener('window:beforeunload', ['$event'])
beforeUnload(e: any) {
if (this.childWindow && !this.childWindow.closed) {
e.preventDefault();
e.returnValue = false;
setTimeout(() => {
this.childWindow.close();
}, 100);
}
}
As for capturing the user action on the browser's default dialog, it's not possible to capture whether the user has clicked 'Leave' or 'Cancel' as the browser's default dialog does not provide any way to capture the user's choice.
You could try to use e.returnValue to provide your own message on the browser's default dialog and then you could set a flag based on the user's choice, but it will be different across the browsers.
@HostListener('window:beforeunload', ['$event'])
beforeUnload(e: any) {
if (this.childWindow && !this.childWindow.closed) {
e.returnValue = 'Are you sure you want to close the window?';
}
}
You can also try to use localStorage or sessionStorage to store a flag indicating if the user has confirmed to close the window, but this will only work if the user does not clear the browser's storage.
If it is closing the child window, even when user has clicked cancel on dialog
One way to address this would be to use the localStorage or sessionStorage to store a flag indicating whether the user has confirmed that they want to close the window.
You can set this flag to true when the user confirms that they want to close the window, and then check the flag's value in the beforeunload event handler. If the flag is true, you can proceed with closing the child window, otherwise, you can cancel the close operation.
@HostListener('window:beforeunload', ['$event'])
beforeUnload(e: any) {
if (this.childWindow && !this.childWindow.closed) {
if (localStorage.getItem('closeConfirmed') === 'true') {
this.childWindow.close();
} else {
e.preventDefault();
e.returnValue = 'Are you sure you want to close the window?';
}
}
}
// Set the flag when the user confirms they want to close the window
confirmClose() {
localStorage.setItem('closeConfirmed', 'true');
window.close();
}
And you can add a confirm button on your dialog that calls the confirmClose method.
closing windows programmatically may be blocked by some browser so to be on a safer side provide a way for the user to close the window manually.