(function( ){ var ns = __namespace( "Astro.Blog.AstroEdit" ); /** @type {System.Cycle} */ var Cycle = __import( "System.Cycle" ); /** @type {System.Debug} */ var debug = __import( "System.Debug" ); /** @type {System.utils.EventKey} */ var EventKey = __import( "System.utils.EventKey" ); /** @type {Components.Mouse.ContextMenu} */ var ContextMenu = __import( "Components.Mouse.ContextMenu" ); /** @type {typeof Dandelion} */ var Dand = __import( "Dandelion" ); /** @type {Dandelion.IDOMObject} */ var IDOMObject = __import( "Dandelion.IDOMObject" ); /** @type {Astro.Blog.Config} */ var Conf = __import( "Astro.Blog.Config" ); /** @type {System.utils.Perf} */ var Perf = __import( "System.utils.Perf" ); var postFile = __import( "System.Net.postFile" ); var Uploader = function ( set_file_uri ) { /** @type {_AstConf_.SiteFile} */ var config = Conf.get( "SiteFile" ); // linkage var busy = false , placedFiles = [] , currentFile // Prepare structure for dockpanel , ptext = Dand.id( "asl_ptext" ) , pbar = Dand.id( "asl_pbar_fill" ) , ppreview = Dand.id( "asl_preview" ) , pfileName = Dand.id( "asl_fileName" ) , instruction = Dand.id( "asl_instruction" ) , p_status = Dand.id( "asl_u_head" ) , fileList = Dand.id( "asl_fileList" ) , stage = Dand.id( "asl_uploader" ) , uploadProgress = function(e) { var done = e.position || e.loaded , total = e.totalSize || e.total , percentage = String( Math.floor( done / total * 1000 )/10 ) + "%"; // Set progress ptext.innetText = ptext.textContent = pbar.style.width = percentage; } , uploadComplete = function ( response ) { try { var obj = JSON.parse( response ); if(obj.status) { currentFile.setStatus( "ok", config.f_host + obj.destination ); } else { currentFile.setStatus( "error", obj.message ); } new ContextMenu( currentFile.stage, currentFile.menuKeys, "LMB", stage ); } catch ( ex ) { currentFile.setStatus( "error", ex.message ); debug.Error( ex ); } beginUpload(); } , beginUpload = function() { busy = true; if( placedFiles.length ) { currentFile = placedFiles.pop(); if( currentFile ) { var file = currentFile.file; pfileName.textContent = pfileName.innetText = file.name; var fd = new FormData(); fd.append( "uploadFile", file ); postFile( set_file_uri, fd, { progress: uploadProgress, complete: uploadComplete } ); currentFile.setStatus("active"); instruction.style.marginTop = "-80px"; } else { // deleted file, skip it beginUpload(); } } else { busy = false; instruction.style.marginTop = ""; } } , clearFileList = function () { while( fileList.hasChildNodes() ) { fileList.removeChild( fileList.firstChild ); } } , retryUpload = function () { this.setStatus("pending"); placedFiles[placedFiles.length] = this; new ContextMenu( this.stage, this.menuKeys, "RMB", stage ); if( !busy ) beginUpload(); } , removeItem = function () { this.stage.style.marginTop = "-2em"; this.stage.style.opacity = "0"; if( placedFiles.indexOf(this) != -1 ) { delete placedFiles[placedFiles.indexOf(this)]; } Cycle.delay(function () { fileList.removeChild(this); }.bind(this.stage), 250); } ; fileList.style.paddingTop = String(p_status.clientHeight) + "px"; var docDom = IDOMObject( document ); // Drag/drop handlers docDom.addEventListener( "DragOver", function ( e ) { e.preventDefault(); this.className = "dragged_over"; } ); docDom.addEventListener( "DragEnd", function () { this.className = ""; } ); docDom.addEventListener( "Drop", function ( e ) { e.preventDefault(); this.className = ""; // Push files var list = e.dataTransfer.files; for(var i in list) { if(list[i].type != undefined) { var fileItem = new ASLFileItem(list[i], {clear: clearFileList, remove: removeItem, retry: retryUpload}); placedFiles[placedFiles.length] = fileItem; fileList.appendChild(fileItem.stage); new ContextMenu(fileItem.stage, fileItem.menuKeys, "LMB", stage); } } if(!busy) beginUpload(); return false; } ); }; var ASLFileItem = function (file, callbacks) { var statusblob = Dand.wrap("span", null, "asl_uItemStat", "\u25CF") , msg , _items = [ new EventKey("Remove this item", callbacks.remove.bind(this)) // Reserved for remove item , null // Reserved for retry/ Open link , null // Reserved for get Error message , new EventKey("Clear all", callbacks.clear) ] , popMessage = function () { new MessageBox("Upload error", msg).show(); } , getFileLink = function () { return msg; } ; this.stage = Dand.wrap( null, "asl_item" + Perf.uuid, "asl_uItem", [ statusblob, Dand.textNode(file.name) ] ); this.file = file; this.menuKeys = _items; this.setStatus = function (st, message) { msg = message; switch(st) { case "active": statusblob.style.color = "cornflowerblue"; break; case "error": statusblob.style.color = "red"; _items[1] = new EventKey( "Retry", callbacks.retry.bind(this) ); _items[2] = new EventKey( "Whats wrong ?", popMessage ); break; case "ok": statusblob.style.color = "greenyellow"; _items[1] = new EventKey( "Copy file link", getFileLink ); break; default:// pending delete _items[1]; delete _items[2]; statusblob.style.color = ""; } } }; ns[ NS_EXPORT ]( EX_CLASS, "Uploader", Uploader ); })();