2
\$\begingroup\$

Please review my code/code quality.

var textarea = document.getElementById("textarea"),
      inputFile = document.getElementById("input-file"),
      prtHelper = document.getElementById("prt-helper"),
      overlay = document.getElementById("overlay"),
      help = document.getElementById("help"),
      appname = " - notepad",
      filename = "untitled.txt",
      isModified = false;

    if (localStorage.getItem("txt")) { // Load localStorage
      textarea.value = localStorage.getItem("txt");
      filename = localStorage.getItem("filename");
      isModified = true;
    }

    window.onunload = function() { // Save localStorage
      if (isModified) {
        localStorage.setItem("txt", textarea.value);
        localStorage.setItem("filename", filename);
      } else {
        localStorage.clear();
      }
    };

    function changeDocTitle() { // Change doc title
      document.title = filename + appname;
    }
    window.onload = changeDocTitle();

    textarea.onpaste = textarea.onkeypress = function() { // Note is modified
      isModified = true;
    };

    function cancelSaving() { // Confirm cancel saving
      if (isModified && confirm("You have unsaved changes that will be lost.")) {
        isModified = false;
        return true;
      }
    }

    function New() { // New
      if (!isModified || cancelSaving()) {
        textarea.value = "";
        filename = "untitled.txt";
        changeDocTitle();
      }
      textarea.focus();
    }

    function Open() { // Open
      if (!isModified || cancelSaving()) {
        inputFile.click();
      }
      textarea.focus();
    }

    function loadFile() { // Load file
      var file = inputFile.files[0],
        fileReader = new FileReader();
      fileReader.onloadend = function(e) {
        filename = file.name;
        changeDocTitle();
        textarea.value = e.target.result;
      };
      fileReader.readAsText(file);
    }

    function rename() { // Rename
      var newFilename;
      do {
        newFilename = prompt("Name this note:", filename);
      } while (newFilename === "");
      if (newFilename) {
        filename = (newFilename.lastIndexOf(".txt") == -1) ? newFilename + ".txt" : newFilename;
        changeDocTitle();
        return true;
      }
    }

    function Save() { // Save
      if (rename()) {
        var blob = new Blob([textarea.value.replace(/\n/g, "\r\n")], {
          type: "text/plain;charset=utf-8"
        });
        saveAs(blob, filename);
        isModified = false;
      }
      textarea.focus();
    }

    function Print() { // Print
      prtHelper.innerHTML = textarea.value;
      window.print();
      prtHelper.innerHTML = "";
      textarea.focus();
    }

    function Help() { // Help
      help.setAttribute("aria-hidden", "false");
      overlay.setAttribute("aria-hidden", "false");
      textarea.blur();
      document.getElementById("cls-hlp").onclick = overlay.onclick = function() {
        closeHelp();
      };
    }

    function closeHelp() { // Close help
      help.setAttribute("aria-hidden", "true");
      overlay.setAttribute("aria-hidden", "true");
      textarea.focus();
    }

    function bookmark() { // temporarily change doc title
      var docTitle = document.title;
      document.title = "Notepad5";
      setTimeout(function() {
        document.title = docTitle;
      }, 3);
    }

    document.onkeydown = function(e) { // Keyboard shortcuts
      var key = e.keyCode || e.which;
      if (e.ctrlKey) {
        if (e.altKey && key == 78) { // Ctrl+Alt+N
          e.preventDefault();
          New();
        }
        switch (key) {
          case 79: // Ctrl+O
            e.preventDefault();
            Open();
            break;
          case 83: // Ctrl+S
            e.preventDefault();
            Save();
            break;
          case 80: // Ctrl+P
            e.preventDefault();
            Print();
            break;
          case 191: // Ctrl+/
            e.preventDefault();
            Help();
            break;
          case 68: //Ctrl+D
            bookmark();
            break;
          default:
            break;
        }
      }
      if (key == 27) { // Esc
        closeHelp();
      }
      if (key == 9) { // Tab
        e.preventDefault();
        var sStart = textarea.selectionStart,
          txt = textarea.value;
        textarea.value = txt.substring(0, sStart) + "\t" + txt.substring(textarea.selectionEnd);
        textarea.selectionEnd = sStart + 1;
      }
    };
\$\endgroup\$
1
\$\begingroup\$

A quick glance,

Code has a lot of global variables

Either namespace it or wrape it so it is in its own scrope and not in window scope.

Attaching Events directly to elements

You should be attaching events with addEventListener.

\$\endgroup\$
1
\$\begingroup\$

There could be a lot to improve

  • As said before, you have a lot of ( too many ) globals
  • You should look up MVC ( Model View Controller )
    • I would put the title, text and all save/load functions under editor.model
    • I would put all routing logic in editor.controller
    • I would put a function that takes the title and text from editor.model and shows it into editor.view, plus also the help displaying/hiding logic
  • In general, try to pass data to functions through parameters, not globals, an example would be fucntion New which should get isModified as a parameter
  • function names shoud start with lowercase, open & new, not Open & New etc.
  • *
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.