I am new to java programing.
I am trying to write a java application using netbeans that uses imagej jar to open a dicom image & process it. I was able to do that using the following java code:
public class user_interface extends java.awt.Frame {
/** Creates new form user_interface */
public user_interface() {
initComponents();
}
private void initComponents() {
btn_open_image = new java.awt.Button();
btn_invert_image = new java.awt.Button();
slbl_display = new javax.swing.JLabel();
setBackground(java.awt.Color.orange);
addWindowListener(new java.awt.event.WindowAdapter() {
public void windowClosing(java.awt.event.WindowEvent evt) {
exitForm(evt);
}
});
setLayout(new org.netbeans.lib.awtextra.AbsoluteLayout());
btn_open_image.setLabel("Open Image");
btn_open_image.addMouseListener(new java.awt.event.MouseAdapter() {
public void mouseClicked(java.awt.event.MouseEvent evt) {
btn_open_imageMouseClicked(evt);
}
});
btn_open_image.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
btn_open_imageActionPerformed(evt);
}
});
add(btn_open_image, new org.netbeans.lib.awtextra.AbsoluteConstraints(10, 40, 80, -1));
btn_invert_image.setLabel("Invert Image");
btn_invert_image.addMouseListener(new java.awt.event.MouseAdapter() {
public void mouseClicked(java.awt.event.MouseEvent evt) {
btn_invert_imageMouseClicked(evt);
}
});
add(btn_invert_image, new org.netbeans.lib.awtextra.AbsoluteConstraints(10, 150, 80, -1));
slbl_display.setBackground(new java.awt.Color(51, 51, 51));
add(slbl_display, new org.netbeans.lib.awtextra.AbsoluteConstraints(120, 60, -1, -1));
pack();
}// </editor-fold>
/**
* Exit the Application
*/
private void exitForm(java.awt.event.WindowEvent evt) {
System.exit(0);
}
private ImagePlus IPL_image;
private ImageJ ImageJ_image;
private ImageJ CovImageJ_image;
private ImageProcessor ip;
private Image AWT_image;
private ImageIcon AWT_icon;
private void btn_open_imageMouseClicked(java.awt.event.MouseEvent evt) {
// TODO add your handling code here:
String MacroName ="C:\\Program Files\\ImageJ\\macros\\RadFz\\DrawGraticule(Worksfine).txt";
String ImgName = "G:\\PV-QA Images\\01-31-2016\\6MV-FS-OF\\RI\\5x5-6MV-MLC.dcm";
//(01) open image
IPL_image = IJ.openImage(ImgName);
int ImgType = IPL_image.getType();
System.out.println("Image Type = " + ImgType);
//IJ.runMacroFile(MacroName);
//(02) pass it to processor to acess each pixel
// ip.convertToColorProcessor();
ip = IPL_image.getProcessor();
//(03) reset the image window & level
ip.resetMinAndMax();
//get width & height
int imgWdth = ip.getWidth();
int imgHgth = ip.getHeight();
// set line color and width
ip.setColor(Color.red);
ip.setLineWidth(3);
ip.drawLine(0, imgHgth/2, imgWdth, imgHgth/2);
ip.drawLine(imgWdth/2, 0, imgWdth/2, imgHgth);
//IPL_image.show(); // Display image in imagej window
//String IIP = IJ.runMacroFile(MacroName);
//convert image from imagej format to one that you can
//display in image container
AWT_image = ip.createImage();
AWT_icon = new ImageIcon(AWT_image);
slbl_display.setIcon(AWT_icon);
System.out.println("Width = " + imgWdth + " pixels");
System.out.println("Height = " + imgHgth + " pixels");
GetDICOMTagVal("300A,012C");
}
private void btn_invert_imageMouseClicked(java.awt.event.MouseEvent evt) {
// TODO add your handling code here:
ip.invert();
AWT_image = ip.createImage();
AWT_icon = new ImageIcon(AWT_image);
slbl_display.setIcon(AWT_icon);
}
private void btn_open_imageActionPerformed(java.awt.event.ActionEvent evt) {
// TODO add your handling code here:
}
private void GetDICOMTagVal(String DICOMTag) {
String imgInfoStr = IPL_image.getInfoProperty();
//"0002,0003" "300A,012C"
System.out.println("imgInfoStr = \n"+ imgInfoStr );
String InfoLines[];
InfoLines = split(imgInfoStr, "\n");
//System.out.println(" Number of lines = " + InfoLines.length);
int i;
for (i =0; i<InfoLines.length; i++){
//System.out.println(i+" -->" + InfoLines[i].startsWith(DICOMTag));
if(InfoLines[i].startsWith(DICOMTag)) {
String Tag;
Tag = InfoLines[i].substring(DICOMTag.length());
System.out.println(DICOMTag + " = " + Tag);
} else {
}
}
}
/**
* #param args the command line arguments
*/
public static void main(String args[]) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
new user_interface().setVisible(true);
}
});
}
// Variables declaration - do not modify
private java.awt.Button btn_invert_image;
private java.awt.Button btn_open_image;
private javax.swing.JLabel slbl_display;
// End of variables declaration
}
I am able to open the image and process it (draw on it) using black lines only. That is because the image is opened as an 8 bit gray image. I am not sure how to convert image to RGB. The convertToRGB() is available in the ij package in the processing folder in the image converter class.
How can I do that?
Indeed as you said, the abstract class ImageProcessor has a method convertToRGB():
public ImageProcessor convertToRGB()
{
if ( type == RGB ) return ip ;
ImageProcessor ip2 = ip.convertToByte(doScaling) ;
return new ColorProcessor(ip2.createImage()) ;
}
It does exactly what you need: convert a ByteProcessor (8 bits) into a ColorProcessor (24 bits).
I have followed this tutorial and the testbed launches, but nothing ever happens. The GUI appears but the tests never run, it just sits there. The testbed is launched from the driver class and you add the testbed test. Anyone else have this problem?
Driver Class
public class Driver {
public static final String GRAVITY_SETTING = "Gravity";
/**
* #param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
TestbedModel model = new TestbedModel(); // create our model
// add tests
model.addCategory("My Tests");
model.addTest(new MJWTest2());
model.addTest(new VerticalStack());
// add our custom setting "My Range Setting", with a default value of 10, between 0 and 20
model.getSettings().addSetting(new TestbedSetting(GRAVITY_SETTING, SettingType.ENGINE, false));
TestbedPanel panel = new TestPanelJ2D(model); // create our testbed panel
JFrame testbed = new TestbedFrame(model, panel, null); // put both into our testbed frame
// etc
testbed.setVisible(true);
testbed.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
Testbed Test class
public class MJWTest2 extends TestbedTest {
public static final String GRAVITY_SETTING = "Gravity";
#Override
public void initTest(boolean argDeserialized) {
setTitle("Couple of Things Test");
getWorld().setGravity(new Vec2());
for (int i = 0; i < 2; i++) {
PolygonShape polygonShape = new PolygonShape();
polygonShape.setAsBox(1, 1);
FixtureDef fix = new FixtureDef();
fix.shape = polygonShape;
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyType.DYNAMIC;
bodyDef.position.set(5 * i, 0);
bodyDef.angle = (float) (Math.PI / 4 * i);
bodyDef.allowSleep = false;
Body body = getWorld().createBody(bodyDef);
body.createFixture(fix);
body.applyForce(new Vec2(-10000 * (i - 1), 0), new Vec2());
}
}
#Override
public void step(TestbedSettings settings) {
super.step(settings); // make sure we update the engine!
TestbedSetting gravity = settings.getSetting(GRAVITY_SETTING); // grab our setting
if (gravity.enabled) {
getWorld().setGravity(new Vec2(0, -9));
}
else {
getWorld().setGravity(new Vec2());
}
}
#Override
public String getTestName() {
return "Couple of Things";
}
}
There was an updated to the engine w/o an update to the wiki. Whoops! sorry. You need to create a controller and start is, as shown here:
https://github.com/dmurph/jbox2d/blob/master/jbox2d-testbed/src/main/java/org/jbox2d/testbed/framework/j2d/TestbedMain.java
Try this
public class MJWTest2 extends TestbedTest {
#Override
public void initTest(boolean argDeserialized) {
setTitle("Couple of Things Test");
getWorld().setGravity(new Vec2());
for (int i = 0; i < 2; i++)
{
// CircleShape circleShape = new CircleShape();
// circleShape.m_radius = 1;
// Shape shape = circleShape;
PolygonShape polygonShape = new PolygonShape();
polygonShape.setAsBox(1, 1);
Shape shape = polygonShape;
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyType.DYNAMIC;
bodyDef.position.set(5 * i, 0);
bodyDef.angle = (float) (Math.PI / 4 * i);
bodyDef.allowSleep = false;
Body body = getWorld().createBody(bodyDef);
body.createFixture(shape, 5.0f);
body.applyForce(new Vec2(-10000 * (i - 1), 0), new Vec2());
}
}
/**
* #see org.jbox2d.testbed.framework.TestbedTest#getTestName()
*/
#Override
public String getTestName() {
return "Couple of Things";
}
}
And so called 'driver class'
public class App2 {
public static final String GRAVITY_SETTING = "Gravity";
public static void main(String[] args) {
// TODO Auto-generated method stub
TestbedModel model = new TestbedModel(); // create our model
// add tests
model.addCategory("My Tests");
model.addTest(new MJWTest2());
model.addTest(new VerticalStack());
// add our custom setting "My Range Setting", with a default value of 10, between 0 and 20
model.getSettings().addSetting(new TestbedSetting(GRAVITY_SETTING, SettingType.ENGINE, false));
TestbedPanel panel = new TestPanelJ2D(model); // create our testbed panel
JFrame testbed = new TestbedFrame(model, panel); // put both into our testbed frame
// etc
testbed.setVisible(true);
testbed.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
worked fine for me.. hope that it works for you as well..
I am working with drag and drop on JavaFX2. It's possible that the dragged-Object (maybe clone of the dragged object) following the mousecursor like on the JavaFX Scene Builder.
This is my sample sourcecode:
Pane pane;
private void dragAndDropExample() {
pane = new Pane();
pane.setPrefSize(800, 600);
TitledPane titlePane = new TitledPane("Partial Order", pane);
add(titlePane, 0, 2);
pane.getChildren().add(createCircle(350, 300, Color.RED));
pane.getChildren().add(createCircle(250, 300, Color.BROWN));
pane.setOnMouseMoved(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
if (circleToMove != null) {
circleToMove.setCenterX(event.getX());
circleToMove.setCenterY(event.getY());
}
}
});
}
Circle circleToMove;
private Circle createCircle(double x, double y, Color color) {
final Circle c = new Circle(x, y, 25);
c.setFill(color);
c.setOnDragDetected(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent arg0) {
System.out.println("SetOnDragDetected");
c.setFill(Paint.valueOf("blue"));
Dragboard db = c.startDragAndDrop(TransferMode.COPY_OR_MOVE);
ClipboardContent content = new ClipboardContent();
content.putString("foo " + c.hashCode());
db.setContent(content);
arg0.consume();
circleToMove = c;
}
});
c.setOnMouseClicked(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
System.out.println("Mouse clicked");
}
});
c.setOnMouseReleased(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
System.out.println("Mouse Released");
circleToMove = null;
}
});
c.setOnDragExited(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent event) {
System.out.println("SetOnDragExited");
System.out.println(event.getGestureSource());
}
});
c.setOnDragOver(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent event) {
System.out.println("setOnDragOver " + c.hashCode());
c.setFill(Paint.valueOf("white"));
event.acceptTransferModes(TransferMode.COPY_OR_MOVE);
event.consume();
}
});
c.setOnDragDropped(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent arg0) {
System.out.println("setOnDragDropped");
c.setFill(Paint.valueOf("black"));
if (arg0.getGestureSource() instanceof Circle) {
if (arg0.getDragboard().hasString()) {
System.out.println(c.hashCode() + " hat jetzt " + arg0.getDragboard().getString());
}
}
}
});
c.setOnDragEntered(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent arg0) {
System.out.println("setOnDragEntered");
}
});
return c;
}
I tried with the mouseEvent on the pane, but this event does not get fired during drag and drop.
You are using wrong handlers. There drag events are used to drag items between panes. If you want to just move handled object use next code:
private Circle createCircle(double x, double y, Color color) {
final Circle c = new Circle(x, y, 25);
c.setFill(color);
c.setOnMouseDragged(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
c.relocate(event.getSceneX() - c.getRadius(), event.getSceneY() - c.getRadius());
}
});
return c;
}
Also you can try to look at next subsample in the Ensemble demo:
I am trying to make a straight ended connection between widgets.But when I am doing so, the orientation of my connector is coming wrong.Its always coming parallel to the required one.Also , it is independent of the connecting widgets i.e when I move my widget, my connector does not move.Snippet of my code is given as :
Link to snapshot of the problem: http://goo.gl/JUEmJ
public class DragNDropPage {
SyncCurrentUser cu = SyncCurrentUser.getUser();
private AbsolutePanel area = new AbsolutePanel();
HorizontalPanel toolsPanel = new HorizontalPanel();
AbsolutePanel canvas = new AbsolutePanel();
DragController toolboxDragController;
Label startLabel = new Label("START");
Label stopLabel = new Label("STOP");
Label activityLabel = new Label("ACTIVITY");
Label processLabel = new Label("PROCESS");
Button stopDrag = new Button("Done Dragging");
Button saveButton = new Button("Save");
PickupDragController dragController = new PickupDragController(area, true);
AbsolutePositionDropController dropController = new AbsolutePositionDropController(area);
private List<Widget> selected = new ArrayList<Widget>();
private List<Widget> onCanvas = new ArrayList<Widget>();
private List<Connection> connections = new ArrayList<Connection>();
private CActivity[] aItems;
private CProcess[] pItems;
MyHandler handler = new MyHandler();
int mouseX,mouseY;
String style;
public DragNDropPage() {
toolboxDragController = new ToolboxDragController(dropController, dragController);
RootPanel.get("rightbar").add(area);
area.setSize("575px", "461px");
area.add(toolsPanel);
toolsPanel.setSize("575px", "37px");
toolsPanel.add(startLabel);
startLabel.setSize("76px", "37px");
toolboxDragController.makeDraggable(startLabel);
toolsPanel.add(stopLabel);
stopLabel.setSize("66px", "37px");
toolboxDragController.makeDraggable(stopLabel);
toolsPanel.add(activityLabel);
activityLabel.setSize("82px", "36px");
toolboxDragController.makeDraggable(activityLabel);
toolsPanel.add(processLabel);
processLabel.setSize("85px", "36px");
toolboxDragController.makeDraggable(processLabel);
stopDrag.addClickHandler(handler);
toolsPanel.add(stopDrag);
stopDrag.setWidth("114px");
saveButton.addClickHandler(handler);
toolsPanel.add(saveButton);
area.add(canvas, 0, 36);
canvas.setSize("575px", "425px");
Event.addNativePreviewHandler(new Event.NativePreviewHandler() {
#Override
public void onPreviewNativeEvent(NativePreviewEvent event) {
//46 is the key code for Delete Button
if(event.getNativeEvent().getKeyCode() == 46 && !selected.isEmpty()) {
for (Iterator<Widget> i = selected.listIterator(); i.hasNext();) {
Widget w = (Widget) i.next();
UIObjectConnector.unwrap(w);
i.remove();
w.removeFromParent();
onCanvas.remove(i);
}
}
}
});
aItems = cu.currentUser.getcActivity();
pItems = cu.currentUser.getcProcess();
}
private class ToolboxDragController extends PickupDragController {
public ToolboxDragController(final DropController dropController, final DragController nodesDragController) {
super(area ,false);
setBehaviorDragProxy(true);
registerDropController(dropController);
addDragHandler(new DragHandlerAdapter(){
public void onPreviewDragEnd(DragEndEvent event) throws VetoDragException {
Widget node = (Widget) event.getSource();
int left = event.getContext().desiredDraggableX;
int top = event.getContext().desiredDraggableY;
AbsolutePanel panel = (AbsolutePanel) dropController.getDropTarget();
createConnector((Label) node, panel, left, top);
throw new VetoDragException();
}
});
}
}
protected UIObjectConnector createConnector(Label proxy, AbsolutePanel panel, int left, int top) {
Widget w;
String str = proxy.getText();
if(str.equals("START") || str.equals("STOP")){
w = new Label(proxy.getText()){
public void onBrowserEvent(Event event) {
if( DOM.eventGetType(event) == 4
&& DOM.eventGetCtrlKey(event)){
select(this);
}
super.onBrowserEvent(event);
}
};
w.getElement().setClassName("dnd-start-stop");
}
else{
w = new ListBox(){
public void onBrowserEvent(Event event) {
if( DOM.eventGetType(event) == 4
&& DOM.eventGetCtrlKey(event)){
select(this);
}
super.onBrowserEvent(event);
}
};
if(str.equals("ACTIVITY")){
getAItems((ListBox)w);
//w.getElement().addClassName("dnd-activity");
}
else if(str.equals("PROCESS")){
getPItems((ListBox)w);
//w.getElement().addClassName("dnd-process");
}
}
onCanvas.add(w);
left -= panel.getAbsoluteLeft();
top -= panel.getAbsoluteTop();
//panel.add(w,10,10);
panel.add(w, left, top);
dragController.makeDraggable(w);
return UIObjectConnector.wrap(w);
}
private void getAItems(ListBox w) {
for(int i=0;i<aItems.length;i++)
w.addItem(aItems[i].getActivityName());
}
private void getPItems(ListBox w) {
/*for(int i=0;i<pItems.length;i++)
w.addItem(pItems[i].getProcessName());*/
w.addItem("Process1");
}
protected void select(Widget w){
if(selected.isEmpty()) {
selected.add(w);
w.getElement().addClassName("color-green");
} else if(selected.contains(w)){
selected.remove(w);
w.getElement().removeClassName("color-green");
} else if(selected.size() == 1) {
Widget w2 = (Widget) selected.get(0);
connect(UIObjectConnector.getWrapper(w2), UIObjectConnector.getWrapper(w));
selected.clear();
}
}
protected void connect(Connector a, Connector b) {
//System.out.println(a.getLeft());
//System.out.println(b.getLeft());
add(new StraightTwoEndedConnection(a,b));
}
private void add(StraightTwoEndedConnection c) {
canvas.add(c);
connections.add(c);
c.update();
}
protected void remove(Connection c) {
connections.remove(c);
}
class MyHandler implements ClickHandler{
#Override
public void onClick(ClickEvent event) {
Button name = (Button) event.getSource();
if(name.equals(stopDrag)){
if(name.getText().equals("Done Dragging")){
for(Iterator<Widget> i = onCanvas.listIterator();i.hasNext();){
Widget w = (Widget) i.next();
dragController.makeNotDraggable(w);
}
name.setText("Continue");
}
else {
for(Iterator<Widget> i = onCanvas.listIterator();i.hasNext();){
Widget w = (Widget) i.next();
dragController.makeDraggable(w);
}
name.setText("Done Dragging");
}
}
else{
}
}
}
}
I know this is quite old, but I was having similar issues with the gwt-connector library.
The connectors will not appear in the correct placement if you are using standards mode. Use quirks mode instead.
Additionally, you need to manually perform a connector.update() while your dnd components are being dragged (in your drag listener) for the connection to move with the endpoint while you are dragging.
All Gmail users should have already noticed that file upload progress bar has been updated recently.
I'm wondering such effect is possible to implement with GWT.
I'm fairly new with GWT, so if any GWT source code that can help me test out the function would be very helpful.
Update
I ended up going with SWFUpload. However, other suggestions under this question are all valid. Just try different options and choose the one you like!
Take a look to this library: http://code.google.com/p/gwtupload/. It is really easy to to use and works fine in all browsers and OS I've checked. It uses ajax requests to calculate progress. BTW Swfupload doesn't do well in linux and Mac.
I've used this tool before:
http://code.google.com/p/gwt-fileapi/
Unlike the other suggestions here, not only does it give the proper API to show upload progress, it also gives the ability to do batch uploads by selecting multiple files, and it also gives drag and drop support. It also has a pre HTML5 fallback mechanism.
I've had had great luck with it gwt-fileap. Recently it broke in Firefox 7 and 8 and I had to apply this patch to it - but otherwise it works really great:
## -57,26 +57,33 ##
/**
* gets the filename
- *
+ *
* #return the filename
*/
public final native String getFileName() /*-{
- return this.fileName;
+ if(this.name)
+ return this.name;
+ else
+ return this.fileName;
+
}-*/;
/**
* gets the file size in bytes
- *
+ *
* #return the file size in bytes
*/
public final native int getFileSize() /*-{
- return this.fileSize;
+ if(this.size)
+ return this.size;
+ else
+ return this.fileSize;
}-*/;
/**
* gets the MIME type of the file, may be null if the browser cannot detect
* the type
I also had to add the following lines to http://code.google.com/p/gwt-fileapi/source/browse/trunk/gwt-fileapi/src/com/gwtpro/html5/fileapi/Html5FileApi.gwt.xml - these lines describe how the fallback mechanism works. You can do something similar if you want your code to fall back on the SWFUploader implementation shown below in case HTML5 is missing.
<define-property name="fileapi.support" values="yes,no" />
<property-provider name="fileapi.support"><![CDATA[
var input=document.createElement('input');
input.setAttribute('type','file');
return input.files==null?'no':'yes';
]]></property-provider>
<replace-with
class="com.gwtpro.html5.fileapi.client.ui.FileInput.FileInputImplHtml5">
<when-type-is
class="com.gwtpro.html5.fileapi.client.ui.FileInput.FileInputImpl" />
<when-property-is name="fileapi.support" value="yes" />
<any>
<when-property-is name="user.agent" value="ie8" />
<when-property-is name="user.agent" value="safari" />
<when-property-is name="user.agent" value="gecko1_8" />
<when-property-is name="user.agent" value="opera" />
<when-property-is name="user.agent" value="chrome" />
</any>
</replace-with>
This is how I use it in my application:
This is the interface that describes the abstraction:
public interface FileUpload {
public void uploadFiles();
public Widget getWidget();
public void initialize(Grid updateTable, Uploader uploader, String url, boolean createDropHandler);
public void setDisabled(boolean b);
public void readyToPaint();
public void reset();
}
The following is the gwt-fileapi implementation of the interface:
package com.hierarchycm.gxt.client.fileUpload;
import com.google.gwt.core.client.JsArray;
import com.google.gwt.event.dom.client.ChangeEvent;
import com.google.gwt.event.dom.client.ChangeHandler;
import com.google.gwt.http.client.RequestException;
import com.google.gwt.http.client.Response;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.ui.Grid;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.Widget;
import com.gwtpro.html5.fileapi.client.FileApiSupport;
import com.gwtpro.html5.fileapi.client.drop.DropHandler;
import com.gwtpro.html5.fileapi.client.file.File;
import com.gwtpro.html5.fileapi.client.file.FileEvent;
import com.gwtpro.html5.fileapi.client.file.FileEvent.FileEventHandler;
import com.gwtpro.html5.fileapi.client.ui.FileInput;
import com.gwtpro.html5.fileapi.client.upload.UploadRequest;
import com.gwtpro.html5.fileapi.client.upload.UploadRequestBuilder;
import com.gwtpro.html5.fileapi.client.upload.UploadRequestCallback;
public class FileUploadHtmlImpl extends FileInput implements FileUpload {
private Grid uploadTable;
int currentFile =0;
String url;
File[] files;
UploadRequestBuilder fileUploader;
Uploader uploader;
public FileUploadHtmlImpl() {
}
FileUploadHtmlImpl(Grid updateTable, Uploader uploader, String url) {
this(updateTable, uploader, url, true);
}
FileUploadHtmlImpl(Grid updateTable, Uploader uploader, String url, boolean createDropHandler) {
initialize(updateTable, uploader, url, createDropHandler);
//this.setCallback(getMyCallback());
}
public void initialize(Grid updateTable, Uploader uploader, String url, boolean createDropHandler){
this.url = url;
this.uploadTable = updateTable;
this.uploader = uploader;
this.setAllowMultipleFiles(true);
this.addChangeHandler(new ChangeHandler() {
#Override
public void onChange(ChangeEvent event) {
addFiles(FileUploadHtmlImpl.this.getFiles());
uploadFiles();
}
});
if (createDropHandler) {
createDropHandler();
}
}
private File[] jsArrToArr (JsArray<File> ipFiles) {
File [] result = new File [ipFiles.length()];
for (int i = 0; i < ipFiles.length(); ++i) {
result[i] = ipFiles.get(i);
}
return result;
}
private UploadRequestCallback getMyCallback() {
return new UploadRequestCallback() {
#Override
public void onError(UploadRequest request, Throwable exception) {
uploadTable.setText(currentFile + 1, 2, "failed: " + exception.getMessage());
uploadNextFile(currentFile + 1);
}
#Override
public void onResponseReceived(UploadRequest request, Response response) {
uploadTable.setText(currentFile + 1, 2, "success: " + response.getText());
uploadNextFile(currentFile + 1);
//If we just finished uploading do your thing
if (currentFile == files.length) {
setDisabled(false);
uploader.uploadDoneEventHandler();
}
}
#Override
public void onUploadProgress(UploadRequest request, int bytesUploaded) {
uploadTable.setText(currentFile + 1, 2, bytesUploaded + "");
}
};
}
public void createDropHandler() {
RootPanel rootPanel = RootPanel.get();
DropHandler dropHandler = new DropHandler(rootPanel);
this.fileUploader = new UploadRequestBuilder(url);
this.fileUploader.setCallback(getMyCallback());
dropHandler.addFileEventHandler(new FileEventHandler() {
#Override
public void onFiles(FileEvent event) {
addFiles(jsArrToArr(event.getFiles()));
uploadFiles();
}
});
}
private void addFiles (File[] ipFiles) {
files = ipFiles;
uploadTable.clear();
uploadTable.resize(files.length + 1, 3);
uploadTable.setText(0, 0, "File name");
uploadTable.setText(0, 1, "File size");
uploadTable.setText(0, 2, "Progress");
for (int i = 0; i < files.length; ++i) {
uploadTable.setText(i + 1, 0, files[i].getFileName());
uploadTable.setText(i + 1, 1, files[i].getFileSize() + "");
uploadTable.setText(i + 1, 2, "");
}
}
public void uploadNextFile(int index) {
for (String paramName : uploader.getPostParams().keySet()) {
fileUploader.setHeader(paramName, uploader.getPostParams().get(paramName));
}
currentFile = index;
this.setDisabled(true);
if (index < this.files.length) {
try {
this.fileUploader.setHeader("itemName", files[currentFile].getFileName());
this.fileUploader.sendFile(files[currentFile]);
} catch (RequestException e) {
this.uploadTable.setText(index + 1, 2, "failed: " + e.getMessage());
uploadNextFile(index + 1);
}
}
}
public void uploadFiles() {
uploadNextFile(0);
}
#Override
public Widget getWidget() {
return this;
}
#Override
public void readyToPaint() {
//no need to do anything - already painted for non swf
}
#Override
public void reset() {
// TODO Auto-generated method stub
}
private void showCapabilities() {
RootPanel
.get("status")
.getElement()
.setInnerHTML(
"Drag and Drop Support: "
+ (FileApiSupport.isDragDropSupported() ? "Yes"
: "No")
+ "<br/>HTTPXmlRequest Level 2: "
+ (FileApiSupport.isHttpXmlRequestLevel2() ? "Yes"
: "No")
+ "<br/>File input supports multiple files: "
+ (FileApiSupport
.isMultipleFileInputSupported() ? "Yes"
: "No")+"<br/><br/>");
}
}
This is the SWFUpload http://code.google.com/p/swfupload-gwt/ implementation of the same interface:
package com.hierarchycm.gxt.client.fileUpload;
import com.extjs.gxt.ui.client.widget.Html;
import com.google.gwt.user.client.ui.Grid;
import com.google.gwt.user.client.ui.Widget;
public class FileUploadSwfImpl extends Html implements FileUpload {
SwfUploadUtil swfUploadUtil = null;
private Uploader uploader;
private String url;
private boolean createDropHandler;
private Grid updateTable;
static int uploadId = 0;
static String divTagId;
public FileUploadSwfImpl() {
divTagId = "swfupload" + uploadId++;
String divTag = "<div id=\"" + divTagId + "\"></div";
this.setHtml(divTag);
}
#Override
public void uploadFiles() {
swfUploadUtil.startUpload();
}
#Override
public Widget getWidget() {
return this;
}
public void readyToPaint() {
swfUploadUtil = new SwfUploadUtil(uploader, updateTable, divTagId, url);
}
#Override
public void initialize(Grid updateTable, Uploader uploader, String url, boolean createDropHandler) {
this.uploader = uploader;
this.url = url;
this.createDropHandler = createDropHandler;
this.updateTable = updateTable;
}
#Override
public void setDisabled(boolean b) {
swfUploadUtil.setDisabled(b);
this.disabled = true;
}
#Override
public void reset() {
swfUploadUtil.reset();
}
}
And this is the utility the FileUploadSwfImpl depends on:
package com.hierarchycm.gxt.client.fileUpload;
import java.util.HashMap;
import org.swfupload.client.File;
import org.swfupload.client.SWFUpload;
import org.swfupload.client.UploadBuilder;
import org.swfupload.client.SWFUpload.ButtonAction;
import org.swfupload.client.SWFUpload.ButtonCursor;
import org.swfupload.client.event.DialogStartHandler;
import org.swfupload.client.event.FileDialogCompleteHandler;
import org.swfupload.client.event.FileQueuedHandler;
import org.swfupload.client.event.UploadCompleteHandler;
import org.swfupload.client.event.UploadErrorHandler;
import org.swfupload.client.event.UploadProgressHandler;
import org.swfupload.client.event.UploadSuccessHandler;
import org.swfupload.client.event.FileDialogCompleteHandler.FileDialogCompleteEvent;
import org.swfupload.client.event.FileQueuedHandler.FileQueuedEvent;
import org.swfupload.client.event.UploadCompleteHandler.UploadCompleteEvent;
import org.swfupload.client.event.UploadErrorHandler.UploadErrorEvent;
import org.swfupload.client.event.UploadProgressHandler.UploadProgressEvent;
import org.swfupload.client.event.UploadSuccessHandler.UploadSuccessEvent;
import com.extjs.gxt.ui.client.widget.form.TextArea;
import com.google.gwt.core.client.GWT;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.ui.Grid;
public class SwfUploadUtil {
HashMap<String, Integer> filenameRowHm = new HashMap<String, Integer>();
private boolean resetIssued;
SWFUpload swfUpload = null;
private HashMap <String, File> files = new HashMap<String, File>();
int tableRow = 5;
Uploader uploader = null;
private Grid updateTable;
private String divName;
private String url;
synchronized private void removeFile(String id) {
files.remove(id);
}
public SwfUploadUtil(Uploader uploader, Grid updateTable, String divName, String url){
reset();
this.uploader = uploader;
this.updateTable = updateTable;
this.divName = divName;
this.url = url;
this.swfUpload = loadSWFUpload();
updateTable.resize(5, 5);
updateTable.setText(2, 0, "Upload URL:" );
updateTable.setText(2, 1, url );
updateTable.setText(4, 0, "File Name" );
updateTable.setText(4, 1, "Bytes In");
updateTable.setText(4, 2, "Status");
updateTable.setText(4, 3, "File Size" );
updateTable.setText(4, 4, "Server response" );
}
public SWFUpload loadSWFUpload() {
this.updateTable = updateTable;
if (swfUpload == null) {
final UploadBuilder builder1 = new UploadBuilder();
builder1.setHTTPSuccessCodes(200, 201);
builder1.setFileTypes("*.webm;*.asf;*.wma;*.wmv;*.avi;*.flv;*.swf;*.mpg;*.mpeg;*.mp4;*.mov;*.m4v;*.aac;*.mp3;*.wav;*.png;*.jpg;*.jpeg;*.gif");
builder1.setFileTypesDescription("Images, Video & Sound");
builder1.setButtonPlaceholderID(divName);
builder1.setButtonImageURL("./images/XPButtonUploadText_61x22.png");
builder1.setButtonCursor(ButtonCursor.HAND);
builder1.setButtonWidth(61);
builder1.setButtonHeight(22);
builder1.setButtonAction(ButtonAction.SELECT_FILES);
builder1.setUploadProgressHandler(new UploadProgressHandler() {
public void onUploadProgress(UploadProgressEvent e) {
File f = e.getFile();
updateTable.setText(getFilenameRow(f), 2, String.valueOf(e.getBytesComplete()));
}
});
builder1.setUploadSuccessHandler(new UploadSuccessHandler() {
public void onUploadSuccess(UploadSuccessEvent e) {
File f = e.getFile();
updateTable.setText(getFilenameRow(f), 4, e.getServerData());
}
});
builder1.setUploadErrorHandler(new UploadErrorHandler() {
public void onUploadError(UploadErrorEvent e) {
File ff = e.getFile();
String message = e.getMessage();
if (message == null || message.trim().length() == 0) {
message = "upload failed";
}
updateTable.setText(getFilenameRow(ff), 2, String.valueOf(message));
removeFile(ff.getId());
if (files.values().size() > 0) {
ff = files.values().iterator().next();
updateTable.setText(getFilenameRow(ff), 2, "Started");
swfUpload.startUpload(ff.getId());
}
}
});
builder1.setUploadURL(url);
builder1.setDialogStartHandler(new DialogStartHandler() {
#Override
public void onDialogStart() {
if(resetIssued == true) {
filenameRowHm.clear();
resetIssued = false;
}
}
}
);
builder1.setUploadCompleteHandler(new UploadCompleteHandler() {
public void onUploadComplete(UploadCompleteEvent e) {
File f = e.getFile();
updateTable.setText(getFilenameRow(f), 2, "Done");
removeFile(f.getId());
if (files.values().size() > 0) {
File ff = files.values().iterator().next();
updateTable.setText(getFilenameRow(ff), 2, "Started");
swfUpload.startUpload(ff.getId());
} else {
uploader.uploadDoneEventHandler();
}
}
});
builder1.setFileQueuedHandler(new FileQueuedHandler() {
public void onFileQueued(FileQueuedEvent event) {
File f = event.getFile();
updateTable.setText(getFilenameRow(f), 2, "Queued");
files.put(f.getId(), f);
}
});
builder1.setFileDialogCompleteHandler(new FileDialogCompleteHandler() {
public void onFileDialogComplete(FileDialogCompleteEvent e) {
updateTable.setText(2, 0, "Number of files");
updateTable.setText(2, 1, String.valueOf(files.values().size()));
for(File f : files.values()) {
getFilenameRow(f);
}
if (files.values().size() > 0) {
for (String paramName : uploader.getPostParams().keySet()) {
swfUpload.addPostParam(paramName,uploader.getPostParams().get(paramName));
}
}
}
});
swfUpload = builder1.build();
}
return swfUpload;
}
public int getFilenameRow (File f) {
Integer filenamerow = filenameRowHm.get(f.getId());
if (filenamerow == null) {
updateTable.resize(tableRow+1, 5);
filenamerow = new Integer(tableRow++);
updateTable.setText(filenamerow.intValue(), 0, f.getName());
updateTable.setText(filenamerow.intValue(), 3, String.valueOf(f.getSize()));
//updateTable.setText(filenamerow.intValue(), 3, String.valueOf(f));
filenameRowHm.put(f.getId(), filenamerow);
}
return filenamerow.intValue();
}
public void startUpload() {
uploader.uploadStartedEventHandler();
swfUpload.startUpload();
}
public void setDisabled(boolean disabled) {
swfUpload.setButtonDisabled(disabled);
}
public void reset() {
// TODO Auto-generated method stub
resetIssued = true;
}
}
Use SWFUpload via swfupload-gwt
The main advantage over the other methods is this does not require any special server code. You could even upload to another domain (if there is a crossdomain.xml which allows it).
Check out GWTC Upload, which has an implementation of exactly what you're looking for.
It's trivial to write your own if you have a java back end, you just start a file upload and then poll the server on a timer to see where it's up to (say every second or two). The java file upload binaries (the apache commons ones) support telling you the current progress so it's trivial to do.
Recently I started a project of my own called gwtupld
http://github.com/kompot/gwtupld/
The main goal is to provide best file upload experience for cutting edge browsers
and acceptable usability for all others. By the moment, following key features are present
multiple file selection
drag'n'drop
progress bars
slick and simple exterior
consistent behavior for all browsers
ease of visual customization
no external dependencies but GWT
Feel free to fork and submit bugs/feature proposals.
You can check out source code, then type
gradlew gwtcompile devmode
and get it will start a fully functional
sandbox (server side with real file saving should work)
You can use GwtSwfExt which is wrapper on top of SWFUpload (Its same as Swfupload-gwt lib ) you can download example and source code from http://code.google.com/p/gwtswfext.
When creating your own file upload progress, instead of pulling it form server at a small set time, you can have the client to display a indeterminate bar for 2 seconds and have the server calculate the estimated finish time the change back to determinate and pull new estimates every 5, 10 seconds instead. that should have little to no effect on the traffic.
There is custom multiupload plugin demo http://ext4all.com/post/extjs-4-multiple-file-upload