s3_cors_fileupload 0.2.0 → 0.2.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +12 -2
- data/Gemfile +1 -1
- data/Gemfile.lock +19 -19
- data/README.md +13 -1
- data/lib/generators/s3_cors_fileupload/install/templates/s3_uploads.js +1 -2
- data/lib/generators/s3_cors_fileupload/install/templates/source_file.rb +1 -1
- data/lib/generators/s3_cors_fileupload/install/templates/views/erb/_template_download.html.erb +19 -16
- data/lib/generators/s3_cors_fileupload/install/templates/views/erb/_template_upload.html.erb +31 -26
- data/lib/generators/s3_cors_fileupload/install/templates/views/erb/_template_uploaded.html.erb +18 -13
- data/lib/generators/s3_cors_fileupload/install/templates/views/erb/index.html.erb +1 -1
- data/lib/generators/s3_cors_fileupload/install/templates/views/haml/_template_download.html.haml +16 -21
- data/lib/generators/s3_cors_fileupload/install/templates/views/haml/_template_upload.html.haml +15 -18
- data/lib/generators/s3_cors_fileupload/install/templates/views/haml/_template_uploaded.html.haml +12 -13
- data/lib/generators/s3_cors_fileupload/install/templates/views/haml/index.html.haml +1 -1
- data/lib/s3_cors_fileupload/rails/form_helper.rb +16 -14
- data/lib/s3_cors_fileupload/version.rb +3 -3
- data/vendor/assets/javascripts/s3_cors_fileupload/index.js +4 -1
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.fileupload-image.js +213 -0
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.fileupload-process.js +164 -0
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.fileupload-ui.js +62 -228
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.fileupload-validate.js +116 -0
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.fileupload.js +212 -84
- data/vendor/assets/javascripts/s3_cors_fileupload/jquery.iframe-transport.js +24 -4
- data/vendor/assets/javascripts/s3_cors_fileupload/vendor/jquery.ui.widget.js +1 -1
- data/vendor/assets/javascripts/s3_cors_fileupload/vendor/load-image.js +138 -172
- data/vendor/assets/javascripts/s3_cors_fileupload/vendor/tmpl.js +3 -4
- data/vendor/assets/stylesheets/jquery.fileupload-ui.css.erb +12 -28
- metadata +5 -2
@@ -1,5 +1,5 @@
|
|
1
1
|
/*
|
2
|
-
* jQuery File Upload Plugin 5.
|
2
|
+
* jQuery File Upload Plugin 5.32.0
|
3
3
|
* https://github.com/blueimp/jQuery-File-Upload
|
4
4
|
*
|
5
5
|
* Copyright 2010, Sebastian Tschan
|
@@ -10,7 +10,7 @@
|
|
10
10
|
*/
|
11
11
|
|
12
12
|
/*jslint nomen: true, unparam: true, regexp: true */
|
13
|
-
/*global define, window, document, File, Blob, FormData
|
13
|
+
/*global define, window, document, location, File, Blob, FormData */
|
14
14
|
|
15
15
|
(function (factory) {
|
16
16
|
'use strict';
|
@@ -27,12 +27,28 @@
|
|
27
27
|
}(function ($) {
|
28
28
|
'use strict';
|
29
29
|
|
30
|
+
// Detect file input support, based on
|
31
|
+
// http://viljamis.com/blog/2012/file-upload-support-on-mobile/
|
32
|
+
$.support.fileInput = !(new RegExp(
|
33
|
+
// Handle devices which give false positives for the feature detection:
|
34
|
+
'(Android (1\\.[0156]|2\\.[01]))' +
|
35
|
+
'|(Windows Phone (OS 7|8\\.0))|(XBLWP)|(ZuneWP)' +
|
36
|
+
'|(w(eb)?OSBrowser)|(webOS)' +
|
37
|
+
'|(Kindle/(1\\.0|2\\.[05]|3\\.0))'
|
38
|
+
).test(window.navigator.userAgent) ||
|
39
|
+
// Feature detection for all other devices:
|
40
|
+
$('<input type="file">').prop('disabled'));
|
41
|
+
|
30
42
|
// The FileReader API is not actually used, but works as feature detection,
|
31
43
|
// as e.g. Safari supports XHR file uploads via the FormData API,
|
32
44
|
// but not non-multipart XHR file uploads:
|
33
45
|
$.support.xhrFileUpload = !!(window.XMLHttpRequestUpload && window.FileReader);
|
34
46
|
$.support.xhrFormDataFileUpload = !!window.FormData;
|
35
47
|
|
48
|
+
// Detect support for Blob slicing (required for chunked uploads):
|
49
|
+
$.support.blobSlice = window.Blob && (Blob.prototype.slice ||
|
50
|
+
Blob.prototype.webkitSlice || Blob.prototype.mozSlice);
|
51
|
+
|
36
52
|
// The fileupload widget listens for change events on file input fields defined
|
37
53
|
// via fileInput setting and paste or drop events of the given dropZone.
|
38
54
|
// In addition to the default jQuery Widget methods, the fileupload widget
|
@@ -115,6 +131,23 @@
|
|
115
131
|
// By default, uploads are started automatically when adding files:
|
116
132
|
autoUpload: true,
|
117
133
|
|
134
|
+
// Error and info messages:
|
135
|
+
messages: {
|
136
|
+
uploadedBytes: 'Uploaded bytes exceed file size'
|
137
|
+
},
|
138
|
+
|
139
|
+
// Translation function, gets the message key to be translated
|
140
|
+
// and an object with context specific data as arguments:
|
141
|
+
i18n: function (message, context) {
|
142
|
+
message = this.messages[message] || message.toString();
|
143
|
+
if (context) {
|
144
|
+
$.each(context, function (key, value) {
|
145
|
+
message = message.replace('{' + key + '}', value);
|
146
|
+
});
|
147
|
+
}
|
148
|
+
return message;
|
149
|
+
},
|
150
|
+
|
118
151
|
// Additional form data to be sent along with the file uploads can be set
|
119
152
|
// using this option, which accepts an array of objects with name and
|
120
153
|
// value properties, a function returning such an array, a FormData
|
@@ -127,21 +160,25 @@
|
|
127
160
|
// The add callback is invoked as soon as files are added to the fileupload
|
128
161
|
// widget (via file input selection, drag & drop, paste or add API call).
|
129
162
|
// If the singleFileUploads option is enabled, this callback will be
|
130
|
-
// called once for each file in the selection for XHR file
|
163
|
+
// called once for each file in the selection for XHR file uploads, else
|
131
164
|
// once for each file selection.
|
165
|
+
//
|
132
166
|
// The upload starts when the submit method is invoked on the data parameter.
|
133
167
|
// The data object contains a files property holding the added files
|
134
|
-
// and allows to override plugin options as well as define ajax settings.
|
168
|
+
// and allows you to override plugin options as well as define ajax settings.
|
169
|
+
//
|
135
170
|
// Listeners for this callback can also be bound the following way:
|
136
171
|
// .bind('fileuploadadd', func);
|
172
|
+
//
|
137
173
|
// data.submit() returns a Promise object and allows to attach additional
|
138
174
|
// handlers using jQuery's Deferred callbacks:
|
139
175
|
// data.submit().done(func).fail(func).always(func);
|
140
176
|
add: function (e, data) {
|
141
177
|
if (data.autoUpload || (data.autoUpload !== false &&
|
142
|
-
|
143
|
-
|
144
|
-
|
178
|
+
$(this).fileupload('option', 'autoUpload'))) {
|
179
|
+
data.process().done(function () {
|
180
|
+
data.submit();
|
181
|
+
});
|
145
182
|
}
|
146
183
|
},
|
147
184
|
|
@@ -205,8 +242,9 @@
|
|
205
242
|
cache: false
|
206
243
|
},
|
207
244
|
|
208
|
-
// A list of options that require
|
209
|
-
|
245
|
+
// A list of options that require reinitializing event listeners and/or
|
246
|
+
// special initialization code:
|
247
|
+
_specialOptions: [
|
210
248
|
'fileInput',
|
211
249
|
'dropZone',
|
212
250
|
'pasteZone',
|
@@ -214,8 +252,13 @@
|
|
214
252
|
'forceIframeTransport'
|
215
253
|
],
|
216
254
|
|
255
|
+
_blobSlice: $.support.blobSlice && function () {
|
256
|
+
var slice = this.slice || this.webkitSlice || this.mozSlice;
|
257
|
+
return slice.apply(this, arguments);
|
258
|
+
},
|
259
|
+
|
217
260
|
_BitrateTimer: function () {
|
218
|
-
this.timestamp =
|
261
|
+
this.timestamp = ((Date.now) ? Date.now() : (new Date()).getTime());
|
219
262
|
this.loaded = 0;
|
220
263
|
this.bitrate = 0;
|
221
264
|
this.getBitrate = function (now, loaded, interval) {
|
@@ -243,7 +286,7 @@
|
|
243
286
|
if ($.isArray(options.formData)) {
|
244
287
|
return options.formData;
|
245
288
|
}
|
246
|
-
if (options.formData) {
|
289
|
+
if ($.type(options.formData) === 'object') {
|
247
290
|
formData = [];
|
248
291
|
$.each(options.formData, function (name, value) {
|
249
292
|
formData.push({name: name, value: value});
|
@@ -262,16 +305,34 @@
|
|
262
305
|
},
|
263
306
|
|
264
307
|
_initProgressObject: function (obj) {
|
265
|
-
|
308
|
+
var progress = {
|
266
309
|
loaded: 0,
|
267
310
|
total: 0,
|
268
311
|
bitrate: 0
|
269
312
|
};
|
313
|
+
if (obj._progress) {
|
314
|
+
$.extend(obj._progress, progress);
|
315
|
+
} else {
|
316
|
+
obj._progress = progress;
|
317
|
+
}
|
318
|
+
},
|
319
|
+
|
320
|
+
_initResponseObject: function (obj) {
|
321
|
+
var prop;
|
322
|
+
if (obj._response) {
|
323
|
+
for (prop in obj._response) {
|
324
|
+
if (obj._response.hasOwnProperty(prop)) {
|
325
|
+
delete obj._response[prop];
|
326
|
+
}
|
327
|
+
}
|
328
|
+
} else {
|
329
|
+
obj._response = {};
|
330
|
+
}
|
270
331
|
},
|
271
332
|
|
272
333
|
_onProgress: function (e, data) {
|
273
334
|
if (e.lengthComputable) {
|
274
|
-
var now =
|
335
|
+
var now = ((Date.now) ? Date.now() : (new Date()).getTime()),
|
275
336
|
loaded;
|
276
337
|
if (data._time && data.progressInterval &&
|
277
338
|
(now - data._time < data.progressInterval) &&
|
@@ -326,8 +387,14 @@
|
|
326
387
|
}
|
327
388
|
},
|
328
389
|
|
390
|
+
_isInstanceOf: function (type, obj) {
|
391
|
+
// Cross-frame instanceof check
|
392
|
+
return Object.prototype.toString.call(obj) === '[object ' + type + ']';
|
393
|
+
},
|
394
|
+
|
329
395
|
_initXHRData: function (options) {
|
330
|
-
var
|
396
|
+
var that = this,
|
397
|
+
formData,
|
331
398
|
file = options.files[0],
|
332
399
|
// Ignore non-multipart setting if not supported:
|
333
400
|
multipart = options.multipart || !$.support.xhrFileUpload,
|
@@ -336,9 +403,11 @@
|
|
336
403
|
if (options.contentRange) {
|
337
404
|
options.headers['Content-Range'] = options.contentRange;
|
338
405
|
}
|
339
|
-
if (!multipart) {
|
406
|
+
if (!multipart || options.blob || !this._isInstanceOf('File', file)) {
|
340
407
|
options.headers['Content-Disposition'] = 'attachment; filename="' +
|
341
408
|
encodeURI(file.name) + '"';
|
409
|
+
}
|
410
|
+
if (!multipart) {
|
342
411
|
options.contentType = file.type;
|
343
412
|
options.data = options.blob || file;
|
344
413
|
} else if ($.support.xhrFormDataFileUpload) {
|
@@ -362,7 +431,7 @@
|
|
362
431
|
});
|
363
432
|
}
|
364
433
|
} else {
|
365
|
-
if (options.formData
|
434
|
+
if (that._isInstanceOf('FormData', options.formData)) {
|
366
435
|
formData = options.formData;
|
367
436
|
} else {
|
368
437
|
formData = new FormData();
|
@@ -371,17 +440,13 @@
|
|
371
440
|
});
|
372
441
|
}
|
373
442
|
if (options.blob) {
|
374
|
-
options.headers['Content-Disposition'] = 'attachment; filename="' +
|
375
|
-
encodeURI(file.name) + '"';
|
376
443
|
formData.append(paramName, options.blob, file.name);
|
377
444
|
} else {
|
378
445
|
$.each(options.files, function (index, file) {
|
379
|
-
// Files are also Blob instances, but some browsers
|
380
|
-
// (Firefox 3.6) support the File API but not Blobs.
|
381
446
|
// This check allows the tests to run with
|
382
447
|
// dummy objects:
|
383
|
-
if ((
|
384
|
-
(
|
448
|
+
if (that._isInstanceOf('File', file) ||
|
449
|
+
that._isInstanceOf('Blob', file)) {
|
385
450
|
formData.append(
|
386
451
|
options.paramName[index] || paramName,
|
387
452
|
file,
|
@@ -398,13 +463,13 @@
|
|
398
463
|
},
|
399
464
|
|
400
465
|
_initIframeSettings: function (options) {
|
466
|
+
var targetHost = $('<a></a>').prop('href', options.url).prop('host');
|
401
467
|
// Setting the dataType to iframe enables the iframe transport:
|
402
468
|
options.dataType = 'iframe ' + (options.dataType || '');
|
403
469
|
// The iframe transport accepts a serialized array as form data:
|
404
470
|
options.formData = this._getFormData(options);
|
405
471
|
// Add redirect url to form data on cross-domain uploads:
|
406
|
-
if (options.redirect &&
|
407
|
-
.prop('host') !== location.host) {
|
472
|
+
if (options.redirect && targetHost && targetHost !== location.host) {
|
408
473
|
options.formData.push({
|
409
474
|
name: options.redirectParamName || 'redirect',
|
410
475
|
value: options.redirect
|
@@ -426,7 +491,7 @@
|
|
426
491
|
options.dataType = 'postmessage ' + (options.dataType || '');
|
427
492
|
}
|
428
493
|
} else {
|
429
|
-
this._initIframeSettings(options
|
494
|
+
this._initIframeSettings(options);
|
430
495
|
}
|
431
496
|
},
|
432
497
|
|
@@ -526,9 +591,20 @@
|
|
526
591
|
return this._enhancePromise(promise);
|
527
592
|
},
|
528
593
|
|
529
|
-
// Adds convenience methods to the callback
|
594
|
+
// Adds convenience methods to the data callback argument:
|
530
595
|
_addConvenienceMethods: function (e, data) {
|
531
|
-
var that = this
|
596
|
+
var that = this,
|
597
|
+
getPromise = function (data) {
|
598
|
+
return $.Deferred().resolveWith(that, [data]).promise();
|
599
|
+
};
|
600
|
+
data.process = function (resolveFunc, rejectFunc) {
|
601
|
+
if (resolveFunc || rejectFunc) {
|
602
|
+
data._processQueue = this._processQueue =
|
603
|
+
(this._processQueue || getPromise(this))
|
604
|
+
.pipe(resolveFunc, rejectFunc);
|
605
|
+
}
|
606
|
+
return this._processQueue || getPromise(this);
|
607
|
+
};
|
532
608
|
data.submit = function () {
|
533
609
|
if (this.state() !== 'pending') {
|
534
610
|
data.jqXHR = this.jqXHR =
|
@@ -541,16 +617,22 @@
|
|
541
617
|
if (this.jqXHR) {
|
542
618
|
return this.jqXHR.abort();
|
543
619
|
}
|
544
|
-
return
|
620
|
+
return that._getXHRPromise();
|
545
621
|
};
|
546
622
|
data.state = function () {
|
547
623
|
if (this.jqXHR) {
|
548
624
|
return that._getDeferredState(this.jqXHR);
|
549
625
|
}
|
626
|
+
if (this._processQueue) {
|
627
|
+
return that._getDeferredState(this._processQueue);
|
628
|
+
}
|
550
629
|
};
|
551
630
|
data.progress = function () {
|
552
631
|
return this._progress;
|
553
632
|
};
|
633
|
+
data.response = function () {
|
634
|
+
return this._response;
|
635
|
+
};
|
554
636
|
},
|
555
637
|
|
556
638
|
// Parses the Range header from the server response
|
@@ -569,12 +651,13 @@
|
|
569
651
|
// should be uploaded in chunks, but does not invoke any
|
570
652
|
// upload requests:
|
571
653
|
_chunkedUpload: function (options, testOnly) {
|
654
|
+
options.uploadedBytes = options.uploadedBytes || 0;
|
572
655
|
var that = this,
|
573
656
|
file = options.files[0],
|
574
657
|
fs = file.size,
|
575
|
-
ub = options.uploadedBytes
|
658
|
+
ub = options.uploadedBytes,
|
576
659
|
mcs = options.maxChunkSize || fs,
|
577
|
-
slice =
|
660
|
+
slice = this._blobSlice,
|
578
661
|
dfd = $.Deferred(),
|
579
662
|
promise = dfd.promise(),
|
580
663
|
jqXHR,
|
@@ -587,7 +670,7 @@
|
|
587
670
|
return true;
|
588
671
|
}
|
589
672
|
if (ub >= fs) {
|
590
|
-
file.error = '
|
673
|
+
file.error = options.i18n('uploadedBytes');
|
591
674
|
return this._getXHRPromise(
|
592
675
|
false,
|
593
676
|
options.context,
|
@@ -623,7 +706,7 @@
|
|
623
706
|
// Create a progress event if no final progress event
|
624
707
|
// with loaded equaling total has been triggered
|
625
708
|
// for this chunk:
|
626
|
-
if (o._progress.loaded
|
709
|
+
if (currentLoaded + o.chunkSize - o._progress.loaded) {
|
627
710
|
that._onProgress($.Event('progress', {
|
628
711
|
lengthComputable: true,
|
629
712
|
loaded: ub - o.uploadedBytes,
|
@@ -679,9 +762,11 @@
|
|
679
762
|
this._progress.loaded = this._progress.total = 0;
|
680
763
|
this._progress.bitrate = 0;
|
681
764
|
}
|
682
|
-
|
683
|
-
|
684
|
-
|
765
|
+
// Make sure the container objects for the .response() and
|
766
|
+
// .progress() methods on the data object are available
|
767
|
+
// and reset to their initial state:
|
768
|
+
this._initResponseObject(data);
|
769
|
+
this._initProgressObject(data);
|
685
770
|
data._progress.loaded = data.loaded = data.uploadedBytes || 0;
|
686
771
|
data._progress.total = data.total = this._getTotal(data.files) || 1;
|
687
772
|
data._progress.bitrate = data.bitrate = 0;
|
@@ -692,7 +777,8 @@
|
|
692
777
|
},
|
693
778
|
|
694
779
|
_onDone: function (result, textStatus, jqXHR, options) {
|
695
|
-
var total = options._progress.total
|
780
|
+
var total = options._progress.total,
|
781
|
+
response = options._response;
|
696
782
|
if (options._progress.loaded < total) {
|
697
783
|
// Create a progress event if no final progress event
|
698
784
|
// with loaded equaling total has been triggered:
|
@@ -702,35 +788,30 @@
|
|
702
788
|
total: total
|
703
789
|
}), options);
|
704
790
|
}
|
705
|
-
options.result = result;
|
706
|
-
options.textStatus = textStatus;
|
707
|
-
options.jqXHR = jqXHR;
|
791
|
+
response.result = options.result = result;
|
792
|
+
response.textStatus = options.textStatus = textStatus;
|
793
|
+
response.jqXHR = options.jqXHR = jqXHR;
|
708
794
|
this._trigger('done', null, options);
|
709
795
|
},
|
710
796
|
|
711
797
|
_onFail: function (jqXHR, textStatus, errorThrown, options) {
|
712
|
-
|
713
|
-
options.textStatus = textStatus;
|
714
|
-
options.errorThrown = errorThrown;
|
715
|
-
this._trigger('fail', null, options);
|
798
|
+
var response = options._response;
|
716
799
|
if (options.recalculateProgress) {
|
717
800
|
// Remove the failed (error or abort) file upload from
|
718
801
|
// the global progress calculation:
|
719
802
|
this._progress.loaded -= options._progress.loaded;
|
720
803
|
this._progress.total -= options._progress.total;
|
721
804
|
}
|
805
|
+
response.jqXHR = options.jqXHR = jqXHR;
|
806
|
+
response.textStatus = options.textStatus = textStatus;
|
807
|
+
response.errorThrown = options.errorThrown = errorThrown;
|
808
|
+
this._trigger('fail', null, options);
|
722
809
|
},
|
723
810
|
|
724
811
|
_onAlways: function (jqXHRorResult, textStatus, jqXHRorError, options) {
|
725
812
|
// jqXHRorResult, textStatus and jqXHRorError are added to the
|
726
813
|
// options object via done and fail callbacks
|
727
|
-
this._active -= 1;
|
728
814
|
this._trigger('always', null, options);
|
729
|
-
if (this._active === 0) {
|
730
|
-
// The stop callback is triggered when all uploads have
|
731
|
-
// been completed, equivalent to the global ajaxStop event:
|
732
|
-
this._trigger('stop');
|
733
|
-
}
|
734
815
|
},
|
735
816
|
|
736
817
|
_onSend: function (e, data) {
|
@@ -756,13 +837,14 @@
|
|
756
837
|
}).fail(function (jqXHR, textStatus, errorThrown) {
|
757
838
|
that._onFail(jqXHR, textStatus, errorThrown, options);
|
758
839
|
}).always(function (jqXHRorResult, textStatus, jqXHRorError) {
|
759
|
-
that._sending -= 1;
|
760
840
|
that._onAlways(
|
761
841
|
jqXHRorResult,
|
762
842
|
textStatus,
|
763
843
|
jqXHRorError,
|
764
844
|
options
|
765
845
|
);
|
846
|
+
that._sending -= 1;
|
847
|
+
that._active -= 1;
|
766
848
|
if (options.limitConcurrentUploads &&
|
767
849
|
options.limitConcurrentUploads > that._sending) {
|
768
850
|
// Start the next queued upload,
|
@@ -776,6 +858,11 @@
|
|
776
858
|
nextSlot = that._slots.shift();
|
777
859
|
}
|
778
860
|
}
|
861
|
+
if (that._active === 0) {
|
862
|
+
// The stop callback is triggered when all uploads have
|
863
|
+
// been completed, equivalent to the global ajaxStop event:
|
864
|
+
that._trigger('stop');
|
865
|
+
}
|
779
866
|
});
|
780
867
|
return jqXHR;
|
781
868
|
};
|
@@ -788,7 +875,8 @@
|
|
788
875
|
this._slots.push(slot);
|
789
876
|
pipe = slot.pipe(send);
|
790
877
|
} else {
|
791
|
-
|
878
|
+
this._sequence = this._sequence.pipe(send, send);
|
879
|
+
pipe = this._sequence;
|
792
880
|
}
|
793
881
|
// Return the piped Promise object, enhanced with an abort method,
|
794
882
|
// which is delegated to the jqXHR object of the current upload,
|
@@ -841,6 +929,7 @@
|
|
841
929
|
var newData = $.extend({}, data);
|
842
930
|
newData.files = fileSet ? element : [element];
|
843
931
|
newData.paramName = paramNameSet[index];
|
932
|
+
that._initResponseObject(newData);
|
844
933
|
that._initProgressObject(newData);
|
845
934
|
that._addConvenienceMethods(e, newData);
|
846
935
|
result = that._trigger('add', e, newData);
|
@@ -1019,44 +1108,50 @@
|
|
1019
1108
|
},
|
1020
1109
|
|
1021
1110
|
_onPaste: function (e) {
|
1022
|
-
var
|
1023
|
-
|
1111
|
+
var items = e.originalEvent && e.originalEvent.clipboardData &&
|
1112
|
+
e.originalEvent.clipboardData.items,
|
1024
1113
|
data = {files: []};
|
1025
|
-
|
1026
|
-
|
1027
|
-
|
1028
|
-
|
1114
|
+
if (items && items.length) {
|
1115
|
+
$.each(items, function (index, item) {
|
1116
|
+
var file = item.getAsFile && item.getAsFile();
|
1117
|
+
if (file) {
|
1118
|
+
data.files.push(file);
|
1119
|
+
}
|
1120
|
+
});
|
1121
|
+
if (this._trigger('paste', e, data) === false ||
|
1122
|
+
this._onAdd(e, data) === false) {
|
1123
|
+
return false;
|
1029
1124
|
}
|
1030
|
-
});
|
1031
|
-
if (this._trigger('paste', e, data) === false ||
|
1032
|
-
this._onAdd(e, data) === false) {
|
1033
|
-
return false;
|
1034
1125
|
}
|
1035
1126
|
},
|
1036
1127
|
|
1037
1128
|
_onDrop: function (e) {
|
1129
|
+
e.dataTransfer = e.originalEvent && e.originalEvent.dataTransfer;
|
1038
1130
|
var that = this,
|
1039
|
-
dataTransfer = e.dataTransfer
|
1131
|
+
dataTransfer = e.dataTransfer,
|
1040
1132
|
data = {};
|
1041
1133
|
if (dataTransfer && dataTransfer.files && dataTransfer.files.length) {
|
1042
1134
|
e.preventDefault();
|
1135
|
+
this._getDroppedFiles(dataTransfer).always(function (files) {
|
1136
|
+
data.files = files;
|
1137
|
+
if (that._trigger('drop', e, data) !== false) {
|
1138
|
+
that._onAdd(e, data);
|
1139
|
+
}
|
1140
|
+
});
|
1043
1141
|
}
|
1044
|
-
this._getDroppedFiles(dataTransfer).always(function (files) {
|
1045
|
-
data.files = files;
|
1046
|
-
if (that._trigger('drop', e, data) !== false) {
|
1047
|
-
that._onAdd(e, data);
|
1048
|
-
}
|
1049
|
-
});
|
1050
1142
|
},
|
1051
1143
|
|
1052
1144
|
_onDragOver: function (e) {
|
1053
|
-
|
1054
|
-
|
1055
|
-
|
1056
|
-
|
1057
|
-
|
1058
|
-
|
1059
|
-
|
1145
|
+
e.dataTransfer = e.originalEvent && e.originalEvent.dataTransfer;
|
1146
|
+
var dataTransfer = e.dataTransfer;
|
1147
|
+
if (dataTransfer) {
|
1148
|
+
if (this._trigger('dragover', e) === false) {
|
1149
|
+
return false;
|
1150
|
+
}
|
1151
|
+
if ($.inArray('Files', dataTransfer.types) !== -1) {
|
1152
|
+
dataTransfer.dropEffect = 'copy';
|
1153
|
+
e.preventDefault();
|
1154
|
+
}
|
1060
1155
|
}
|
1061
1156
|
},
|
1062
1157
|
|
@@ -1070,9 +1165,11 @@
|
|
1070
1165
|
paste: this._onPaste
|
1071
1166
|
});
|
1072
1167
|
}
|
1073
|
-
|
1074
|
-
|
1075
|
-
|
1168
|
+
if ($.support.fileInput) {
|
1169
|
+
this._on(this.options.fileInput, {
|
1170
|
+
change: this._onChange
|
1171
|
+
});
|
1172
|
+
}
|
1076
1173
|
},
|
1077
1174
|
|
1078
1175
|
_destroyEventHandlers: function () {
|
@@ -1082,12 +1179,12 @@
|
|
1082
1179
|
},
|
1083
1180
|
|
1084
1181
|
_setOption: function (key, value) {
|
1085
|
-
var
|
1086
|
-
if (
|
1182
|
+
var reinit = $.inArray(key, this._specialOptions) !== -1;
|
1183
|
+
if (reinit) {
|
1087
1184
|
this._destroyEventHandlers();
|
1088
1185
|
}
|
1089
1186
|
this._super(key, value);
|
1090
|
-
if (
|
1187
|
+
if (reinit) {
|
1091
1188
|
this._initSpecialOptions();
|
1092
1189
|
this._initEventHandlers();
|
1093
1190
|
}
|
@@ -1109,10 +1206,35 @@
|
|
1109
1206
|
}
|
1110
1207
|
},
|
1111
1208
|
|
1112
|
-
|
1113
|
-
var
|
1209
|
+
_getRegExp: function (str) {
|
1210
|
+
var parts = str.split('/'),
|
1211
|
+
modifiers = parts.pop();
|
1212
|
+
parts.shift();
|
1213
|
+
return new RegExp(parts.join('/'), modifiers);
|
1214
|
+
},
|
1215
|
+
|
1216
|
+
_isRegExpOption: function (key, value) {
|
1217
|
+
return key !== 'url' && $.type(value) === 'string' &&
|
1218
|
+
/^\/.*\/[igm]{0,3}$/.test(value);
|
1219
|
+
},
|
1220
|
+
|
1221
|
+
_initDataAttributes: function () {
|
1222
|
+
var that = this,
|
1223
|
+
options = this.options;
|
1114
1224
|
// Initialize options set via HTML5 data-attributes:
|
1115
|
-
$.
|
1225
|
+
$.each(
|
1226
|
+
$(this.element[0].cloneNode(false)).data(),
|
1227
|
+
function (key, value) {
|
1228
|
+
if (that._isRegExpOption(key, value)) {
|
1229
|
+
value = that._getRegExp(value);
|
1230
|
+
}
|
1231
|
+
options[key] = value;
|
1232
|
+
}
|
1233
|
+
);
|
1234
|
+
},
|
1235
|
+
|
1236
|
+
_create: function () {
|
1237
|
+
this._initDataAttributes();
|
1116
1238
|
this._initSpecialOptions();
|
1117
1239
|
this._slots = [];
|
1118
1240
|
this._sequence = this._getXHRPromise(true);
|
@@ -1121,6 +1243,12 @@
|
|
1121
1243
|
this._initEventHandlers();
|
1122
1244
|
},
|
1123
1245
|
|
1246
|
+
// This method is exposed to the widget API and allows to query
|
1247
|
+
// the number of active uploads:
|
1248
|
+
active: function () {
|
1249
|
+
return this._active;
|
1250
|
+
},
|
1251
|
+
|
1124
1252
|
// This method is exposed to the widget API and allows to query
|
1125
1253
|
// the widget upload progress.
|
1126
1254
|
// It returns an object with loaded, total and bitrate properties
|