joe

by Joe

HTML

<form id="file-upload-form" action="<?php echo $_SERVER['PHP_SELF'] ?>">
  <input id="file-upload" type="file" name="fileUpload" />
  <label for="file-upload" id="file-drag">
    Select a file to upload
    <br />OR
    <br />Drag a file into this box

    <br /><br /><span id="file-upload-btn" class="button">Add a file</span>
  </label>

  <progress id="file-progress" value="0">
    <span>0</span>%
  </progress>

  <output for="file-upload" id="messages"></output>
</form>

CSS

body {
  font-family: sans-serif;
}

.button {
  background: #005f95;
  border: none;
  border-radius: 3px;
  color: white;
  display: inline-block;
  font-size: 19px;
  font-weight: bolder;
  letter-spacing: 0.02em;
  padding: 10px 20px;
  text-align: center;
  text-shadow: 0px 1px 2px rgba(0, 0, 0, 0.75);
  text-decoration: none;
  text-transform: uppercase;
  transition: all 0.2s;
}

.btn:hover {
  background: #4499c9;
}

.btn:active {
  background: #49ade5;
}

input[type="file"] {
  display: none;
}

#file-drag {
  border: 2px dashed #555;
  border-radius: 7px;
  color: #555;
  cursor: pointer;
  display: block;
  font-weight: bold;
  margin: 1em 0;
  padding: 3em;
  text-align: center;
  transition: background 0.3s, color 0.3s;
}

#file-drag:hover {
  background: #ddd;
}

#file-drag:hover,
#file-drag.hover {
  border-color: #3070a5;
  border-style: solid;
  box-shadow: inset 0 3px 4px #888;
  color: #3070a5;
}

#file-progress {
  display: none;
  margin: 1em auto;
  width: 100%;
}

#file-upload-btn {
  margin: auto;
}

#file-upload-btn:hover {
  background: #4499c9;
}

#file-upload-form {
  margin: auto;
  width: 40%;
}

progress {
  appearance: none;
  background: #eee;
  border: none;
  border-radius: 3px;
  box-shadow: 0 2px 5px rgba(0, 0, 0, 0.25) inset;
  height: 30px;
}

progress[value]::-webkit-progress-value {
  background: -webkit-linear-gradient(-45deg,
      transparent 33%,
      rgba(0, 0, 0, 0.2) 33%,
      rgba(0, 0, 0, 0.2) 66%,
      transparent 66%),
    -webkit-linear-gradient(right, #005f95, #07294d);
  background: linear-gradient(-45deg,
      transparent 33%,
      rgba(0, 0, 0, 0.2) 33%,
      rgba(0, 0, 0, 0.2) 66%,
      transparent 66%),
    linear-gradient(right, #005f95, #07294d);
  background-size: 60px 30px, 100% 100%, 100% 100%;
  border-radius: 3px;
}

progress[value]::-moz-progress-bar {
  background: -moz-linear-gradient(-45deg,
      transparent 33%,
      rgba(0, 0, 0, 0.2) 33%,
      rgba(0, 0, 0, 0.2) 66%,
     ...

JavaScript

(function() {
  function Init() {
    var fileSelect = document.getElementById("file-upload"),
      fileDrag = document.getElementById("file-drag"),
      submitButton = document.getElementById("submit-button");

    fileSelect.addEventListener("change", fileSelectHandler, false);

    // Is XHR2 available?
    var xhr = new XMLHttpRequest();
    if (xhr.upload) {
      // File Drop
      fileDrag.addEventListener("dragover", fileDragHover, false);
      fileDrag.addEventListener("dragleave", fileDragHover, false);
      fileDrag.addEventListener("drop", fileSelectHandler, false);
    }
  }

  function fileDragHover(e) {
    var fileDrag = document.getElementById("file-drag");

    e.stopPropagation();
    e.preventDefault();

    fileDrag.className =
      e.type === "dragover" ? "hover" : "modal-body file-upload";
  }

  function fileSelectHandler(e) {
    // Fetch FileList object
    var files = e.target.files || e.dataTransfer.files;

    // Cancel event and hover styling
    fileDragHover(e);

    // Process all File objects
    for (var i = 0, f;
      (f = files[i]); i++) {
      parseFile(f);
      uploadFile(f);
    }
  }

  function output(msg) {
    var m = document.getElementById("messages");
    m.innerHTML = msg;
  }

  function parseFile(file) {
    output(
      "<ul>" +
      "<li>Name: <strong>" +
      encodeURI(file.name) +
      "</strong></li>" +
      "<li>Type: <strong>" +
      file.type +
      "</strong></li>" +
      "<li>Size: <strong>" +
      (file.size / (1024 * 1024)).toFixed(2) +
      " MB</strong></li>" +
      "</ul>"
    );
  }

  function setProgressMaxValue(e) {
    var pBar = document.getElementById("file-progress");

    if (e.lengthComputable) {
      pBar.max = e.total;
    }
  }

  function updateFileProgress(e) {
    var pBar = document.getElementById("file-progress");

    if (e.lengthComputable) {
      pBar.value = e.loaded;
    }
  }

  function uploadFile(file) {
    var xhr = new XMLHttpRequest(),
     ...