Created
September 11, 2014 09:30
-
-
Save akjava/27008a12975c4a27a376 to your computer and use it in GitHub Desktop.
GWTWebWorker Sample
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?xml version="1.0" encoding="UTF-8"?> | |
<!-- | |
When updating your version of GWT, you should also update this DTD reference, | |
so that your app can take advantage of the latest GWT module capabilities. | |
--> | |
<!DOCTYPE module PUBLIC "-//Google Inc.//DTD Google Web Toolkit 2.5.1//EN" | |
"http://google-web-toolkit.googlecode.com/svn/tags/2.5.1/distro-source/core/src/gwt-module.dtd"> | |
<module rename-to='gwtwebworkerssample'> | |
<!-- Inherit the core Web Toolkit stuff. --> | |
<inherits name='com.google.gwt.user.User'/> | |
<!-- Inherit the default GWT style sheet. You can change --> | |
<!-- the theme of your GWT application by uncommenting --> | |
<!-- any one of the following lines. --> | |
<inherits name='com.google.gwt.user.theme.clean.Clean'/> | |
<!-- <inherits name='com.google.gwt.user.theme.standard.Standard'/> --> | |
<!-- <inherits name='com.google.gwt.user.theme.chrome.Chrome'/> --> | |
<!-- <inherits name='com.google.gwt.user.theme.dark.Dark'/> --> | |
<!-- Other module inherits --> | |
<inherits name='com.google.gwt.webworker.WebWorker'/> | |
<!-- Specify the app entry point class. --> | |
<entry-point class='com.akjava.gwt.webworkers.client.GWTWebWorkersSample'/> | |
<!-- Specify the paths for translatable code --> | |
<source path='client'/> | |
<source path='shared'/> | |
<set-property name="user.agent" value="safari"/> | |
</module> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package com.akjava.gwt.webworkers.client; | |
import com.google.gwt.canvas.client.Canvas; | |
import com.google.gwt.canvas.dom.client.Context2d; | |
import com.google.gwt.canvas.dom.client.ImageData; | |
import com.google.gwt.core.client.EntryPoint; | |
import com.google.gwt.core.client.JavaScriptObject; | |
import com.google.gwt.core.client.JsArray; | |
import com.google.gwt.dom.client.Document; | |
import com.google.gwt.dom.client.ImageElement; | |
import com.google.gwt.dom.client.NativeEvent; | |
import com.google.gwt.event.dom.client.ChangeEvent; | |
import com.google.gwt.event.dom.client.ChangeHandler; | |
import com.google.gwt.event.dom.client.ClickEvent; | |
import com.google.gwt.event.dom.client.ClickHandler; | |
import com.google.gwt.user.client.Timer; | |
import com.google.gwt.user.client.Window; | |
import com.google.gwt.user.client.ui.Button; | |
import com.google.gwt.user.client.ui.FileUpload; | |
import com.google.gwt.user.client.ui.Image; | |
import com.google.gwt.user.client.ui.RootPanel; | |
import com.google.gwt.user.client.ui.VerticalPanel; | |
import com.google.gwt.webworker.client.MessageEvent; | |
import com.google.gwt.webworker.client.MessageHandler; | |
import com.google.gwt.webworker.client.MessagePort; | |
import com.google.gwt.webworker.client.Worker; | |
/** | |
* Entry point classes define <code>onModuleLoad()</code>. | |
*/ | |
public class GWTWebWorkersSample implements EntryPoint { | |
@Override | |
public void onModuleLoad() { | |
final VerticalPanel root=new VerticalPanel(); | |
RootPanel.get().add(root); | |
Button helloBt=new Button("Hello",new ClickHandler() { | |
@Override | |
public void onClick(ClickEvent event) { | |
//relative on modulebase | |
Worker worker=Worker.create("/test1.js"); | |
worker.setOnMessage(new MessageHandler() { | |
@Override | |
public void onMessage(MessageEvent event) { | |
Window.alert(event.getDataAsString()); | |
} | |
}); | |
worker.postMessage("Hello"); | |
} | |
}); | |
root.add(helloBt); | |
final Canvas canvas=Canvas.createIfSupported(); | |
canvas.getContext2d().fillRect(0, 0, canvas.getCoordinateSpaceWidth(), canvas.getCoordinateSpaceHeight()); | |
root.add(canvas); | |
Button pixelBt=new Button("Gray",new ClickHandler() { | |
@Override | |
public void onClick(ClickEvent event) { | |
//relative on modulebase | |
Worker worker=Worker.create("/gray.js"); | |
final ImageData imageData=canvas.getContext2d().getImageData(0, 0, canvas.getCoordinateSpaceWidth(), canvas.getCoordinateSpaceHeight()); | |
worker.setOnMessage(new MessageHandler() { | |
@Override | |
public void onMessage(MessageEvent event) { | |
log(imageData); | |
log(event.getDataAsJavaScriptObject()); | |
ImageData newData=event.getDataAsJavaScriptObject().cast(); | |
canvas.getContext2d().putImageData(newData, 0, 0); | |
log(event.getPorts().get(0)); | |
} | |
}); | |
JsArray<MessagePort> ports=JavaScriptObject.createArray().cast(); | |
MessagePort array=DataBuffer.create(imageData); | |
ports.push(array); | |
//worker.postMessage(w,ports); | |
log(""+imageData.getData().getLength()); | |
worker.postMessage(imageData,ports);// | |
//worker.postMessage(convert(imageData),ports);//no copy | |
log(""+imageData.getData().getLength()); | |
} | |
}); | |
root.add(pixelBt); | |
final Canvas imageCanvas=Canvas.createIfSupported(); | |
imageCanvas.setSize("400px", "400px"); | |
FileUpload upload=new FileUpload(); | |
upload.addChangeHandler(new ChangeHandler() { | |
@Override | |
public void onChange(ChangeEvent event) { | |
JsArray<Blob> blobs=toFile(event.getNativeEvent()); | |
String url=DownloadURL.get().createObjectURL(blobs.get(0)); | |
final ImageElement image=Document.get().createImageElement(); | |
image.setSrc(url); | |
images=0; | |
imageCanvas.getContext2d().drawImage(image, 0, 0); | |
new Timer(){ | |
@Override | |
public void run() { | |
final long s=System.currentTimeMillis(); | |
//blob url need load? | |
imageCanvas.setWidth(image.getWidth()+"px"); | |
imageCanvas.setHeight(image.getHeight()+"px"); | |
imageCanvas.setCoordinateSpaceWidth(image.getWidth()); | |
imageCanvas.setCoordinateSpaceHeight(image.getHeight()); | |
imageCanvas.getContext2d().drawImage(image, 0, 0); | |
for(int i=0;i<50;i++){ | |
final ImageData imageData=imageCanvas.getContext2d().getImageData(0, 0, imageCanvas.getCoordinateSpaceWidth(), imageCanvas.getCoordinateSpaceHeight()); | |
if(useWorker){ | |
Worker worker=Worker.create("/grayscale.js"); | |
worker.setOnMessage(new MessageHandler() { | |
@Override | |
public void onMessage(MessageEvent event) { | |
ImageData newData=event.getDataAsJavaScriptObject().cast(); | |
imageCanvas.getContext2d().putImageData(newData, 0, 0); | |
images++; | |
if(images==50){ | |
log("time:"+(System.currentTimeMillis()-s)); | |
} | |
root.add(new Image(imageCanvas.toDataUrl())); | |
} | |
}); | |
JsArray<MessagePort> ports=JavaScriptObject.createArray().cast(); | |
MessagePort array=DataBuffer.create(imageData); | |
ports.push(array); | |
worker.postMessage(imageData,ports);// | |
}else{ | |
for(int y=0;y<imageData.getHeight();y++){ | |
for(int x=0;x<imageData.getWidth();x++){ | |
int value=(int) (0.299*imageData.getRedAt(x, y) + 0.587*imageData.getGreenAt(x, y) + 0.114*imageData.getBlueAt(x, y)); | |
imageData.setRedAt(value, x, y); | |
imageData.setGreenAt(value, x, y); | |
imageData.setBlueAt(value, x, y); | |
} | |
} | |
imageCanvas.getContext2d().putImageData(imageData, 0, 0); | |
images++; | |
if(images==50){ | |
log("time:"+(System.currentTimeMillis()-s)); | |
} | |
root.add(new Image(imageCanvas.toDataUrl())); | |
} | |
} | |
}}.schedule(500); | |
//it's time to web worker | |
} | |
}); | |
root.add(imageCanvas); | |
root.add(upload); | |
FileUpload uploadTest=new FileUpload(); | |
uploadTest.addChangeHandler(new ChangeHandler() { | |
@Override | |
public void onChange(ChangeEvent event) { | |
JsArray<Blob> blobs=toFile(event.getNativeEvent()); | |
String url=DownloadURL.get().createObjectURL(blobs.get(0)); | |
final ImageElement image=Document.get().createImageElement(); | |
image.setSrc(url); | |
images=0; | |
imageCanvas.getContext2d().drawImage(image, 0, 0);//for load | |
new Timer(){ | |
@Override | |
public void run() { | |
//blob url need load? | |
imageCanvas.setWidth(image.getWidth()+"px"); | |
imageCanvas.setHeight(image.getHeight()+"px"); | |
imageCanvas.setCoordinateSpaceWidth(image.getWidth()); | |
imageCanvas.setCoordinateSpaceHeight(image.getHeight()); | |
imageCanvas.getContext2d().drawImage(image, 0, 0); | |
final ImageData imageData=imageCanvas.getContext2d().getImageData(0, 0, imageCanvas.getCoordinateSpaceWidth(), imageCanvas.getCoordinateSpaceHeight()); | |
Context2d ctx=imageCanvas.getContext2d(); | |
final long s=System.currentTimeMillis(); | |
for(int i=0;i<10;i++){ | |
/* | |
* ImageData newData=ctx.createImageData(imageData); //just copy w&h 30ms-45ms | |
for(int j=0;j<imageData.getData().getLength();j++){ | |
newData.getData().set(j, imageData.getData().get(j));//maybe slow copy,use native //wao 1400ms | |
} | |
*/ | |
ImageData newData=copy(ctx, imageData);//50ms extremly first | |
if(i==0){ | |
imageData.setAlphaAt(1, 0, 0);//check cloned? | |
log(""+newData.getAlphaAt(0, 0)); | |
} | |
} | |
log("time:"+(System.currentTimeMillis()-s)); | |
/* | |
for(int i=0;i<imageData.getData().getLength();i++){ | |
newData.getData().set(i, imageData.getData().get(i));//maybe slow copy,use native | |
} | |
*/ | |
} | |
}.schedule(500); | |
//it's time to web worker | |
} | |
}); | |
root.add(uploadTest); | |
} | |
int images=0; | |
boolean useWorker=false; | |
public static native final ImageData copy(Context2d ctx,ImageData src)/*-{ | |
var dst = ctx.createImageData(src.width, src.height); | |
dst.data.set(src.data); | |
return dst; | |
}-*/; | |
public static class DownloadURL extends JavaScriptObject{ | |
protected DownloadURL(){} | |
public native final String createObjectURL(JavaScriptObject object)/*-{ | |
return this.createObjectURL(object); | |
}-*/; | |
public native final void revokeObjectURL(String url)/*-{ | |
this.revokeObjectURL(url); | |
}-*/; | |
public static native final DownloadURL get()/*-{ | |
return window.webkitURL || window.URL; | |
}-*/; | |
} | |
public static class Blob extends JavaScriptObject{ | |
protected Blob(){} | |
} | |
public static final native JsArray<Blob> toFile(NativeEvent event)/*-{ | |
return event.target.files; | |
}-*/; | |
public static native JavaScriptObject convert(ImageData imageData) /*-{ | |
return {data:imageData.data.buffer,width:imageData.width,height:imageData.height}; | |
}-*/; | |
public static native void log(String object) /*-{ | |
console.log(object); | |
}-*/; | |
public static native void log(JavaScriptObject object) /*-{ | |
console.log(object); | |
}-*/; | |
//this is not so good | |
public static class DataBuffer extends MessagePort{ | |
protected DataBuffer(){} | |
public static native DataBuffer create(ImageData imageData) /*-{ | |
return imageData.data.buffer; | |
}-*/; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
need add these on Worker.java
/* added my self**/
public final native void postMessage(JavaScriptObject message) /-{
this.postMessage(message);
}-/;
/** added my self/
public final native void postMessage(JavaScriptObject message,JsArray ports) /-{
this.postMessage(message,ports);
}-*/;
//MessageEvent.java
public final native JavaScriptObject getDataAsJavaScriptObject() /-{
return this.data;
}-/;