Intercept page exit event

JavascriptInternet ExplorerDom Events

Javascript Problem Overview


When editing a page within my system, a user might decide to navigate to another website and in doing so could lose all the edits they have not saved.

I would like to intercept any attempt to go to another page and prompt the user to be sure they want this to happen since they could potentially lose their current work.

Gmail does this in a very similar way. For example, compose a new email, start typing into the message body and enter a new location in the address bar (say twitter.com or something). It will prompt asking "Are you sure?"

Ideas how to replicate this? I'm targeting IE8, but would like to be compatible with Firefox and Chrome also.

Javascript Solutions


Solution 1 - Javascript

Similar to Ghommey's answer, but this also supports old versions of IE and Firefox.

window.onbeforeunload = function (e) {
  var message = "Your confirmation message goes here.",
  e = e || window.event;
  // For IE and Firefox
  if (e) {
    e.returnValue = message;
  }

  // For Safari
  return message;
};

Solution 2 - Javascript

See this article. The feature you are looking for is the onbeforeunload

sample code:

  <script language="JavaScript">
  window.onbeforeunload = confirmExit;
  function confirmExit()
  {
    return "You have attempted to leave this page.  If you have made any changes to the fields without clicking the Save button, your changes will be lost.  Are you sure you want to exit this page?";
  }
</script>

Solution 3 - Javascript

Instead of an annoying confirmation popup, it would be nice to delay leaving just a bit (matter of milliseconds) to manage successfully posting the unsaved data to the server, which I managed for my site using writing dummy text to the console like this:

window.onbeforeunload=function(e){
  // only take action (iterate) if my SCHEDULED_REQUEST object contains data    	
  for (var key in SCHEDULED_REQUEST){ 	
    postRequest(SCHEDULED_REQUEST); // post and empty SCHEDULED_REQUEST object
    for (var i=0;i<1000;i++){
      // do something unnoticable but time consuming like writing a lot to console
      console.log('buying some time to finish saving data'); 
    };
    break;
  };
}; // no return string --> user will leave as normal but data is send to server

Edit: See also Synchronous_AJAX and how to do that with jquery

Solution 4 - Javascript

I have users who have not been completing all required data.

<cfset unloadCheck=0>//a ColdFusion precheck in my page generation to see if unload check is needed
var erMsg="";
$(document).ready(function(){
<cfif q.myData eq "">
    <cfset unloadCheck=1>
    $("#myInput").change(function(){
        verify(); //function elsewhere that checks all fields and populates erMsg with error messages for any fail(s)
        if(erMsg=="") window.onbeforeunload = null; //all OK so let them pass
        else window.onbeforeunload = confirmExit(); //borrowed from Jantimon above;
    });
});
<cfif unloadCheck><!--- if any are outstanding, set the error message and the unload alert --->
    verify();
    window.onbeforeunload = confirmExit;
    function confirmExit() {return "Data is incomplete for this Case:"+erMsg;}
</cfif>

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionChris BallanceView Question on Stackoverflow
Solution 1 - JavascriptEli GreyView Answer on Stackoverflow
Solution 2 - JavascriptjantimonView Answer on Stackoverflow
Solution 3 - JavascriptRemiView Answer on Stackoverflow
Solution 4 - JavascriptgordonView Answer on Stackoverflow