From: Artur Signell Date: Thu, 12 Nov 2009 13:55:27 +0000 (+0000) Subject: Fix for #3589 - Window.executeJavaScript(). Removed DOM reference possibility. X-Git-Tag: 6.7.0.beta1~2308 X-Git-Url: https://source.dussan.org/?a=commitdiff_plain;h=1d2c11a2f7b4f528aae73601caff3479cbf6d26a;p=vaadin-framework.git Fix for #3589 - Window.executeJavaScript(). Removed DOM reference possibility. svn changeset:9746/svn branch:6.2 --- diff --git a/src/com/vaadin/terminal/gwt/client/ui/VView.java b/src/com/vaadin/terminal/gwt/client/ui/VView.java index 1c097adcf7..bfa4a653bd 100644 --- a/src/com/vaadin/terminal/gwt/client/ui/VView.java +++ b/src/com/vaadin/terminal/gwt/client/ui/VView.java @@ -10,7 +10,6 @@ import java.util.Iterator; import java.util.LinkedHashSet; import java.util.Set; -import com.google.gwt.core.client.JavaScriptObject; import com.google.gwt.dom.client.DivElement; import com.google.gwt.dom.client.Document; import com.google.gwt.event.logical.shared.ResizeEvent; @@ -145,39 +144,20 @@ public class VView extends SimplePanel implements Container, ResizeHandler, }-*/; /** - * Evaluate given script in browser document. + * Evaluate the given script in the browser document. * * @param script - * Script to be executed with $1, $2, ... markers to be replaced - * with argument references. - * @param args - * JavaScript array of element references to be replaced in - * script + * Script to be executed. */ - private static native void eval(String script, JavaScriptObject args) + private static native void eval(String script) /*-{ try { if (script == null) return; - $wnd.vaadin.evalargs = args; - if (args != null) - for (var i=1;i<= args.length;i++) - script = script.replace("$"+i, "$wnd.vaadin.evalargs["+(i-1)+"]"); $wnd.eval(script); - delete $wnd.vaadin.evalargs; } catch (e) { } }-*/; - /** Helper for creating empty javascript arrays */ - private native static JavaScriptObject createArray() /*-{ - return new Array(); - }-*/; - - /** Add an element to javascript array */ - private native static void pushArray(JavaScriptObject array, Element e) /*-{ - array.push(e); - }-*/; - public void updateFromUIDL(UIDL uidl, ApplicationConnection client) { rendering = true; @@ -300,16 +280,7 @@ public class VView extends SimplePanel implements Container, ResizeHandler, actionHandler.updateActionMap(childUidl); } else if (tag == "execJS") { String script = childUidl.getStringAttribute("script"); - int argNum = childUidl.getChildCount(); - JavaScriptObject args = createArray(); - for (int i = 0; i < argNum; i++) { - String id = childUidl.getChildUIDL(i).getStringAttribute( - "ref"); - Paintable p = client.getPaintable(id); - pushArray(args, p == null ? null : ((Widget) p) - .getElement()); - } - eval(script, args); + eval(script); } else if (tag == "notifications") { for (final Iterator it = childUidl.getChildIterator(); it .hasNext();) { diff --git a/src/com/vaadin/ui/Window.java b/src/com/vaadin/ui/Window.java index 8de7a944f7..d234f7aaac 100644 --- a/src/com/vaadin/ui/Window.java +++ b/src/com/vaadin/ui/Window.java @@ -20,7 +20,6 @@ import com.vaadin.Application; import com.vaadin.terminal.DownloadStream; import com.vaadin.terminal.PaintException; import com.vaadin.terminal.PaintTarget; -import com.vaadin.terminal.Paintable; import com.vaadin.terminal.ParameterHandler; import com.vaadin.terminal.Resource; import com.vaadin.terminal.Sizeable; @@ -122,7 +121,6 @@ public class Window extends Panel implements URIHandler, ParameterHandler { private Focusable pendingFocus; private ArrayList jsExecQueue = null; - private ArrayList> jsExecParamsQueue = null; /* ********************************************************************* */ @@ -527,22 +525,12 @@ public class Window extends Panel implements URIHandler, ParameterHandler { // Add executable javascripts if needed if (jsExecQueue != null) { - while (jsExecQueue.size() > 0) { - String script = jsExecQueue.get(0); - ArrayList args = jsExecParamsQueue.get(0); + for (String script : jsExecQueue) { target.startTag("execJS"); target.addAttribute("script", script); - for (Paintable p : args) { - target.startTag("arg"); - target.paintReference(p, "ref"); - target.endTag("arg"); - } target.endTag("execJS"); - jsExecQueue.remove(0); - jsExecParamsQueue.remove(0); } jsExecQueue = null; - jsExecParamsQueue = null; } // Window position @@ -1661,82 +1649,34 @@ public class Window extends Panel implements URIHandler, ParameterHandler { * Executes JavaScript in this window. * *

- * This method allows one to inject javascript from the server to client. - * Client implementation is not required to implenment this functionality, + * This method allows one to inject javascript from the server to client. A + * client implementation is not required to implement this functionality, * but currently all web-based clients do implement this. *

* *

- * Use of this method should be avoided. Executing javascript often leads to - * cross-browser compatibility issues and regressions that are hard to - * resolve. Instead it is recommended to create new widgets with google web - * toolkit. For more info on creating own, reusable client-side widgets in - * Java, read corresponding chapter on Book of Vaadin. - *

- * - *

- * The script may contain markers indentified with "$x", where x is a one - * digit number. The number of markers must match to the number of optional - * Paintable reference parameters. The first marker is $1, second $2 and so - * on. If the markers are specified, the markers are replaced in the browser - * with references to outmost DOM elements connected to the given - * paintables. - *

- * - *

- * Use example 1: Show a alert box in the current window - mainWindow.executeJavaScript("alert('foo');"); - * - *

- * - *

- * Use example 2: Print current window - mainWindow.executeJavaScript("window.print()"); - * - *

- * - *

- * Use example 3: Change labels background to yellow - Label label = new Label("Label"); - mainWindow.addComponent(label); - mainWindow.executeJavaScript("$1.style.backgroundColor='yellow';",label); - * - *

- * - *

- * Use example 4: Print contents of a label - Label label = new Label("This label contains some report"); - mainWindow.addComponent(label); - mainWindow.executeJavaScript("var w = window.open(); w.document.write($1.outerHTML); w.print();",label); - * + * Executing javascript this way often leads to cross-browser compatibility + * issues and regressions that are hard to resolve. Use of this method + * should be avoided and instead it is recommended to create new widgets + * with GWT. For more info on creating own, reusable client-side widgets in + * Java, read the corresponding chapter in Book of Vaadin. *

* * @param script - * JavaScript snippet that will be executed and that might - * optionally contain $1, $2, ... markers. - * @param paintables - * References to number of visible paintables that correspond the - * to markers listed in script + * JavaScript snippet that will be executed. */ - public void executeJavaScript(String script, Paintable... paintables) { + public void executeJavaScript(String script) { if (getParent() != null) { throw new UnsupportedOperationException( "Only application level windows can execute javascript."); } - ArrayList ps = new ArrayList(); - for (Paintable p : paintables) { - ps.add(p); - } - if (jsExecQueue == null) { jsExecQueue = new ArrayList(); - jsExecParamsQueue = new ArrayList>(); } jsExecQueue.add(script); - jsExecParamsQueue.add(ps); requestRepaint(); } diff --git a/tests/src/com/vaadin/tests/components/window/ExecuteJavaScript.java b/tests/src/com/vaadin/tests/components/window/ExecuteJavaScript.java new file mode 100644 index 0000000000..3d4394dede --- /dev/null +++ b/tests/src/com/vaadin/tests/components/window/ExecuteJavaScript.java @@ -0,0 +1,46 @@ +package com.vaadin.tests.components.window; + +import com.vaadin.tests.components.AbstractTestCase; +import com.vaadin.ui.Button; +import com.vaadin.ui.Panel; +import com.vaadin.ui.Window; +import com.vaadin.ui.Button.ClickEvent; + +public class ExecuteJavaScript extends AbstractTestCase { + + @Override + public void init() { + final Window mainWindow = new Window("Test"); + setMainWindow(mainWindow); + + for (final String script : new String[] { "alert('foo');", + "window.print()", "document.write('foo')" }) { + Panel p = new Panel("Example: " + script); + p.addComponent(createScriptButton(script)); + mainWindow.addComponent(p); + } + + } + + private Button createScriptButton(final String script) { + Button b = new Button(script); + b.addListener(new Button.ClickListener() { + + public void buttonClick(ClickEvent event) { + getMainWindow().executeJavaScript(script); + } + }); + + return b; + } + + @Override + protected String getDescription() { + return "Test for the Window.executeJavaScript method. Click a button to execute the javascript"; + } + + @Override + protected Integer getTicketNumber() { + return 3589; + } +} diff --git a/tests/src/com/vaadin/tests/tickets/Ticket3589.java b/tests/src/com/vaadin/tests/tickets/Ticket3589.java deleted file mode 100644 index f072f2dd90..0000000000 --- a/tests/src/com/vaadin/tests/tickets/Ticket3589.java +++ /dev/null @@ -1,57 +0,0 @@ -package com.vaadin.tests.tickets; - -import com.vaadin.Application; -import com.vaadin.ui.Button; -import com.vaadin.ui.Label; -import com.vaadin.ui.Panel; -import com.vaadin.ui.TextField; -import com.vaadin.ui.Window; -import com.vaadin.ui.Button.ClickEvent; - -public class Ticket3589 extends Application { - - @Override - public void init() { - final Window mainWindow = new Window("Test"); - setMainWindow(mainWindow); - - for (final String script : new String[] { "alert('foo');", - "window.print()", "document.write('foo')" }) { - Panel p = new Panel("Example: " + script); - p.addComponent(new Button("Run javascript", - new Button.ClickListener() { - - public void buttonClick(ClickEvent event) { - mainWindow.executeJavaScript(script); - } - })); - mainWindow.addComponent(p); - } - - final String script = "$1.style.backgroundColor='yellow';$2.style.borderColor='red';"; - Panel p = new Panel("Example: " + script); - final Label label = new Label("Label"); - final TextField textfield = new TextField("TestField"); - p.addComponent(label); - p.addComponent(textfield); - p.addComponent(new Button("Run javascript", new Button.ClickListener() { - - public void buttonClick(ClickEvent event) { - mainWindow.executeJavaScript(script, label, textfield); - } - })); - mainWindow.addComponent(p); - - final String script2 = "var w = window.open(); w.document.write($1.outerHTML); w.print();"; - final Panel p2 = new Panel("Example: " + script2); - p2.addComponent(new Label("Only this panel will be printed...")); - p2.addComponent(new Button("Run javascript", - new Button.ClickListener() { - public void buttonClick(ClickEvent event) { - mainWindow.executeJavaScript(script2, p2); - } - })); - mainWindow.addComponent(p2); - - } -}