ghwikipp: edit: Use sessionStorage to keep the current textarea contents.

From 3f34c850b6de60d5e00037d0ee8435c6eb765b5a Mon Sep 17 00:00:00 2001
From: "Ryan C. Gordon" <[EMAIL REDACTED]>
Date: Mon, 1 Jul 2024 05:01:51 +0000
Subject: [PATCH] edit: Use sessionStorage to keep the current textarea
 contents.

This makes your in-progress work survive reloads, etc, as long as the
browser tab lives, so jumping to a different page and then hitting back,
or pressing the reload button, won't throw away your edits, so we don't
have to have a popup warning if this works.

Clicking "Cancel" or submitting an edit will dump the sessionStorage
item, so you don't end up with old/rejected text later in this case.

Also, this uses sessionStorage, so it will not save your work
long-term! This seems more sensible, since we're trying to save against
accidental loss in the moment and not saving drafts, and don't want
_really_ old work popping up and replacing newer revisions.
---
 templates/edit | 34 +++++++++++++++++++++++++++++++---
 1 file changed, 31 insertions(+), 3 deletions(-)

diff --git a/templates/edit b/templates/edit
index 4fda344..3769164 100644
--- a/templates/edit
+++ b/templates/edit
@@ -55,6 +55,7 @@
 </style>
 
 <script type='text/javascript'>
+  var session_storage_item = "docedit-@page@";
   var cooking_timer = undefined;
   var xhr = undefined;
   var origtext = undefined;
@@ -91,7 +92,19 @@
   }
 
   function set_warn_when_leaving(enable) {
-      window.onbeforeunload = enable ? warn_when_leaving : null;
+      // if we can save this in sessionStorage, we don't need to warn when you leave/reload the page.
+      if (enable) {
+        try {
+          sessionStorage.setItem(session_storage_item, document.getElementById("rawtext").value);
+          window.onbeforeunload = null;
+        } catch (error) {
+          sessionStorage.removeItem(session_storage_item);
+          window.onbeforeunload = warn_when_leaving;
+        }
+      } else {
+        sessionStorage.removeItem(session_storage_item);
+        window.onbeforeunload = null;
+      }
   }
 
   function rawtext_needs_recooking() {
@@ -111,7 +124,7 @@
       if (!changed_from_original) {
           document.getElementById("cooked").innerHTML = origcooked;  // in case this changed _back_.
       } else {
-          // only fire off an AJAX request if no new input happened for X seconds.
+          // only fire off an AJAX request if no new input happened for X milliseconds.
           cooking_timer = setTimeout(cook_new_rawtext, 500);
       }
   }
@@ -137,6 +150,21 @@
       origtext = document.getElementById("rawtext").value;
       origformat = document.getElementById("format").value;
       origcooked = document.getElementById("cooked").innerHTML;
+      var sessiontext = sessionStorage.getItem(session_storage_item);
+      if ((sessiontext !== null) && (sessiontext != origtext)) {
+        document.getElementById("rawtext").value = sessiontext;
+        rawtext_needs_recooking();
+      }
+  }
+
+  function cancel_clicked() {
+    if (document.getElementById("rawtext").value != origtext) {
+        if (!confirm("Are you sure you want to throw away your changes?")) {
+            return false;  // stop the page leave.
+        }
+    }
+    set_warn_when_leaving(false);
+    return true;  // let the href proceed.
   }
 </script>
 
@@ -169,7 +197,7 @@
       <option value="mediawiki" @fmt_mediawiki_selected@ >MediaWiki</option>
     </select>
     <input type="submit" id="submit" name="submit" value="Submit" onclick="set_warn_when_leaving(false);" disabled />
-    <a href='/@page@'>[ Cancel ]</a>
+    <a href='/@page@' onclick="cancel_clicked();">[ Cancel ]</a>
   </form>
 </div>