commit 1238d28db2efb64baf599bda579a73259b34f256
Author: Christos Stathis <chstath@ebs.gr>
Date:   Fri May 11 17:15:07 2012 +0300

    First version of drag 'n' drop upload (issue #2224)

diff --git a/src/gr/grnet/pithos/web/client/Pithos.java b/src/gr/grnet/pithos/web/client/Pithos.java
index 7ab8f91..bba7a5e 100644
--- a/src/gr/grnet/pithos/web/client/Pithos.java
+++ b/src/gr/grnet/pithos/web/client/Pithos.java
@@ -92,6 +92,7 @@ import com.google.gwt.user.client.Window;
 import com.google.gwt.user.client.ui.AbstractImagePrototype;
 import com.google.gwt.user.client.ui.Button;
 import com.google.gwt.user.client.ui.Composite;
+import com.google.gwt.user.client.ui.FlowPanel;
 import com.google.gwt.user.client.ui.HTML;
 import com.google.gwt.user.client.ui.HasHorizontalAlignment;
 import com.google.gwt.user.client.ui.HasVerticalAlignment;
@@ -249,7 +250,7 @@ public class Pithos implements EntryPoint, ResizeHandler {
 
     @SuppressWarnings("rawtypes") List<SingleSelectionModel> selectionModels = new ArrayList<SingleSelectionModel>();
     
-    Button upload;
+    public Button upload;
     
     private HTML numOfFiles;
     
@@ -359,6 +360,8 @@ public class Pithos implements EntryPoint, ResizeHandler {
         fileList = new FileList(this, images);
         inner.add(fileList);
 
+        inner.add(createUploadArea());
+        
         trees = new VerticalPanel();
         trees.setWidth("100%");
         
@@ -460,19 +463,26 @@ public class Pithos implements EntryPoint, ResizeHandler {
 
     public void applyPermissions(Folder f) {
     	if (f != null) {
-    		if (f.isInTrash())
+    		if (f.isInTrash()) {
     			upload.setEnabled(false);
+    			hideUploadArea();
+    		}
     		else {
 		    	Boolean[] perms = f.getPermissions().get(username);
 		    	if (f.getOwner().equals(username) || (perms != null && perms[1] != null && perms[1])) {
 		    		upload.setEnabled(true);
+		    		showUploadArea();
 		    	}
-		    	else
+		    	else {
 		    		upload.setEnabled(false);
+		    		hideUploadArea();
+		    	}
     		}
     	}
-    	else
+    	else {
     		upload.setEnabled(false);
+    		hideUploadArea();
+    	}
 	}
 
 	@SuppressWarnings({ "rawtypes", "unchecked" })
@@ -1087,6 +1097,7 @@ public class Pithos implements EntryPoint, ResizeHandler {
 		        if (mysharedTreeSelectionModel.getSelectedObject() != null) {
 		            deselectOthers(mysharedTreeView, mysharedTreeSelectionModel);
 		            upload.setEnabled(false);
+		            hideUploadArea();
 		            updateSharedFolder(mysharedTreeSelectionModel.getSelectedObject(), true);
 					showRelevantToolbarButtons();
 		        }
@@ -1276,4 +1287,132 @@ public class Pithos implements EntryPoint, ResizeHandler {
 	public boolean isMySharedSelected() {
 		return getSelectedTree().equals(getMySharedTreeView());
 	}
+	
+	private FlowPanel createUploadArea() {
+		FlowPanel area = new FlowPanel();
+		area.getElement().setId("container");
+		HTML list = new HTML();
+		list.getElement().setId("filelist");
+		area.add(list);
+		Scheduler.get().scheduleDeferred(new ScheduledCommand() {
+			
+			@Override
+			public void execute() {
+				setupUploadArea(Pithos.this, getToken());
+			}
+		});
+		
+		return area;
+	}
+	
+	native void setupUploadArea(Pithos app, String token) /*-{
+		$wnd.$("#container").pluploadQueue({
+			// General settings
+			runtimes : 'html5',
+			unique_names : true,
+			multiple_queues: true,
+			drop_element: 'filelist',
+			
+			preinit: {
+				Init: function(up, info) {
+					if ($wnd.console && $wnd.console.log)
+						$wnd.console.log("Init fired");
+					up.settings.file_data_name = "X-Object-Data";				
+				}
+			},
+			
+			init: {
+				FilesAdded: function(up, files) {
+					$wnd.$('#container').css('border', '');
+					var api = app.@gr.grnet.pithos.web.client.Pithos::getApiPath()();
+					var folder = app.@gr.grnet.pithos.web.client.Pithos::getUploadFolder()();
+					var owner = folder.@gr.grnet.pithos.web.client.foldertree.Folder::getOwner()();
+					var uri = folder.@gr.grnet.pithos.web.client.foldertree.Folder::getUri()();
+					var path = api + owner + uri;
+					for (var j=0; j<files.length; j++) {
+						files[j].folder = folder;
+						files[j].url = path + "/" + files[j].name + "?X-Auth-Token=" + encodeURIComponent(token);
+					}
+					up.start();
+				},
+				
+				BeforeUpload: function(up, file) {
+					if ($wnd.console && $wnd.console.log)
+						$wnd.console.log('About to upload ' + file.url);
+					up.settings.url = file.url;
+				},
+				
+				FileUploaded: function(up, file, response) {
+					if ($wnd.console && $wnd.console.log) {
+						$wnd.console.log('File ' + file.name + ' uploaded');
+						$wnd.console.log('Response: ' + response);
+					}
+					up.removeFile(file);
+					var folder = app.@gr.grnet.pithos.web.client.Pithos::getUploadFolder()();
+					if (folder == file.folder)
+						app.@gr.grnet.pithos.web.client.Pithos::updateUploadFolder()();
+				},
+				
+				UploadComplete: function(up, files) {
+					if ($wnd.console && $wnd.console.log)
+						$wnd.console.log('All files finished');
+				},
+				
+				Error: function(up, error) {
+					if ($wnd.console && $wnd.console.log)
+						$wnd.console.log("Error occured:" + error);
+				}
+			}
+		});
+		var uploader = $wnd.$("#container").pluploadQueue();
+		if (uploader.runtime != 'html5')
+			$wnd.$("#container").hide();
+		else {
+			if ($wnd.console && $wnd.console.log) {
+				$wnd.console.log(uploader);
+				$wnd.console.log($wnd.plupload);
+			}
+			$wnd.$('.plupload_header').hide();
+			$wnd.$('.plupload_filelist_header').hide();
+			$wnd.$('#container_filelist').css('overflow-y', 'auto');
+			$wnd.$('.plupload_filelist_footer').hide();
+			$wnd.document.getElementById('container').addEventListener('dragenter', function(event) {
+				$wnd.$('#container').css('border', '3px inset');
+			}, false);
+			$wnd.document.getElementById('container').addEventListener('dragleave', function(event) {
+				$wnd.$('#container').css('border', '');
+			}, false);
+		}
+	}-*/;
+	
+	private Folder getUploadFolder() {
+		if (folderTreeView.equals(getSelectedTree()) || otherSharedTreeView.equals(getSelectedTree())) {
+			return getSelection();
+		}
+		return null;
+	}
+	
+	private void updateUploadFolder() {
+		if (folderTreeView.equals(getSelectedTree()) || otherSharedTreeView.equals(getSelectedTree())) {
+			Folder f = getSelection();
+			if (getSelectedTree().equals(getFolderTreeView()))
+				updateFolder(f, true, new Command() {
+				
+					@Override
+					public void execute() {
+						updateStatistics();
+					}
+				}, false);
+			else
+				updateOtherSharedFolder(f, true);
+		}
+	}
+
+	public native void hideUploadArea() /*-{
+		$wnd.$("#container").hide();
+	}-*/;
+
+	public native void showUploadArea() /*-{
+		$wnd.$("#container").show();
+	}-*/;
 }
diff --git a/src/gr/grnet/pithos/web/client/grouptree/GroupTreeViewModel.java b/src/gr/grnet/pithos/web/client/grouptree/GroupTreeViewModel.java
index 3648646..f229aa2 100644
--- a/src/gr/grnet/pithos/web/client/grouptree/GroupTreeViewModel.java
+++ b/src/gr/grnet/pithos/web/client/grouptree/GroupTreeViewModel.java
@@ -122,6 +122,8 @@ public class GroupTreeViewModel implements TreeViewModel {
 				if (selected != null) {
 					app.deselectOthers(app.getGroupTreeView(), groupSelectionModel);
 					app.showFiles(new HashSet<File>());
+					app.hideUploadArea();
+					app.upload.setEnabled(false);
 					app.showRelevantToolbarButtons();
 					if (selected.equals(createGroup)) {
 						new CreateGroupCommand(app, null).execute();
