What this is

This jQuery Multiple File Upload Plugin ($.MultiFile) is a non-obstrusive plugin for jQuery that helps users easily select multiple files for upload quickly and easily on your hosting server whilst also providing some basic validation functionality to help developers idenfity simple errors, without having to submit the form (ie.: upload files).

What this isn't

This plugin will not create a dialog that allows the user to select multiple files at once. That simply cannot be done via javascript. If that's what you need, you should consider using HTML5's multiple="multiple" attribute or one of the many other flash based file upload solutions (eg.: SWFupload, uploadify and others)

How it works

The plugin creates a new file input element every time the user select a file, which allows the user to select a file, then another, then another, then another and so on... selecting as many files is required, one at a time.

How do I use it?

Just add the multi class to your file input element.

<input type="file" class="multi"/>


 

Use the maxlength property if you want to limit the number of files selected. (server-side validation is always required)

<input type="file" class="multi" maxlength="2"/>


 

Use the accept property if you only want files of a certain extension to be selected Separate valid extensions with a "|", like this: "jpg|gif|png". (server-side validation is always required)

<input type="file" class="multi" accept="gif|jpg"/>


Using HTML

Example 1 class="multi" maxlength="2"
Limit: 2 files.
Allowed extensions: any.
Example 2 class="multi" accept="gif|jpg"
Limit: no limit.
Allowed extensions: gif and jpg.
Example 3 class="multi" accept="gif|jpg" maxlength="3"
Limit: 3 files
Allowed extensions: gif, jpg.
Note that server-side validation is always required

Using class property

Example 4 class="multi max-2"
Limit: 2 files.
Allowed extensions: any.
Example 5 class="multi accept-gif|jpg"
Limit: no limit.
Allowed extensions: gif, jpg.
Example 6 class="multi max-3 accept-gif|jpg"
Limit: 3 files
Allowed extensions: gif, jpg.
Note that server-side validation is always required

Moving the file list

Example 7

This example populates the file list in a custom element

$(function(){ // wait for document to load 
 $('#T7').MultiFile({ 
  list: '#T7-list'
 }); 
});
This is div#T7-list - selected files will be populated here...


Customising the file list

Example 8 A

Use a custom 'remove' image in the file list

$(function(){ // wait for document to load 
 $('#T8A').MultiFile({ 
  STRING: {
   remove: '<img src="/i/bin.gif" height="16" width="16" alt="x"/>'
  }
 }); 
});
Example 8 B

Customising all list content

$(function(){ // wait for document to load 
 $('#T8B').MultiFile({ 
  STRING: {
   file: '<em title="Click to remove" onclick="$(this).parent().prev().click()">$file</em>',
   remove: '<img src="/i/bin.gif" height="16" width="16" alt="x"/>'
  }
 }); 
});

Using events

Example 9

The events available are:
onFileAppend, afterFileAppend, onFileSelect, afterFileSelect, onFileRemove, afterFileRemove

The arguments passed on to each event handler are:
element: file element which triggered the event
value: the value of the element in question
master_element: the original element containing all relevant settings

$(function(){ // wait for document to load 
 $('#T9').MultiFile({
  onFileRemove: function(element, value, master_element){
   $('#F9-Log').append('<li>onFileRemove - '+value+'</li>')
  },
  afterFileRemove: function(element, value, master_element){
   $('#F9-Log').append('<li>afterFileRemove - '+value+'</li>')
  },
  onFileAppend: function(element, value, master_element){
   $('#F9-Log').append('<li>onFileAppend - '+value+'</li>')
  },
  afterFileAppend: function(element, value, master_element){
   $('#F9-Log').append('<li>afterFileAppend - '+value+'</li>')
  },
  onFileSelect: function(element, value, master_element){
   $('#F9-Log').append('<li>onFileSelect - '+value+'</li>')
  },
  afterFileSelect: function(element, value, master_element){
   $('#F9-Log').append('<li>afterFileSelect - '+value+'</li>')
  }
 }); 
});
This is div#F9-Log - selected files will be populated here...

Advanced Usage

Using your own selectors

$(function(){ // wait for document to load
  $('#MyFileUpload').MultiFile();
 });

Setting limit via script

$(function(){ // wait for document to load
  $('#MyFileUpload').MultiFile(5 /*limit will be set to 5*/);
 });

Advanced configuration

$(function(){ // wait for document to load
  $('#MyCoolFileUpload').MultiFile({
   max: 5,
   accept: 'gif|jpg|png|bmp|swf'
  });
 });

Customising visible strings for multi-lingual support

$(function(){ // wait for document to load
  $('#PortugueseFileUpload').MultiFile({
   STRING: {
    remove:'Remover',
    selected:'Selecionado: $file',
    denied:'Invalido arquivo de tipo $ext!'
   }
  });
 });

Multi-lingual support

The plugin doesn't have any additional languages built-in, but it's very easy to customise the messages to any language of your choosing. See the examples below...

NB.: This example has been configured to accept gif/pg files only in order to demonstrate the error messages.

Method 1: Using class property (require MetaData plugin)

<input type="file" class="multi
 {accept:'gif|jpg', max:3, STRING:{
  remove:'Remover',
  selected:'Selecionado: $file',
  denied:'Invalido arquivo de tipo $ext!',
  duplicate:'Arquivo ja selecionado:\n$file!'
 }}" />

Method 2: Programatically by ID (ONE element only, does not require MetaData plugin)

<input type="file" id="PortugueseFileUpload" />
$(function(){
  $('#PortugueseFileUpload').MultiFile({
   accept:'gif|jpg', max:3, STRING: {
    remove:'Remover',
    selected:'Selecionado: $file',
    denied:'Invalido arquivo de tipo $ext!',
    duplicate:'Arquivo ja selecionado:\n$file!'
   }
  });
 });

Method 3: Programatically (n elements, does not require MetaData plugin)

See this feature request for details
<input type="file" class="multi-pt" />
<input type="file" class="multi-pt" />
<input type="file" class="multi-pt" />
$(function(){
 $('.multi-pt').MultiFile({
  accept:'gif|jpg', max:3, STRING: {
   remove:'Remover',
   selected:'Selecionado: $file',
   denied:'Invalido arquivo de tipo $ext!',
   duplicate:'Arquivo ja selecionado:\n$file!'
  }
 });
});

Can this plugin upload files?

No, this jQuery plugin does not upload files

Javascript is a client side language and cannot upload files - this plugin will only go as far as helping the user select the files to upload and assisting in the validation process by warning the user of common mistakes before server-side validation takes place. When the form is submitted, it's up to you to have a server-side script that will actually upload the files.

Please do not email me asking how to do this!!! There is plenty of information out there and you can easily find it on Google. But because I'm such a nice guy, I've put a quick list of the best links here:

ASP users

FreeASPUpload - Free, easy to use and no component required. This is my favourite.
Pure ASP File Upload by Jacob Gilley
File Upload via ASP (Pure ASP Solution, no .DLL)

PHP users

See File Upload Tutorials from W3CSchools, About.com, Tizag

NOTICE TO PHP USERS: The plugin's default behaviour generates an array of elements (sharing the same name). In order for this array to be properly identified and handled in PHP, you have to add "[]" to name of your element.
eg.:

<input type="file" name="MyStuff[]"...



Having problems?

1. Make sure your form has method=POST and enctype=multipart/form-data

2. Are you using valid (x)HTML? Invalid markup can stop the form from being submitted altogether

3. Are you using the correct element names as required/expected by your server-side script?

4. Have you tried uploading a single file without using the plugin? Makes sure this works before submitting a bug report



I promise I can upload my own files. What do I need to know?

You should know that the plugin works by hiding elements with a selected file and creating new empty elements. This means when submitting the form, there will always be an empty item at the end of the list of files. Actually, that would have been a problem but this plugin takes care of disabling all dummy empty file inputs for you before the form gets submitted - be it via ajax or natively. So this is good to know, but it's not something you need to worry about.

However, if you are submitting the form programmatically via javascript, you must call this before submitting the form....

$.fn.MultiFile.disableEmpty(); // before submiting the form

And if you're doing things the ajax way, you should call this when you're done to re-enable the dummy element:

$.fn.MultiFile.reEnableEmpty(); // after submiting the form



Ajax

You may use the jQuery Form Plugin to submit the form via ajax.

How do I reset the control?

To reset the file selections, just make the following call:

$('input:file').MultiFile('reset')

Download

This project (and all related files) can also be accessed via its Google Code Project Page.

Full Package: v1.48 multiple-file-upload.zip
Stay up-to-date! Major updates will be announced on Twitter: @fyneworks
Core Files: These are the individual required files (already included in the zip package above)
jQuery: jquery-latest.js (see jQuery.com)

Download www.activextest.com program for free and keep your computer protected for improved speed, performance and operation!

Related Downloads

Related: Metadata plugin - Used to retrieve inline configuration from class variable
blockUI plugin - Used to show pretty error messages
Form plugin - Used to submit forms via ajax

Installation

Required Files

<script src="jquery-latest.js" type="text/javascript" language="javascript"></script>
<script src="jquery.MultiFile.js" type="text/javascript" language="javascript"></script>
    

Optional Files

Metadata Plugin
This great plugin can be used to configure the plugin via the class parameter.
You can also download the version being used on this page

BlockUI Plugin
Used to show 'pretty' error messages, instead of the browser's alert() function.
You can also download the version being used on this page

Form Plugin
Used to submit forms via Ajax.

SVN Repository

If you're a major geek or if you really really want to stay up-to-date with with future updates of this plugin, go ahead and plug yourself to the SVN Repository on the official Google Code Project Page.

SVN Checkout: SVN Checkout Instructions
Browse Online: Browse Source

Alternative Download - From this website

Just in case it's the end of the world and the Google Code site becomes unavailable, the project files can also be downloaded from this site.
However, please note that this site is updated periodically whereas the Google Code project is kept up-to-date almost instantaneously. If you'd like the very latest version of this plugin you are advised to use the links above and download the files from Google Code - this will ensure the files you download have the very latest features and bug fixes.

Full Package: v1.48 multiple-file-upload.zip
Stay up-to-date! Major updates will be announced on Twitter: @fyneworks
Core Files: These are the individual required files (already included in the zip package above)
jQuery: jquery-latest.js (see jQuery.com)

Support

Quick Support Links: Help me! | Report a bug | Suggest new feature

Support for this plugin is available through the jQuery Mailing List. This is a very active list to which many jQuery developers and users subscribe.
Access to the jQuery Mailing List is also available through Nabble Forums and the jQuery Google Group.

WARNING: Support will not be provided via the jQuery Plugins website. If you need help, please direct your questions to the jQuery Mailing List or report an issue on the official Google Code Project Page.

Official Links

Credit where it's due...

  • Fyneworks.com professional web design and google SEO experts
  • Dean Edwards - Author of JS Packer used to compress the plugin
  • Adrian Wróbel - Fixed a nasty bug so the script could work perfectly in Opera
  • Jonas Wagner - Modified plugin so newly created elements are an exact copy of the original element (ie.: persists attributes)
  • Mike Alsup - Author of several jQuery Plugins...
    • Suggested solution to element naming convention / server-side handling
    • Form plugin - Used to submit forms via ajax
    • blockUI plugin - Used to show pretty error messages
  • Julien Phalip - Identified conflict with variable name 'class' in several methods

What's the catch?

There's no catch. Use it, abuse it - even take it apart and modify it if you know what you're doing. You don't have to, but if you're feeling generous you can link back to this website (instructions below).

Attribute this work

Attribution link: © Fyneworks.com
HTML Code:

License Info

Multiple File Upload Plugin by Fyneworks.com is licensed under the MIT License and the GPL License. Creative Commons License

Multiple File Upload Plugin

Provides a non-obstrusive way of selecting multiple files for upload. Supports validation and form plugins.

Star-Rating Plugin

Creates a non-obstrusive star-rating control from any set of radio boxes. Features include half/partial stars and an API for programmatic control. Supports the validation plugin.

XML to JSON

Convert XML to JSON and read data from XML files/RSS feeds with ease.

CKEditor Plugin

jQuery plugin for non-obstrusive integration of textareas with CKEditor.

FCKEditor Plugin

jQuery plugin for non-obstrusive integration of textareas with FCKEditor.
OLD! It is recommended you upgrade to CKEditor (above).

Codepress Plugin

jQuery plugin for non-obstrusive integration of textareas with Codepress.