Using the HTML5 File API to read the file contents

Friday 14 October 2011

In the previous blog post we use the new HTML5 Drag and Drop API to drag files from the Windows Explorer into the browser and process them using JavaScript. That worked pretty well, except for Internet Explorer that is, but the File object didn’t give is a lot of details about the file. In fact we only get the file name, size, last modified date and the type. Useful but not a whole lot of information. But HTML 5 also provides a way we can read the data using the FileReader API.


The FileReader API

This API basically lets us read the contents of the file in a number of different ways:

  • readAsArrayBuffer()
  • readAsBinaryString()
  • readAsText()
  • readAsDataURL()

As we are dragging images into the browser, you can check using the file.type which is the file MIME type, the best option is to use the readAsDataURL() which reads the contents of the file and returns it as an encoded URL. The FileReader is basically an asynchronous object so we can use the onload event to work with the file contents.

Thanks to the power of jQuery the code doesn’t become much more complex Smile The whole change is in the jQuery.each() block where we start reading the file and creating an <img> tag instead of just displaying the file name.

   1: $(function () {
   2:     if (Modernizr.draganddrop) {
   3:         var dropTarget = $('#dropTarget')[0];
   5:         dropTarget.addEventListener('dragover', function (e) {
   6:             e.preventDefault();
   7:         });
   9:         dropTarget.addEventListener('drop', function (e) {
  10:             e.preventDefault();
  12:             if (e.dataTransfer.files === undefined) {
  13:                 // IE doesn't support file drops yet.
  14:                 $('#dropTarget').text('Drag & Drop of files is not supported');
  15:                 return;
  16:             }
  18:             $.each(e.dataTransfer.files, function () {
  19:                 var file = this;
  20:                 var reader = new FileReader();
  21:                 reader.onload = function () {
  22:                     $('<img>')
  23:                         .attr('title',
  24:                         .attr('src', this.result)
  25:                         .css('width', '75%')
  26:                         .appendTo('#images');
  27:                 };
  28:                 reader.readAsDataURL(file);
  29:             });
  30:         });
  31:     }
  32:     else {
  33:         $('#dropTarget').text('Drag & Drop is not supported');
  34:     }
  35: });


And the result looks like this:



As you can see below the image element source is not set to the usual URL but to a data URL that contains all data in a base 64 encoded string.



Using one of the other operations on the FileReader we can get the file contents in a way where we can easily work with it or possibly send it to the server for processing.