import Sortable from 'sortablejs';
import anime from 'animejs/lib/anime.es.js';
import DataUtils from '../utils/DataUtils';
import Notfications from './Notifications.js';
import Maintenance from '../controllers/MaintenanceManager';
const notify = new Notfications();

export default class FileManager {
	//--------------------------
	// constructor
	//--------------------------
	constructor(upload, input, imageList, fileList) {
		this.mm = new Maintenance(null, null, document.getElementById('notify-progress'));
		this.upload = upload;
		this.input = input;
		this.imageList = imageList;
		this.fileList = fileList;
		this.accetableFiles = [
			'image/jpeg',
			'image/gif',
			'image/png',
			'image/svg',
			'audio/mpeg',
			'video/mp4',
			'application/pdf',
			'text/plain',
			'text/rtf'
		];
		this.files = [];
		this.sortedFiles = [];
		this.storage = [];
		this.mediaSort = Sortable.create(this.imageList, {
			animation: 150,
			onUpdate: () => {
				//notify.alert('REINDEXING MEDIA', null);
				//this.updateFiles();
			}
		});
		this.fileSort = Sortable.create(this.fileList, {
			animation: 150,
			onUpdate: () => {
				//notify.alert('REINDEXING FILES', null);
				//this.updateFiles();
			}
		});
		this.start();
	}
	//--------------------------
	// methods
	//--------------------------
	start() {
		this.upload.addEventListener('dragover', e => this.handleFileActions(e), false);
		this.upload.addEventListener('drop', e => this.handleFileActions(e), false);
		this.input.addEventListener('change', e => this.handleFileActions(e), false);
		var removeMedia = document.querySelectorAll('.media-remove');
		for (var i = 0, length = removeMedia.length; i < length; i++) {
			removeMedia[i].addEventListener(
				'click',
				e => this.removeFile(e, 'media'),
				false
			);
		}
	}
	getFileOrder() {
		let imgList = '';
		let fileList = '';
		for (var i = 0, length = this.imageList.childNodes.length; i < length; i++) {
			let div = this.imageList.childNodes[i];
			imgList = imgList + div.getAttribute('data-source') + ',';
		}
		for (var i = 0, length = this.fileList.childNodes.length; i < length; i++) {
			let div = this.fileList.childNodes[i];
			fileList = fileList + div.getAttribute('data-source') + ',';
		}
		let media = { images: imgList, files: fileList };
		return media;
	}

	sortFiles(files) {
		var self = this;
		for (var i = 0, file; (file = files[i]); i++) {
			var reader = new FileReader();
			// Closure to capture the file information
			reader.onload = (theFile => {
				return function (f) {
					//create remove button object
					var remove = document.createElement('button');
					var removeIcon = document.createElement('i');
					removeIcon.classList.add('ti', 'ti-x');
					remove.className = 'media-remove';
					remove.appendChild(removeIcon);
					//remove.setAttribute('id', mediaCount);
					remove.addEventListener(
						'click',
						e => self.removeFile(e, 'media'),
						false
					);

					//upload the file
					let upload = new FormData();
					upload.enctype = 'multipart/form-data';
					upload.append('upload_files[]', theFile, theFile.name);
					let item = null;
					let progress = null;

					// sort files
					switch (theFile.type) {
						case 'image/jpg':
						case 'image/jpeg':
						case 'image/gif':
						case 'image/svg':
						case 'image/png':
							item = self.itemFactory('img-item');
							progress = document.getElementById(
								'pgs' + item.getAttribute('id')
							);
							self.mm
								.filesUpload(theFile.type, upload, progress)
								.then(result => {
									item.setAttribute('data-source', result.filePath);
									item.style.background =
										'url(' +
										f.target.result +
										') no-repeat center center / cover';
									anime({
										targets: progress,
										width: 0,
										easing: 'easeInOutQuint',
										duration: 1000,
										complete: () => {
											item.removeChild(progress);
											item.appendChild(remove);
										}
									});
								});
							break;
						case 'video/mp4':
							item = self.itemFactory('video-item');
							progress = document.getElementById(
								'pgs' + item.getAttribute('id')
							);
							self.mm
								.filesUpload(theFile.type, upload, progress)
								.then(result => {
									item.setAttribute('data-source', result.filePath);
									let video = document.createElement('video');
									let source = document.createElement('source');
									source.src = f.target.result;
									video.appendChild(source);
									item.appendChild(video);
									anime({
										targets: progress,
										width: 0,
										easing: 'easeInOutQuint',
										duration: 1000,
										complete: () => {
											item.removeChild(progress);
											item.appendChild(remove);
										}
									});
								});
							break;
						case 'audio/mpeg':
							item = self.itemFactory('audio-item');
							progress = document.getElementById(
								'pgs' + item.getAttribute('id')
							);
							self.mm
								.filesUpload(theFile.type, upload, progress)
								.then(result => {
									item.setAttribute('data-source', result.filePath);
									let audio = document.createElement('audio');
									audio.setAttribute('controls', true);
									let source = document.createElement('source');
									source.src = f.target.result;
									audio.appendChild(source);
									item.appendChild(audio);
									anime({
										targets: progress,
										width: 0,
										easing: 'easeInOutQuint',
										duration: 1000,
										complete: () => {
											item.removeChild(progress);
											item.appendChild(remove);
										}
									});
								});
							break;
						case 'application/pdf':
						case 'text/plain':
						case 'text/rtf':
							item = self.itemFactory('file-item');
							progress = document.getElementById(
								'pgs' + item.getAttribute('id')
							);
							self.mm
								.filesUpload(theFile.type, upload, progress)
								.then(result => {
									item.setAttribute('data-source', result.filePath);
									let link = document.createElement('a');
									link.href = result.filePath;
									link.innerHTML = result.fileName;
									item.appendChild(link);
									anime({
										targets: progress,
										width: 0,
										easing: 'easeInOutQuint',
										duration: 1000,
										complete: () => {
											item.removeChild(progress);
											item.appendChild(remove);
										}
									});
								});
							break;
					}
				};
			})(file);
			// Read in the image file as a data URL.
			reader.readAsDataURL(file);
		}
	}
	itemFactory(type = null) {
		//get counts for lists
		var mediaCount = this.imageList.childNodes.length;
		var fileCount = this.fileList.childNodes.length;
		if (mediaCount < 0) mediaCount = 0;
		if (fileCount < 0) fileCount = 0;
		var item = document.createElement('div');
		item.className = type;
		var progress = document.createElement('div');
		progress.className = 'item-progress';
		item.appendChild(progress);

		if (type == 'img-item' || type == 'video-item') {
			this.imageList.appendChild(item);
			progress.setAttribute('id', 'pgs' + mediaCount);
			item.setAttribute('id', mediaCount);
		} else {
			this.fileList.appendChild(item);
			progress.setAttribute('id', 'pgs' + fileCount);
			item.setAttribute('id', fileCount);
		}
		return item;
	}

	//--------------------------
	// event handlers
	//--------------------------
	removeFile(e) {
		var item = e.target.parentNode.parentNode;
		switch (item.className) {
			case 'img-item':
			case 'video-item':
				this.imageList.removeChild(item);
				break;
			case 'audio-item':
			case 'file-item':
				this.fileList.removeChild(item);
				break;
		}
		notify.alert('File Removed!', true);
	}

	handleFileActions(e) {
		e.stopPropagation();
		e.preventDefault();
		let self = this;
		let rawList = [];
		let sortedList = [];
		let notOnTheList = [];

		switch (e.type) {
			case 'dragover':
				e.dataTransfer.dropEffect = 'copy'; // Explicitly show this is a copy.
				break;
			case 'change':
			case 'drop':
				e.type == 'drop'
					? (rawList = e.dataTransfer.files)
					: (rawList = e.target.files);
				for (var i = 0, f; (f = rawList[i]); i++) {
					// check witch files are cool to upload
					if (this.accetableFiles.includes(f.type)) {
						sortedList.push(f);
					} else {
						notOnTheList.push(f);
					}
				}
				//send for sorting
				self.sortFiles(sortedList);
				break;
		}
	}
}
