Skip to content

Instantly share code, notes, and snippets.

@alexlcdee
Created August 21, 2017 10:20
Show Gist options
  • Save alexlcdee/e64f8becedb70d87103bf63736df0428 to your computer and use it in GitHub Desktop.
Save alexlcdee/e64f8becedb70d87103bf63736df0428 to your computer and use it in GitHub Desktop.
var __extends = (this && this.__extends) || (function () {
var extendStatics = Object.setPrototypeOf ||
({__proto__: []} instanceof Array && function (d, b) {
d.__proto__ = b;
}) ||
function (d, b) {
for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
};
return function (d, b) {
extendStatics(d, b);
function __() {
this.constructor = d;
}
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
})();
var DropZoneModule;
(function (DropZoneModule) {
var DropUpload = (function () {
function DropUpload($container) {
this.files = {};
this.errors = {};
this.succeed = {};
this.fileFieldName = '';
this.events = {
'error': [function (responseText) {
}],
'success': [function (responseText) {
}]
};
this.$container = $container;
this.endpoint = this.$container.data('endpoint-url') || '';
this.events['success'].push(this.$container.data('on-success') || function () {
});
this.events['error'].push(this.$container.data('on-error') || function () {
});
this.fileFieldName = this.$container.data('file-field');
this.init();
}
DropUpload.prototype.uploadFiles = function (files, endpoint) {
if (endpoint === void 0) { endpoint = ''; }
this.clearErrors();
for (var i = 0; i < files.length; i++) {
var file = new DropZoneFile(files[i], i, this);
file.upload(endpoint || this.endpoint);
this.files[i] = file;
this.addProgressRow(i);
}
};
DropUpload.prototype.clearErrors = function () {
var bars = this.$container.find('.progress-bar-danger');
bars.each(function () {
$(this).parent().remove();
});
};
DropUpload.prototype.finish = function (idx) {
delete this.files[idx];
if (!Object.keys(this.files).length) {
if (Object.keys(this.succeed).length) {
setTimeout(this.trigger.apply(this, ['success', this.succeed]), 1);
this.succeed = {};
}
if (Object.keys(this.errors).length) {
setTimeout(this.trigger.apply(this, ['error', this.errors]), 1);
this.errors = {};
}
}
};
DropUpload.prototype.success = function (idx, responseText) {
this.succeed[idx] = responseText;
var $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.parent().removeClass('active').removeClass('progress-striped');
$progressBar.addClass('progress-bar-success');
$progressBar.html('Файл успешно загружен');
setTimeout(function () {
$progressBar.parent().fadeOut(300, function () {
$(this).remove();
});
}, 3000);
}
//setTimeout(this.trigger.apply(this, ['success', responseText]), 1);
};
DropUpload.prototype.progress = function (idx) {
var $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.width(this.files[idx].progress + '%');
$progressBar.html('Загрузка: ' + parseInt(this.files[idx].progress.toString()) + '%');
}
};
DropUpload.prototype.error = function (idx, responseText) {
this.errors[idx] = responseText;
var $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.parent().removeClass('active').removeClass('progress-striped');
$progressBar.html('При загрузке произошла ошибка');
$progressBar.addClass('progress-bar-danger');
}
//setTimeout(this.trigger.apply(this, ['error', responseText]), 1);
};
DropUpload.prototype.on = function (eventName, callback) {
this.events[eventName].push(callback);
return this;
};
DropUpload.prototype.trigger = function (eventName) {
var args = [];
for (var _i = 1; _i < arguments.length; _i++) {
args[_i - 1] = arguments[_i];
}
var context = this;
for (var i in this.events[eventName]) {
if (this.events[eventName].hasOwnProperty(i)) {
setTimeout(this.events[eventName][i].apply(context, args), 1);
}
}
};
DropUpload.prototype.addProgressRow = function (idx) {
var $progressContainer = this.$container.find('.progress-container');
if ($progressContainer.length === 0) {
$progressContainer = $('<div class="progress-container"></div>');
this.$container.append('<div class="clearfix"></div>');
this.$container.append($progressContainer);
}
$progressContainer.append('<div class="progress progress-striped active"><div class="progress-bar" id="DropZone_progress_' + idx + '"></div></div>');
};
return DropUpload;
}());
var DropZone = (function (_super) {
__extends(DropZone, _super);
function DropZone() {
return _super !== null && _super.apply(this, arguments) || this;
}
DropZone.prototype.init = function () {
this.$dropZone = $('<div class="col-md-10 drop-zone">Перетащите файлы с диска сюда</div>');
this.$container.append(this.$dropZone);
this.$dropZone[0].ondragover = this.onDragOver.bind(this);
this.$dropZone[0].ondragleave = this.onDragLeave.bind(this);
this.$dropZone[0].ondrop = this.onDrop.bind(this);
};
DropZone.prototype.onDragOver = function (event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.addClass("active");
};
DropZone.prototype.onDragLeave = function (event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.removeClass("active");
};
DropZone.prototype.onDrop = function (event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.removeClass("active");
var files = event.dataTransfer.files;
this.uploadFiles(files);
};
return DropZone;
}(DropUpload));
DropZoneModule.DropZone = DropZone;
var DropClick = (function (_super) {
__extends(DropClick, _super);
function DropClick() {
return _super !== null && _super.apply(this, arguments) || this;
}
DropClick.prototype.init = function () {
var btnClasses = 'col-md-2 btn btn-success btn-lg';
if (this.$container.data('btn-class')) {
btnClasses = this.$container.data('btn-class');
}
var $button = $('<button class="' + btnClasses + '" id="yw2" name="yt3" type="button">Выбрать</button>');
this.$container.append($button);
this.$inputField = $('<input type="file" style="display:none" multiple="multiple" />');
this.$container.append(this.$inputField);
this.$inputField.on('change', this.onFieldChange.bind(this));
$button.on('click', this.onButtonClick.bind(this));
var cleanInput = function () {
this.$inputField.val("");
};
this.on('success', cleanInput.bind(this)).on('error', cleanInput.bind(this));
};
DropClick.prototype.onButtonClick = function (event) {
this.$inputField.click();
};
DropClick.prototype.onFieldChange = function (event) {
var field = this.$inputField[0];
this.uploadFiles(field.files);
};
return DropClick;
}(DropUpload));
DropZoneModule.DropClick = DropClick;
var DropCustom = (function (_super) {
__extends(DropCustom, _super);
function DropCustom() {
return _super !== null && _super.apply(this, arguments) || this;
}
DropCustom.prototype.init = function () {
this.$inputField = $('<input type="file" style="display:none" multiple="multiple" />');
this.$container.parent().append(this.$inputField);
this.$inputField.on('change', this.onFieldChange.bind(this));
this.$container.on('click', this.onButtonClick.bind(this));
var cleanInput = function () {
this.$inputField.val("");
};
this.on('success', cleanInput.bind(this)).on('error', cleanInput.bind(this));
};
DropCustom.prototype.onButtonClick = function (event) {
event.preventDefault();
this.$inputField.click();
};
DropCustom.prototype.onFieldChange = function (event) {
event.preventDefault();
var field = this.$inputField[0];
this.uploadFiles(field.files);
};
return DropCustom;
}(DropUpload));
DropZoneModule.DropCustom = DropCustom;
var DropZoneFile = (function () {
function DropZoneFile(file, idx, zone) {
this.progress = 0;
this.file = file;
this.zone = zone;
this.idx = idx;
}
DropZoneFile.prototype.upload = function (endpoint) {
var formData = new FormData();
formData.append(this.zone.fileFieldName, this.file);
this.xhr = new XMLHttpRequest();
this.xhr.upload.addEventListener("progress", this.onProgress.bind(this), false);
this.xhr.onreadystatechange = this.onReadyStateChange.bind(this);
this.xhr.onerror = this.onError.bind(this);
this.xhr.open("POST", endpoint);
this.xhr.send(formData);
};
DropZoneFile.prototype.onProgress = function (event) {
this.progress = event.loaded / event.total * 100;
this.zone.progress(this.idx);
};
DropZoneFile.prototype.onReadyStateChange = function (event) {
if (this.xhr.readyState === 4) {
if (this.xhr.status === 200) {
this.zone.success(this.idx, this.xhr.responseText);
}
else {
this.zone.error(this.idx, this.xhr.responseText);
}
this.zone.finish(this.idx);
}
};
DropZoneFile.prototype.onError = function (event) {
this.zone.error(this.idx, this.xhr.responseText);
};
return DropZoneFile;
}());
})(DropZoneModule || (DropZoneModule = {}));
//# sourceMappingURL=dropupload.js.map
module DropZoneModule {
abstract class DropUpload {
protected $container;
protected files: { [id: number]: DropZoneFile } = {};
protected errors: { [idx: number]: string } = {};
protected succeed: { [idx: number]: string } = {};
public fileFieldName: string = '';
public endpoint: string;
public events: { [name: string]: [(responseText: string) => void] } = {
'error': [function (responseText: string) {
}],
'success': [function (responseText: string) {
}]
};
public constructor($container: JQuery) {
this.$container = $container;
this.endpoint = this.$container.data('endpoint-url') || '';
this.events['success'].push(this.$container.data('on-success') || function () {
});
this.events['error'].push(this.$container.data('on-error') || function () {
});
this.fileFieldName = this.$container.data('file-field');
this.init();
}
public abstract init();
public uploadFiles(files: FileList, endpoint: string = '') {
this.clearErrors();
for (let i = 0; i < files.length; i++) {
let file = new DropZoneFile(files[i], i, this);
file.upload(endpoint || this.endpoint);
this.files[i] = file;
this.addProgressRow(i);
}
}
public clearErrors() {
let bars = this.$container.find('.progress-bar-danger');
bars.each(function () {
$(this).parent().remove();
});
}
public finish(idx) {
delete this.files[idx];
if (!Object.keys(this.files).length) {
if (Object.keys(this.succeed).length) {
setTimeout(this.trigger.apply(this, ['success', this.succeed]), 1);
this.succeed = {};
}
if (Object.keys(this.errors).length) {
setTimeout(this.trigger.apply(this, ['error', this.errors]), 1);
this.errors = {};
}
}
}
public success(idx, responseText) {
this.succeed[idx] = responseText;
let $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.parent().removeClass('active').removeClass('progress-striped');
$progressBar.addClass('progress-bar-success');
$progressBar.html('Файл успешно загружен');
setTimeout(function () {
$progressBar.parent().fadeOut(300, function () {
$(this).remove();
});
}, 3000);
}
//setTimeout(this.trigger.apply(this, ['success', responseText]), 1);
}
public progress(idx) {
let $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.width(this.files[idx].progress + '%');
$progressBar.html('Загрузка: ' + parseInt(this.files[idx].progress.toString()) + '%');
}
}
public error(idx, responseText) {
this.errors[idx] = responseText;
let $progressBar = this.$container.find('#DropZone_progress_' + idx);
if ($progressBar.length) {
$progressBar.parent().removeClass('active').removeClass('progress-striped');
$progressBar.html('При загрузке произошла ошибка');
$progressBar.addClass('progress-bar-danger');
}
//setTimeout(this.trigger.apply(this, ['error', responseText]), 1);
}
public on(eventName: string, callback: (responseText: string) => void) {
this.events[eventName].push(callback);
return this;
}
public trigger(eventName: string, ...args: any[]) {
let context = this;
for (let i in this.events[eventName]) {
if (this.events[eventName].hasOwnProperty(i)) {
setTimeout(this.events[eventName][i].apply(context, args), 1);
}
}
}
public addProgressRow(idx) {
let $progressContainer = this.$container.find('.progress-container');
if ($progressContainer.length === 0) {
$progressContainer = $('<div class="progress-container"></div>');
this.$container.append('<div class="clearfix"></div>');
this.$container.append($progressContainer);
}
$progressContainer.append('<div class="progress progress-striped active"><div class="progress-bar" id="DropZone_progress_' + idx + '"></div></div>');
}
}
export class DropZone extends DropUpload {
private $dropZone;
public init() {
this.$dropZone = $('<div class="col-md-10 drop-zone">Перетащите файлы с диска сюда</div>');
this.$container.append(this.$dropZone);
this.$dropZone[0].ondragover = this.onDragOver.bind(this);
this.$dropZone[0].ondragleave = this.onDragLeave.bind(this);
this.$dropZone[0].ondrop = this.onDrop.bind(this);
}
private onDragOver(event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.addClass("active");
}
private onDragLeave(event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.removeClass("active");
}
private onDrop(event) {
event.preventDefault();
event.stopPropagation();
this.$dropZone.removeClass("active");
let files = event.dataTransfer.files;
this.uploadFiles(files);
}
}
export class DropClick extends DropUpload {
private $inputField: JQuery;
public init() {
let btnClasses = 'col-md-2 btn btn-success btn-lg';
if (this.$container.data('btn-class')) {
btnClasses = this.$container.data('btn-class');
}
let $button = $('<button class="' + btnClasses + '" id="yw2" name="yt3" type="button">Выбрать</button>');
this.$container.append($button);
this.$inputField = $('<input type="file" style="display:none" multiple="multiple" />');
this.$container.append(this.$inputField);
this.$inputField.on('change', this.onFieldChange.bind(this));
$button.on('click', this.onButtonClick.bind(this));
let cleanInput = function () {
this.$inputField.val("");
};
this.on('success', cleanInput.bind(this)).on('error', cleanInput.bind(this));
}
public onButtonClick(event) {
this.$inputField.click();
}
public onFieldChange(event) {
let field = <HTMLInputElement>this.$inputField[0];
this.uploadFiles(field.files);
}
}
export class DropCustom extends DropUpload {
private $inputField: JQuery;
public init() {
this.$inputField = $('<input type="file" style="display:none" multiple="multiple" />');
this.$container.parent().append(this.$inputField);
this.$inputField.on('change', this.onFieldChange.bind(this));
this.$container.on('click', this.onButtonClick.bind(this));
let cleanInput = function () {
this.$inputField.val("");
};
this.on('success', cleanInput.bind(this)).on('error', cleanInput.bind(this));
}
public onButtonClick(event) {
event.preventDefault();
this.$inputField.click();
}
public onFieldChange(event) {
event.preventDefault();
let field = <HTMLInputElement>this.$inputField[0];
this.uploadFiles(field.files);
}
}
class DropZoneFile {
private file: File;
private zone: DropUpload;
private idx: number;
private xhr: XMLHttpRequest;
public progress: number = 0;
public constructor(file: File, idx: number, zone: DropUpload) {
this.file = file;
this.zone = zone;
this.idx = idx;
}
public upload(endpoint: string) {
let formData = new FormData();
formData.append(this.zone.fileFieldName, this.file);
this.xhr = new XMLHttpRequest();
this.xhr.upload.addEventListener("progress", this.onProgress.bind(this), false);
this.xhr.onreadystatechange = this.onReadyStateChange.bind(this);
this.xhr.onerror = this.onError.bind(this);
this.xhr.open("POST", endpoint);
this.xhr.send(formData);
}
private onProgress(event) {
this.progress = event.loaded / event.total * 100;
this.zone.progress(this.idx);
}
private onReadyStateChange(event) {
if (this.xhr.readyState === 4) {
if (this.xhr.status === 200) {
this.zone.success(this.idx, this.xhr.responseText);
} else {
this.zone.error(this.idx, this.xhr.responseText);
}
this.zone.finish(this.idx);
}
}
private onError(event) {
this.zone.error(this.idx, this.xhr.responseText);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment