Elegant Customizable jQuery & PHP File Uploader - Fileuploader

Elegant Customizable jQuery & PHP File Uploader - Fileuploader
File Size: 185 KB
Views Total:
Last Update:
Publish Date:
Official Website: Go to website
License: MIT
   

Fileuploader is a flexible, powerful jQuery & PHP file uploader that turns any standard file input into a high customizable file selection field with validators and previews. The plugin is licensed under the GPLv3 license for all open source applications. For commercial license, click here for more information.

Features:

  • Easy to use.
  • Highly customizable.
  • Drag & drop with instant upload.
  • Edit mode.
  • Various form field validators.
  • Lots of API.

Basic usage:

1. Include the core style sheet and a theme CSS of your choice on the page.

<link href="jquery.fileuploader.css" media="all" rel="stylesheet">
<link href="jquery.fileuploader-theme-dragdrop.css" rel="stylesheet">
<link href="jquery.fileuploader-theme-onebutton.css" rel="stylesheet">
<link href="jquery.fileuploader-theme-thumbnails.css" rel="stylesheet">

2. Include both jQuery library and the jQuery Fileuploader plugin's script at the bottom of the webpage.

<script src="//code.jquery.com/jquery.min.js"></script>
<script src="jquery.fileuploader.min.js"></script>

3. Create a standard file input on the page.

<input type="file" name="files">

4. Just call the function on the input field and you're done.

$('input[name="files"]').fileuploader();

5. All available options.

// limit of files {null, Number}
// also with the appended files
// if null - has no limits
// example: 3
limit: null,

// file's maximal size in MB {null, Number}
// also with the appended files
// if null - has no limits
// example: 2
maxSize: null,

// each file's maximal size in MB {null, Number}
// if null - has no limits
// example: 2
fileMaxSize: null,

// allowed extensions or file types {null, Array}
// if null - has no limits
// example: ['jpg', 'jpeg', 'png', 'audio/mp3', 'text/plain']
extensions: null,

// new input {Boolean, String, Function, jQuery Object}
// example: true
// example: ' ' - no input
// example: '<div>Click me</div>'
// example: function(options) { return '<div>Click me</div>'; }
// example: $('.selector')
changeInput: true,

// add brackets at the end of the input name by multiple files {Boolean}
// specially for PHP
inputNameBrackets: true,

// fileuploader theme {null, String}
// it will be only a class name in fileuploader parent element
// the class name will be: fileuploader-theme-default
theme: 'default',

// enable thumbnails for files {null, Object}
// set on null to disable the thumbnails
thumbnails: {
  // thumbnails list HTML {String, Function}
  // example: '<ul></ul>'
  // example: function(options) { return '<ul></ul>'; }
  box: '<div class="fileuploader-items">' +
      '<ul class="fileuploader-items-list"></ul>' +
        '</div>',
  
  // append thumbnails list to selector {null, String, jQuery Object}
  // example: 'body'
  // example: $('body')
  boxAppendTo: null,
  
  // thumbnails item HTML {String, Function}
  // example: '<li>${name}</li>'
  // example: function(item) { return '<li>' + item.name + '</li>'; }
  item: '<li class="fileuploader-item">' +
       '<div class="columns">' +
        '<div class="column-thumbnail">${image}</div>' +
      '<div class="column-title">' +
           '<div title="${name}">${name}</div>' +
           '<span>${size2}</span>' +
      '</div>' +
      '<div class="column-actions">' +
           '<a class="fileuploader-action fileuploader-action-remove" title="Remove"><i></i></a>' +
      '</div>' +
        '</div>' +
        '<div class="progress-bar2">${progressBar}<span></span></div>' +
    '</li>',
  
  // thumbnails appended item HTML {String, Function}
  // example: '<li>${name}</li>'
  // example: function(item) { return '<li>' + item.name + '</li>'; }
  item2: '<li class="fileuploader-item">' +
       '<div class="columns">' +
        '<a href="${data.url}" target="_blank">' +
           '<div class="column-thumbnail">${image}</div>' +
           '<div class="column-title">' +
                '<div title="${name}">${name}</div>' +
                '<span>${size2}</span>' +
           '</div>' +
      '</a>' +
      '<div class="column-actions">' +
           '<a href="${file}" class="fileuploader-action fileuploader-action-download" title="Download" download><i></i></a>' +
           '<a class="fileuploader-action fileuploader-action-remove" title="Remove"><i></i></a>' +
      '</div>' +
        '</div>' +
    '</li>',
    
  // insert the thumbnail's item at the beginning of the list? {Boolean}
  itemPrepend: false,
  
  // show a confirmation dialog by removing a file? {Boolean}
  // it will not be shown in upload mode by canceling an upload
  removeConfirmation: true,
  
  // render the image thumbnail? {Boolean}
  // if it will be false, it will generate an icon(you can also hide it with css)
  // if it will be false, you can use the API method (item.renderImage()) to render it (check thumbnails example)
  startImageRenderer: true,
  
  // render the images synchron {Boolean}
  // made to improve the browser speed
  synchronImages: true,
  
  // render the image in a canvas element {Boolea, Object}
  // if it will be true, it will generate an image with the css sizes from the parent element (.column-thumbnail)
  // you can also set the width and the height in the object
  // by default - true
  canvasImage: {
    width: null,
    height: null
  },
  
  // thumbnails selectors
  _selectors: {
    list: '.fileuploader-items-list',
    item: '.fileuploader-item',
    start: '.fileuploader-action-start',
    retry: '.fileuploader-action-retry',
    remove: '.fileuploader-action-remove'
  },
  
  // Callback fired before adding the list element
  beforeShow: function(parentEl, newInputEl, inputEl) {
    // callback will go here
  },
  
  // Callback fired after adding the item element
  onItemShow: function(item, listEl, parentEl, newInputEl, inputEl) {
    // callback will go here
  },
  
  // Callback fired after removing the item element
  // by default we will animate the removing action
  onItemRemove: function(itemEl, listEl, parentEl, newInputEl, inputEl) {
    itemEl.children().animate({'opacity': 0}, 200, function() {
      setTimeout(function() {
        itemEl.slideUp(200, function() {
          itemEl.remove(); 
        });
      }, 100);
    });
  },
  
  // Callback fired after the item image was loaded
  onImageLoaded: function(itemEl, listEl, parentEl, newInputEl, inputEl) {
    // callback will go here
  },
},

// enable the upload mode {null, Object}
// each file will be separately uploaded to server
// if you want to send all files, you don't even need this option. Just use the standard HTML <form> to do this.
// by default - null
upload: {
  // upload URL {String}
  url: 'index.php',
  
  // upload data {null, Object}
  // you can also change this Object in beforeSend callback
  // example: { option_1: 'yes', option_2: 'ok' }
  data: null,
  
  // upload type {String}
  // for more details http://api.jquery.com/jquery.ajax/
  type: 'POST',
  
  // upload enctype {String}
  // for more details http://api.jquery.com/jquery.ajax/
  enctype: 'multipart/form-data',
  
  // auto-start file uploading {Boolean}
  // if it will be false, you can use the API methods to start it (check options example)
  start: false,
  
  // upload the files synchron {Boolean}
  synchron: true,
  
  // Callback fired before uploading a file
  // by returning false, you can prevent the upload
  beforeSend: function(item, listEl, parentEl, newInputEl, inputEl) {
    // example:
    // here you can extend the uploading data
    item.upload.data.new_data_attribute = 'nice';

    return true;
  },
  
  // Callback fired if the uploading succeeds
  // by default we will add a success icon and fadeOut the progressbar
  onSuccess: function(data, item, listEl, parentEl, newInputEl, inputEl, textStatus, jqXHR) {
    item.html.find('.column-actions').append(
      '<a class="fileuploader-action fileuploader-action-remove fileuploader-action-success" title="Remove"><i></i></a>'
    );

    setTimeout(function() {
      item.html.find('.progress-bar2').fadeOut(400);
    }, 400);
  },
  
  // Callback fired if the uploading failed
  // by default we will set the progressbar to 0% and if it wasn't cancelled, we will add a retry button
  onError: function(item, listEl, parentEl, newInputEl, inputEl, jqXHR, textStatus, errorThrown) {
    var progressBar = item.html.find('.progress-bar2');

    if(progressBar.length > 0) {
      progressBar.find('span').html(0 + "%");
      progressBar.find('.fileuploader-progressbar .bar').width(0 + "%");
      item.html.find('.progress-bar2').fadeOut(400);
    }

    item.upload.status != 'cancelled' && item.html.find('.fileuploader-action-retry').length == 0 ? item.html.find('.column-actions').prepend(
      '<a class="fileuploader-action fileuploader-action-retry" title="Retry"><i></i></a>'
    ) : null;
  },
  
  // Callback fired while uploading the file
  // by default we will set the progressbar width and percentage
  // data = {
    loaded: ...,
    loadedInFormat: ...,
    total: ...,
    totalInFormat: ...,
    percentage: ...,
    secondsElapsed: ...,
    secondsElapsedInFormat:...,
    bytesPerSecond: ...,
    bytesPerSecondInFormat: ...,
    remainingBytes: ...,
    remainingBytesInFormat: ...,
    secondsRemaining: ...,
    secondsRemainingInFormat: ...
  }
  onProgress: function(data, item, listEl, parentEl, newInputEl, inputEl) {
    var progressBar = item.html.find('.progress-bar2');

    if(progressBar.length > 0) {
      progressBar.show();
      progressBar.find('span').html(data.percentage + "%");
      progressBar.find('.fileuploader-progressbar .bar').width(data.percentage + "%");
    }
  },
  
  // Callback fired after all files were uploaded
  onComplete: function(listEl, parentEl, newInputEl, inputEl, jqXHR, textStatus) {
    // callback will go here
  },
},

// enable the drag&drop feature {Boolean, Object}
// this feature is available only in upload mode
// by default - true
dragDrop: {
  // set drag&drop container {null, String, jQuery Object}
  // example: 'body'
  // example: $('body')
  container: null,
  
  // Callback fired on entering with dragged files the drop container
  onDragEnter: function(event, listEl, parentEl, newInputEl, inputEl) {
    // callback will go here
  },
  
  // Callback fired on leaving with dragged files the drop container
  onDragLeave: function(event, listEl, parentEl, newInputEl, inputEl) {
    // callback will go here
  },
  
  // Callback fired on dropping the dragged files in drop container
  onDrop: function(event, listEl, parentEl, newInputEl, inputEl) {
    // callback will go here
  },

},

// enable the addMore mode {Boolean}
// choose more files from different folders; can be used in the standard HTML <form>
addMore: false,

// appended files {null, Array of Objects}
// useful for REST API in javascript
// please follow this structure for each file:
{
  name: 'filename1.txt',
  size: 1024,
  type: 'text/plain',
  file: 'uploads/filename1.txt',
  data: {
    url: 'http://your_link.com/',
    another_attribute: 'ok',
    you_can_use_it_later: 'hehe',
    also_in_templates: 'perfect'
  }
}
files: null,

// upload an image from clipboard {Boolean, Number in ms}
// the input should be completely into view by pasting
// this feature is available only in upload mode
// compatible only for Chrome
clipboardPaste: 2000,

// input with the listed files {Boolean, String}
// this list is an input[type="hidden"]
// this list will be generated from each choosed/appended file name in a JSON format. You can use the onListInput callback to mainpulate this list
// files in this list that are "0://file_name.ext" are showing to PHP that they are choosed and should be uploaded
// if you've appended some files on the server-side, PHP will check if each appended file is in this list, if not, PHP will set it as removed. Also, it is very important if you have appended files
// example: true
// example: 'custom_listInput_name'
listInput: true,

// enable API methods {Boolean}
// if it will be true, you can use API methods like writing this code:
// var api = $.fileuploader.getInstance(input_element); (check api example to see all available methods)
enableApi: false,

// standard input events {null, Object}
// bind standard Javascript input events
// example: {
  click: function(event) {
    // input was clicked
  }
}
listeners: null,

// Callback fired when fileuploader is not supported in your browser
onSupportError: function(parentEl, inputEl) {
  // callback will go here
},

// Callback fired before rendering the fileuploader elements
// by returning false, you will prevent the rendering
beforeRender: function(parentEl, inputEl) {
  // callback will go here
  
  return true;
},

// Callback fired after rendering the fileuploader elements
afterRender: function(listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
},

// Callback fired after selecting the files from computer but only before processing them
// by returning false, you will prevent the processing of the files but they will remain in the input
beforeSelect: function(files, listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
  
  return true;
},

// Callback fired on checking for warnings the choosed files
// by returning false, you will prevent the files from adding/uploading
onFilesCheck: function(files, options, listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
  
  return true;
},

// Callback fired on selecting and processing a file
onSelect: function(item, listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
},

// Callback fired after selecting and processing of all files
afterSelect: function(listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
},

// Callback fired after generating a list input. Needs to return an array!
// by default - null
onListInput: function(fileList, listInputEl, listEl, parentEl, newInputEl, inputEl) {
  var list = [];

  $.each(fileList, function(index, value) {
    list.push(value.name);
  });

  return list;
},

// Callback fired after deleting a file
// by returning false, you can prevent a file from removing
onRemove: function(item, listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
  
  return true;
},

// Callback fired when fileuploader has no files
onEmpty: function(listEl, parentEl, newInputEl, inputEl) {
  // callback will go here
},

// dialogs
// made to let you customizing the standard Javascript dialogs
// this dialogs are used by showing a file warning or confirming a file removing
dialogs: {

  // alert dialog
  alert: function(text) {
    return alert(text);
  },
  
  // confirm dialog
  confirm: function(text, callback) {
    confirm(text) ? callback() : null;
  }
},

// captions
captions: {
  button: function(options) { return 'Choose ' + (options.limit == 1 ? 'File' : 'Files'); },
  feedback: function(options) { return 'Choose ' + (options.limit == 1 ? 'file' : 'files') + ' to upload'; },
  feedback2: function(options) { return options.length + ' ' + (options.length > 1 ? ' files were' : ' file was') + ' chosen'; },
  drop: 'Drop the files here to Upload',
  paste: '<div class="fileuploader-pending-loader"><div class="left-half" style="animation-duration: ${ms}s"></div><div class="spinner" style="animation-duration: ${ms}s"></div><div class="right-half" style="animation-duration: ${ms}s"></div></div> Pasting a file, click here to cancel.',
  removeConfirmation: 'Are you sure you want to remove this file?',
  errors: {
    filesLimit: 'Only ${limit} files are allowed to be uploaded.',
    filesType: 'Only ${extensions} files are allowed to be uploaded.',
    fileSize: '${name} is too large! Please choose a file up to ${fileMaxSize}MB.',
    filesSizeAll: 'Files that you choosed are too large! Please upload files up to ${maxSize} MB.',
    fileName: 'File with the name ${name} is already selected.',
    folderUpload: 'You are not allowed to upload folders.'
  }
}

6. PHP Options.

array (
  // limit of files {null, Number}
  // also with the appended files
  // if null - has no limits
  // example: 3
  'limit' => null,
  
  // file's maximal size in MB {null, Number}
  // also with the appended files
  // if null - has no limits
  // example: 2
  'maxSize' => null,
  
  // each file's maximal size in MB {null, Number}
  // if null - has no limits
  // example: 2
  'fileMaxSize' => null,
  
  // allowed extensions or file types {null, Array}
  // if null - has no limits
  // example: ['jpg', 'jpeg', 'png', 'audio/mp3', 'text/plain']
  'extensions' => null,
  
  // check if file input exists ($_FILES[ file_input_name ]) {Boolean}
  // check if files were choosed (minimum 1 file should be choosed)
  'required' => false,
  
  // upload directory {String}
  // note that main directory is the directory where you are initializing the FileUploader class
  // example: '../uploads/'
  'uploadDir' => 'uploads/',
  
  // file title {String, Array}
  // example: 'name' - original file name
  // example: 'auto' - random text from 12 letters
  // example: 'my_custom_filename' - custom file name
  // example: 'my_custom_filename_{random}' - my_custom_filename_(+ random text from 12 letters)
  // '{random} {file_name} {file_size} {timestamp} {date} {extension}' - variables that can be used to generate a new file name
  // example: array('auto', 24) - [0] is a string as in the examples above, [1] is the length of the random string
  'title' => 'name',
  
  // replace the file with the same name? {Boolean}
  // if it will be false - will automatically generate a new file name with (1,2,3...) at the end of the file name
  'replace' => false,
  
  // input with the listed files {Boolean, String}
  // this list is an input[type="hidden"]
  // this list is important to check which files shouldn't be uploaded or need to be removed
  // example: true
  // example: 'custom_listInput_name'
  'listInput' => true,
  
  // appended files {null, Array with arrays}
  // it is important to declare them if you want to check the right limit and maxSize options; by appended files; by generating an input
  // please follow this structure for each file:
  array(
    "name" => 'filename1.txt',
    "type" => FileUploader::mime_content_type('uploads/filename1.txt'),
    "size" => filesize('uploads/filename1.txt'),
    "file" => 'uploads/filename1.txt',
    "data" => array(
      "url" => 'http://localhost/example/uploads/filename1.txt',
      "another_attribute" => "ok"
    )
  )
  'files' => null
)

7. You can configurate the Fileuploader not only in Javascript but also setting some input attributes in HTML.

<!-- limit option {Number} -->
data-fileuploader-limit="2"

<!-- maxSize option {Number} -->
data-fileuploader-maxSize="3"

<!-- fileMaxSize option {Number} -->
data-fileuploader-fileMaxSize="1"

<!-- extensions option {Comma spliced String} -->
data-fileuploader-fileMaxSize="jpg, png, gif"

<!-- theme option {String} -->
data-fileuploader-theme="default"

<!-- listInput option {String} -->
data-fileuploader-listInput="myCustomName"

<!-- files option {JSON String} -->
data-fileuploader-files='"[{"name":"filename1.txt","size":1024,"type":"text/plain","file":"uploads/filename1.txt"}]"'

8. Available API methods.

// get Fileuploader input element
api.getInputEl();

// get Fileuploader new/generated input element
api.getNewInputEl();

// get Fileuploader thumbnails list element
api.getListEl();

// get Fileuploader listInput element
api.getListInputEl();

// get Fileuploader file items
api.getFiles();

// get Fileuploader choosed file items
api.getChoosedFiles();

// get Fileuploader appended file items
api.getAppendedFiles();

// get Fileuploader uploaded file items
api.getUploadedFiles();

// get Fileuploader list of files using custom key
api.getFileList(toJSON, customItemKey);

// set Fileuploader option
api.setOption(key, value);

// get an Fileuploader item data by giving an item HTML element
api.findFile(itemHtmlElement);

// append file (Object) / files(Array with Objects)
api.append(file);

// remove an item by giving an item Object or item HTML element
api.remove(item);

// reset the Fileuploader input
api.reset();

// disable Fileuploader input
api.disable(also_lock_item_remove_startUpload_retry_action);

// enable Fileuploader input
api.enable();

// return true if there are no files
api.isEmpty();

// return true if the input is disabled
api.isDisabled();

// return true if the input is rendered
api.isRendered();

// return the plugin mode ('default', 'addMore', 'upload')
api.getPluginMode();

// generate a text with variables
api.assets.textParse(myText, myObjectWithVariables);

// destroy Fileuploader
api.destroy();

9. PHP API.

<?php
  include('class.fileuploader.php');

  // initialize the FileUploader
  $FileUploader = new FileUploader('input_file_name', array(
    // Options will go here
  ));

  // call to upload the files
  $upload = $FileUploader->upload();

  if($upload['isSuccess']) {
    // get the uploaded files
    $files = $upload['files'];
  }
  if($upload['hasWarnings']) {
    // get the warnings
    $warnings = $upload['warnings'];
  };

  // get listInput value
  $FileUploader->getListInput();

        // get removed list
        // give a String parameter (ex: 'file' or 'name' or 'data.url') to get a file by a custom input attribute. Default is 'file'
        // note that FileUploader will not remove your appended files that were removed on Front-End
        // to remove them, please use this example: 
        // foreach($FileUploader->getRemovedFiles('file') as $key=>$value) {
        //     unlink('../uploads/' . $value['name']);
        // }
  $FileUploader->getRemovedFiles();

  // get the list of the files
  // without parameter it will return an array with appended and uploaded files
  // give a String parameter (ex: 'file' or 'name' or 'data.url') to generate a custom input list of the files
  // example: you can store the files in the MySQL using this function
  // $myFilesForSql = implode('|', $FileUploader->getFileList('name'));
  // $myFilesForSql = json_encode($FileUploader->getFileList('name'));
  $FileUploader->getFileList();

  // get the HTML generated input
  $FileUploader->generateInput();
?>

This awesome jQuery plugin is developed by innostudio. For more Advanced Usages, please check the demo page or visit the official website.