summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLeif Åstrand <leif@vaadin.com>2013-01-09 13:53:23 +0000
committerVaadin Code Review <review@vaadin.com>2013-01-09 13:53:23 +0000
commit30f4d3ede40f95919a225a1f7f8bff182a1bf0e2 (patch)
tree6cbd35abff436c9dbaf132b32465cabdb5693f03
parent1a20331682f4495509fa79ad54c96fe77de82eed (diff)
parent058224f31198b2a56fd7fd52e9a767909b58cd79 (diff)
downloadvaadin-framework-30f4d3ede40f95919a225a1f7f8bff182a1bf0e2.tar.gz
vaadin-framework-30f4d3ede40f95919a225a1f7f8bff182a1bf0e2.zip
Merge "Merge of (#7842) to Vaadin 7."
-rw-r--r--client/src/com/vaadin/client/ui/ui/UIConnector.java45
-rw-r--r--server/src/com/vaadin/server/Page.java102
-rw-r--r--server/src/com/vaadin/ui/LegacyWindow.java66
-rw-r--r--uitest/src/com/vaadin/tests/components/window/LegacyWindowOpenTest.java74
-rw-r--r--uitest/src/com/vaadin/tests/components/window/PageOpenTest.java81
5 files changed, 339 insertions, 29 deletions
diff --git a/client/src/com/vaadin/client/ui/ui/UIConnector.java b/client/src/com/vaadin/client/ui/ui/UIConnector.java
index 099cd5562e..85e75b943e 100644
--- a/client/src/com/vaadin/client/ui/ui/UIConnector.java
+++ b/client/src/com/vaadin/client/ui/ui/UIConnector.java
@@ -131,6 +131,11 @@ public class UIConnector extends AbstractSingleComponentContainerConnector
});
}
+ private native void open(String url, String name)
+ /*-{
+ $wnd.open(url, name);
+ }-*/;
+
@Override
public void updateFromUIDL(final UIDL uidl, ApplicationConnection client) {
ConnectorMap paintableMap = ConnectorMap.get(getConnection());
@@ -194,27 +199,35 @@ public class UIConnector extends AbstractSingleComponentContainerConnector
VUI.goTo(url);
} else {
String options;
- if (open.hasAttribute("border")) {
- if (open.getStringAttribute("border").equals("minimal")) {
- options = "menubar=yes,location=no,status=no";
+ boolean alwaysAsPopup = true;
+ if (open.hasAttribute("popup")) {
+ alwaysAsPopup = open.getBooleanAttribute("popup");
+ }
+ if (alwaysAsPopup) {
+ if (open.hasAttribute("border")) {
+ if (open.getStringAttribute("border").equals("minimal")) {
+ options = "menubar=yes,location=no,status=no";
+ } else {
+ options = "menubar=no,location=no,status=no";
+ }
+
} else {
- options = "menubar=no,location=no,status=no";
+ options = "resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes";
}
- } else {
- options = "resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes";
- }
+ if (open.hasAttribute("width")) {
+ int w = open.getIntAttribute("width");
+ options += ",width=" + w;
+ }
+ if (open.hasAttribute("height")) {
+ int h = open.getIntAttribute("height");
+ options += ",height=" + h;
+ }
- if (open.hasAttribute("width")) {
- int w = open.getIntAttribute("width");
- options += ",width=" + w;
- }
- if (open.hasAttribute("height")) {
- int h = open.getIntAttribute("height");
- options += ",height=" + h;
+ Window.open(url, target, options);
+ } else {
+ open(url, target);
}
-
- Window.open(url, target, options);
}
childIndex++;
}
diff --git a/server/src/com/vaadin/server/Page.java b/server/src/com/vaadin/server/Page.java
index 18120ef347..8737b478c3 100644
--- a/server/src/com/vaadin/server/Page.java
+++ b/server/src/com/vaadin/server/Page.java
@@ -132,6 +132,8 @@ public class Page implements Serializable {
*/
private final BorderStyle border;
+ private final boolean tryToOpenAsPopup;
+
/**
* Creates a new open resource.
*
@@ -145,10 +147,13 @@ public class Page implements Serializable {
* The height of the target window
* @param border
* The border style of the target window
+ * @param tryToOpenAsPopup
+ * Should try to open as a pop-up
*/
private OpenResource(String url, String name, int width, int height,
- BorderStyle border) {
- this(new ExternalResource(url), name, width, height, border);
+ BorderStyle border, boolean tryToOpenAsPopup) {
+ this(new ExternalResource(url), name, width, height, border,
+ tryToOpenAsPopup);
}
/**
@@ -164,14 +169,17 @@ public class Page implements Serializable {
* The height of the target window
* @param border
* The border style of the target window
+ * @param tryToOpenAsPopup
+ * Should try to open as a pop-up
*/
private OpenResource(Resource resource, String name, int width,
- int height, BorderStyle border) {
+ int height, BorderStyle border, boolean tryToOpenAsPopup) {
this.resource = resource;
this.name = name;
this.width = width;
this.height = height;
this.border = border;
+ this.tryToOpenAsPopup = tryToOpenAsPopup;
}
/**
@@ -188,6 +196,9 @@ public class Page implements Serializable {
if (name != null && name.length() > 0) {
target.addAttribute("name", name);
}
+ if (!tryToOpenAsPopup) {
+ target.addAttribute("popup", tryToOpenAsPopup);
+ }
if (width >= 0) {
target.addAttribute("width", width);
}
@@ -636,7 +647,7 @@ public class Page implements Serializable {
* the URI to show
*/
public void setLocation(String uri) {
- openList.add(new OpenResource(uri, null, -1, -1, BORDER_DEFAULT));
+ openList.add(new OpenResource(uri, null, -1, -1, BORDER_DEFAULT, false));
uI.markAsDirty();
}
@@ -681,7 +692,8 @@ public class Page implements Serializable {
}
/**
- * Opens the given URL in a window with the given name.
+ * Opens the given url in a window with the given name. Equivalent to
+ * {@link #open(String, String, boolean) open} (url, windowName, true) .
* <p>
* The supplied {@code windowName} is used as the target name in a
* window.open call in the client. This means that special values such as
@@ -717,7 +729,7 @@ public class Page implements Serializable {
* browser's popup-blocker because the new browser window is opened when
* processing a response from the server. To avoid this, you should instead
* use {@link Link} for opening the window because browsers are more
- * forgiving then the window is opened directly from a client-side click
+ * forgiving when the window is opened directly from a client-side click
* event.
* </p>
*
@@ -727,7 +739,62 @@ public class Page implements Serializable {
* the name of the window.
*/
public void open(String url, String windowName) {
- openList.add(new OpenResource(url, windowName, -1, -1, BORDER_DEFAULT));
+ open(url, windowName, true);
+ }
+
+ /**
+ * Opens the given url in a window with the given name. Equivalent to
+ * {@link #open(String, String, boolean) open} (url, windowName, true) .
+ * <p>
+ * The supplied {@code windowName} is used as the target name in a
+ * window.open call in the client. This means that special values such as
+ * "_blank", "_self", "_top", "_parent" have special meaning. An empty or
+ * <code>null</code> window name is also a special case.
+ * </p>
+ * <p>
+ * "", null and "_self" as {@code windowName} all causes the URL to be
+ * opened in the current window, replacing any old contents. For
+ * downloadable content you should avoid "_self" as "_self" causes the
+ * client to skip rendering of any other changes as it considers them
+ * irrelevant (the page will be replaced by the response from the URL). This
+ * can speed up the opening of a URL, but it might also put the client side
+ * into an inconsistent state if the window content is not completely
+ * replaced e.g., if the URL is downloaded instead of displayed in the
+ * browser.
+ * </p>
+ * <p>
+ * "_blank" as {@code windowName} causes the URL to always be opened in a
+ * new window or tab (depends on the browser and browser settings).
+ * </p>
+ * <p>
+ * "_top" and "_parent" as {@code windowName} works as specified by the HTML
+ * standard.
+ * </p>
+ * <p>
+ * Any other {@code windowName} will open the URL in a window with that
+ * name, either by opening a new window/tab in the browser or by replacing
+ * the contents of an existing window with that name.
+ * </p>
+ * <p>
+ * Please note that opening a popup window in this way may be blocked by the
+ * browser's popup-blocker because the new browser window is opened when
+ * processing a response from the server. To avoid this, you should instead
+ * use {@link Link} for opening the window because browsers are more
+ * forgiving when the window is opened directly from a client-side click
+ * event.
+ * </p>
+ *
+ * @param url
+ * the URL to open.
+ * @param windowName
+ * the name of the window.
+ * @param tryToOpenAsPopup
+ * Whether to try to force the resource to be opened in a new
+ * window
+ */
+ public void open(String url, String windowName, boolean tryToOpenAsPopup) {
+ openList.add(new OpenResource(url, windowName, -1, -1, BORDER_DEFAULT,
+ tryToOpenAsPopup));
uI.markAsDirty();
}
@@ -740,7 +807,7 @@ public class Page implements Serializable {
* browser's popup-blocker because the new browser window is opened when
* processing a response from the server. To avoid this, you should instead
* use {@link Link} for opening the window because browsers are more
- * forgiving then the window is opened directly from a client-side click
+ * forgiving when the window is opened directly from a client-side click
* event.
* </p>
*
@@ -757,7 +824,8 @@ public class Page implements Serializable {
*/
public void open(String url, String windowName, int width, int height,
BorderStyle border) {
- openList.add(new OpenResource(url, windowName, width, height, border));
+ openList.add(new OpenResource(url, windowName, width, height, border,
+ true));
uI.markAsDirty();
}
@@ -771,7 +839,21 @@ public class Page implements Serializable {
public void open(Resource resource, String windowName, int width,
int height, BorderStyle border) {
openList.add(new OpenResource(resource, windowName, width, height,
- border));
+ border, true));
+ uI.markAsDirty();
+ }
+
+ /**
+ * @deprecated As of 7.0, only retained to maintain compatibility with
+ * LegacyWindow.open methods. See documentation for
+ * {@link LegacyWindow#open(Resource, String, boolean)} for
+ * discussion about replacing API.
+ */
+ @Deprecated
+ public void open(Resource resource, String windowName,
+ boolean tryToOpenAsPopup) {
+ openList.add(new OpenResource(resource, windowName, -1, -1,
+ BORDER_DEFAULT, tryToOpenAsPopup));
uI.markAsDirty();
}
diff --git a/server/src/com/vaadin/ui/LegacyWindow.java b/server/src/com/vaadin/ui/LegacyWindow.java
index 359f258c8d..1b66b608c1 100644
--- a/server/src/com/vaadin/ui/LegacyWindow.java
+++ b/server/src/com/vaadin/ui/LegacyWindow.java
@@ -19,7 +19,6 @@ import java.net.MalformedURLException;
import java.net.URL;
import com.vaadin.server.LegacyApplication;
-import com.vaadin.server.Page;
import com.vaadin.server.Page.BrowserWindowResizeEvent;
import com.vaadin.server.Page.BrowserWindowResizeListener;
import com.vaadin.server.Resource;
@@ -169,7 +168,7 @@ public class LegacyWindow extends UI {
*/
@Deprecated
public void open(Resource resource) {
- open(resource, null);
+ open(resource, null, false);
}
/* ********************************************************************* */
@@ -221,7 +220,68 @@ public class LegacyWindow extends UI {
*/
@Deprecated
public void open(Resource resource, String windowName) {
- open(resource, windowName, -1, -1, Page.BORDER_DEFAULT);
+ open(resource, windowName, true);
+ }
+
+ /**
+ * Opens the given resource in a window with the given name and optionally
+ * tries to force the resource to open in a new window instead of a new tab.
+ * <p>
+ * The supplied {@code windowName} is used as the target name in a
+ * window.open call in the client. This means that special values such as
+ * "_blank", "_self", "_top", "_parent" have special meaning. An empty or
+ * <code>null</code> window name is also a special case.
+ * </p>
+ * <p>
+ * "", null and "_self" as {@code windowName} all causes the resource to be
+ * opened in the current window, replacing any old contents. For
+ * downloadable content you should avoid "_self" as "_self" causes the
+ * client to skip rendering of any other changes as it considers them
+ * irrelevant (the page will be replaced by the resource). This can speed up
+ * the opening of a resource, but it might also put the client side into an
+ * inconsistent state if the window content is not completely replaced e.g.,
+ * if the resource is downloaded instead of displayed in the browser.
+ * </p>
+ * <p>
+ * "_blank" as {@code windowName} causes the resource to always be opened in
+ * a new window or tab (depends on the browser and browser settings).
+ * </p>
+ * <p>
+ * "_top" and "_parent" as {@code windowName} works as specified by the HTML
+ * standard.
+ * </p>
+ * <p>
+ * Any other {@code windowName} will open the resource in a window with that
+ * name, either by opening a new window/tab in the browser or by replacing
+ * the contents of an existing window with that name.
+ * </p>
+ * <p>
+ * If {@code windowName} is set to open the resource in a new window or tab
+ * and {@code tryToOpenAsPopup} is true, this method attempts to force the
+ * browser to open a new window instead of a tab. NOTE: This is a
+ * best-effort attempt and may not work reliably with all browsers and
+ * different pop-up preferences. With most browsers using default settings,
+ * {@code tryToOpenAsPopup} works properly.
+ * </p>
+ * <p>
+ * As of Vaadin 7.0.0, the functionality for opening a Resource in a Page
+ * has been replaced with similar methods based on a String URL. This is
+ * because the usage of Resource is problematic with memory management and
+ * with security features in some browsers. Is is recommended to instead use
+ * {@link Link} for starting downloads.
+ * </p>
+ *
+ * @param resource
+ * the resource.
+ * @param windowName
+ * the name of the window.
+ * @param tryToOpenAsPopup
+ * Whether to try to force the resource to be opened in a new
+ * window
+ * */
+ public void open(Resource resource, String windowName,
+ boolean tryToOpenAsPopup) {
+ getPage().open(resource, windowName, tryToOpenAsPopup);
}
/**
diff --git a/uitest/src/com/vaadin/tests/components/window/LegacyWindowOpenTest.java b/uitest/src/com/vaadin/tests/components/window/LegacyWindowOpenTest.java
new file mode 100644
index 0000000000..175c3f6d8a
--- /dev/null
+++ b/uitest/src/com/vaadin/tests/components/window/LegacyWindowOpenTest.java
@@ -0,0 +1,74 @@
+package com.vaadin.tests.components.window;
+
+import com.vaadin.server.ExternalResource;
+import com.vaadin.tests.TestForWindowOpen;
+import com.vaadin.tests.components.TestBase;
+import com.vaadin.ui.Button;
+import com.vaadin.ui.Button.ClickEvent;
+import com.vaadin.ui.LegacyWindow;
+
+public class LegacyWindowOpenTest extends TestBase {
+
+ final ExternalResource r = new ExternalResource("http://www.google.com");
+
+ @Override
+ protected void setup() {
+ final LegacyWindow win = getMainWindow();
+
+ addComponent(new TestForWindowOpen());
+
+ addComponent(new Button("Window.open _blank always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.open(r, "_blank", true);
+ }
+ }));
+
+ addComponent(new Button("Window.open _blank NOT always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.open(r, "_blank", false);
+ }
+ }));
+
+ addComponent(new Button("Window.open _new always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.open(r, "_new", true);
+ }
+ }));
+
+ addComponent(new Button("Window.open _new NOT always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.open(r, "_new", false);
+ }
+ }));
+ addComponent(new Button(
+ "Window execute Javascript window.open(www.google.com, _blank)",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.executeJavaScript("window.open(\"http://www.google.com\", \"_blank\");");
+ }
+ }));
+ addComponent(new Button(
+ "Window execute Javascript window.open(www.google.com, _blank, resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes)",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ win.executeJavaScript("window.open(\"http://www.google.com\", \"_blank\", \"resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes\");");
+ }
+ }));
+
+ }
+
+ @Override
+ protected String getDescription() {
+ return "Windows never opened to a new tab";
+ }
+
+ @Override
+ protected Integer getTicketNumber() {
+ return 7842;
+ }
+
+}
diff --git a/uitest/src/com/vaadin/tests/components/window/PageOpenTest.java b/uitest/src/com/vaadin/tests/components/window/PageOpenTest.java
new file mode 100644
index 0000000000..2dbc24cb66
--- /dev/null
+++ b/uitest/src/com/vaadin/tests/components/window/PageOpenTest.java
@@ -0,0 +1,81 @@
+package com.vaadin.tests.components.window;
+
+import com.vaadin.server.Page;
+import com.vaadin.server.VaadinRequest;
+import com.vaadin.tests.TestForWindowOpen;
+import com.vaadin.tests.components.AbstractTestUI;
+import com.vaadin.ui.Button;
+import com.vaadin.ui.Button.ClickEvent;
+import com.vaadin.ui.JavaScript;
+
+public class PageOpenTest extends AbstractTestUI {
+
+ final String url = "http://www.google.com";
+
+ @Override
+ protected void setup(VaadinRequest request) {
+ final Page page = getPage();
+
+ addComponent(new TestForWindowOpen());
+
+ addComponent(new Button("Page.open _blank always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ page.open(url, "_blank", true);
+ }
+ }));
+
+ addComponent(new Button("Page.open _blank NOT always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ page.open(url, "_blank", false);
+ }
+ }));
+
+ addComponent(new Button("Page.open _new always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ page.open(url, "_new", true);
+ }
+ }));
+
+ addComponent(new Button("Page.open _new NOT always as popup",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ page.open(url, "_new", false);
+ }
+ }));
+ addComponent(new Button(
+ "Execute Javascript window.open(www.google.com, _blank)",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ JavaScript
+ .getCurrent()
+ .execute(
+ "window.open(\"http://www.google.com\", \"_blank\");");
+ }
+ }));
+ addComponent(new Button(
+ "Execute Javascript window.open(www.google.com, _blank, resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes)",
+ new Button.ClickListener() {
+ public void buttonClick(ClickEvent event) {
+ JavaScript
+ .getCurrent()
+ .execute(
+ "window.open(\"http://www.google.com\", \"_blank\", \"resizable=yes,menubar=yes,toolbar=yes,directories=yes,location=yes,scrollbars=yes,status=yes\");");
+ }
+ }));
+
+ }
+
+ @Override
+ protected String getTestDescription() {
+ return "Windows never opened to a new tab";
+ }
+
+ @Override
+ protected Integer getTicketNumber() {
+ return 7842;
+ }
+
+}