aboutsummaryrefslogtreecommitdiffstats
path: root/server
diff options
context:
space:
mode:
authorAhmed Ashour <asashour@yahoo.com>2017-09-27 12:44:01 +0200
committerHenri Sara <henri.sara@gmail.com>2017-09-27 13:44:01 +0300
commit9f9efe0058397992fda43e104c90b79039d41c0f (patch)
tree6903fb464d96fb1f8f6a4e92c1308833388fd210 /server
parent94c57dea3848635e0ae42fae464e23301f9e7c2c (diff)
downloadvaadin-framework-9f9efe0058397992fda43e104c90b79039d41c0f.tar.gz
vaadin-framework-9f9efe0058397992fda43e104c90b79039d41c0f.zip
Support addCloseListener for Notification (#10027)
Converts Notification to an Extension and adds support for listening to the closing of notifications. Fixes #888
Diffstat (limited to 'server')
-rw-r--r--server/src/main/java/com/vaadin/server/Page.java74
-rw-r--r--server/src/main/java/com/vaadin/server/PaintTarget.java20
-rw-r--r--server/src/main/java/com/vaadin/ui/Notification.java201
-rw-r--r--server/src/main/java/com/vaadin/ui/Window.java2
4 files changed, 173 insertions, 124 deletions
diff --git a/server/src/main/java/com/vaadin/server/Page.java b/server/src/main/java/com/vaadin/server/Page.java
index 3e95de0c4b..d458839e4c 100644
--- a/server/src/main/java/com/vaadin/server/Page.java
+++ b/server/src/main/java/com/vaadin/server/Page.java
@@ -311,12 +311,6 @@ public class Page implements Serializable {
private final LinkedList<OpenResource> openList = new LinkedList<>();
/**
- * A list of notifications that are waiting to be sent to the client.
- * Cleared (set to null) when the notifications have been sent.
- */
- private List<Notification> notifications;
-
- /**
* Event fired when the URI fragment of a <code>Page</code> changes.
*
* @see Page#addUriFragmentChangedListener(UriFragmentChangedListener)
@@ -937,45 +931,6 @@ public class Page implements Serializable {
openList.clear();
}
- // Paint notifications
- if (notifications != null) {
- target.startTag("notifications");
- for (final Notification n : notifications) {
- target.startTag("notification");
- if (n.getCaption() != null) {
- target.addAttribute(
- UIConstants.ATTRIBUTE_NOTIFICATION_CAPTION,
- n.getCaption());
- }
- if (n.getDescription() != null) {
- target.addAttribute(
- UIConstants.ATTRIBUTE_NOTIFICATION_MESSAGE,
- n.getDescription());
- }
- if (n.getIcon() != null) {
- target.addAttribute(UIConstants.ATTRIBUTE_NOTIFICATION_ICON,
- n.getIcon());
- }
- if (!n.isHtmlContentAllowed()) {
- target.addAttribute(
- UIConstants.NOTIFICATION_HTML_CONTENT_NOT_ALLOWED,
- true);
- }
- target.addAttribute(UIConstants.ATTRIBUTE_NOTIFICATION_POSITION,
- n.getPosition().ordinal());
- target.addAttribute(UIConstants.ATTRIBUTE_NOTIFICATION_DELAY,
- n.getDelayMsec());
- if (n.getStyleName() != null) {
- target.addAttribute(
- UIConstants.ATTRIBUTE_NOTIFICATION_STYLE,
- n.getStyleName());
- }
- target.endTag("notification");
- }
- target.endTag("notifications");
- notifications = null;
- }
-
if (newPushState != null) {
target.addAttribute(UIConstants.ATTRIBUTE_PUSH_STATE, newPushState);
newPushState = null;
@@ -1342,20 +1297,6 @@ public class Page implements Serializable {
}
/**
- * Internal helper method to actually add a notification.
- *
- * @param notification
- * the notification to add
- */
- private void addNotification(Notification notification) {
- if (notifications == null) {
- notifications = new LinkedList<>();
- }
- notifications.add(notification);
- uI.markAsDirty();
- }
-
- /**
* Shows a notification message.
*
* @see Notification
@@ -1367,7 +1308,7 @@ public class Page implements Serializable {
*/
@Deprecated
public void showNotification(Notification notification) {
- addNotification(notification);
+ notification.show(this);
}
/**
@@ -1469,11 +1410,22 @@ public class Page implements Serializable {
* @since 8.1
*/
public Collection<Dependency> getPendingDependencies() {
- ArrayList<Dependency> copy = new ArrayList<>();
+ List<Dependency> copy = new ArrayList<>();
if (pendingDependencies != null) {
copy.addAll(pendingDependencies);
}
pendingDependencies = null;
return copy;
}
+
+ /**
+ * Returns the {@link UI} of this {@link Page}.
+ *
+ * @return the {@link UI} of this {@link Page}.
+ *
+ * @since
+ */
+ public UI getUI() {
+ return uI;
+ }
}
diff --git a/server/src/main/java/com/vaadin/server/PaintTarget.java b/server/src/main/java/com/vaadin/server/PaintTarget.java
index 6d531abc2c..0719fb26aa 100644
--- a/server/src/main/java/com/vaadin/server/PaintTarget.java
+++ b/server/src/main/java/com/vaadin/server/PaintTarget.java
@@ -39,7 +39,7 @@ public interface PaintTarget extends Serializable {
* @param sectionTagName
* the name of the tag.
* @param sectionData
- * the scetion data.
+ * the section data.
* @throws PaintException
* if the paint operation failed.
*/
@@ -145,7 +145,7 @@ public interface PaintTarget extends Serializable {
public void endTag(String tagName) throws PaintException;
/**
- * Adds a boolean attribute to component. Atributes must be added before any
+ * Adds a boolean attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -159,7 +159,7 @@ public interface PaintTarget extends Serializable {
public void addAttribute(String name, boolean value) throws PaintException;
/**
- * Adds a integer attribute to component. Atributes must be added before any
+ * Adds a integer attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -173,7 +173,7 @@ public interface PaintTarget extends Serializable {
public void addAttribute(String name, int value) throws PaintException;
/**
- * Adds a resource attribute to component. Atributes must be added before
+ * Adds a resource attribute to component. Attributes must be added before
* any content is written.
*
* @param name
@@ -222,7 +222,7 @@ public interface PaintTarget extends Serializable {
StreamVariable value) throws PaintException;
/**
- * Adds a long attribute to component. Atributes must be added before any
+ * Adds a long attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -236,7 +236,7 @@ public interface PaintTarget extends Serializable {
public void addAttribute(String name, long value) throws PaintException;
/**
- * Adds a float attribute to component. Atributes must be added before any
+ * Adds a float attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -250,7 +250,7 @@ public interface PaintTarget extends Serializable {
public void addAttribute(String name, float value) throws PaintException;
/**
- * Adds a double attribute to component. Atributes must be added before any
+ * Adds a double attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -264,7 +264,7 @@ public interface PaintTarget extends Serializable {
public void addAttribute(String name, double value) throws PaintException;
/**
- * Adds a string attribute to component. Atributes must be added before any
+ * Adds a string attribute to component. Attributes must be added before any
* content is written.
*
* @param name
@@ -318,7 +318,7 @@ public interface PaintTarget extends Serializable {
throws PaintException;
/**
- * Adds a int type variable.
+ * Adds an int type variable.
*
* @param owner
* the Listener for variable changes.
@@ -434,7 +434,7 @@ public interface PaintTarget extends Serializable {
throws PaintException;
/**
- * Adds a upload stream type variable.
+ * Adds an upload stream type variable.
*
* @param owner
* the Listener for variable changes.
diff --git a/server/src/main/java/com/vaadin/ui/Notification.java b/server/src/main/java/com/vaadin/ui/Notification.java
index 9ec031799f..15637ef3b0 100644
--- a/server/src/main/java/com/vaadin/ui/Notification.java
+++ b/server/src/main/java/com/vaadin/ui/Notification.java
@@ -17,10 +17,17 @@
package com.vaadin.ui;
import java.io.Serializable;
+import java.lang.reflect.Method;
+import com.vaadin.event.ConnectorEvent;
+import com.vaadin.server.AbstractExtension;
import com.vaadin.server.Page;
import com.vaadin.server.Resource;
+import com.vaadin.server.ResourceReference;
import com.vaadin.shared.Position;
+import com.vaadin.shared.Registration;
+import com.vaadin.shared.ui.notification.NotificationServerRpc;
+import com.vaadin.shared.ui.notification.NotificationState;
/**
* A notification message, used to display temporary messages to the user - for
@@ -61,7 +68,15 @@ import com.vaadin.shared.Position;
* </p>
*
*/
-public class Notification implements Serializable {
+public class Notification extends AbstractExtension implements Serializable {
+
+ /**
+ * The server RPC.
+ */
+ protected NotificationServerRpc rpc = () -> {
+ fireEvent(new CloseEvent(Notification.this));
+ };
+
public enum Type {
HUMANIZED_MESSAGE("humanized"), WARNING_MESSAGE(
"warning"), ERROR_MESSAGE("error"), TRAY_NOTIFICATION("tray"),
@@ -113,14 +128,6 @@ public class Notification implements Serializable {
public static final int DELAY_FOREVER = -1;
public static final int DELAY_NONE = 0;
- private String caption;
- private String description;
- private Resource icon;
- private Position position = Position.MIDDLE_CENTER;
- private int delayMsec = 0;
- private String styleName;
- private boolean htmlContentAllowed;
-
/**
* Creates a "humanized" notification message.
*
@@ -199,28 +206,29 @@ public class Notification implements Serializable {
*/
public Notification(String caption, String description, Type type,
boolean htmlContentAllowed) {
- this.caption = caption;
- this.description = description;
- this.htmlContentAllowed = htmlContentAllowed;
+ registerRpc(rpc);
+ setCaption(caption);
+ setDescription(description);
+ setHtmlContentAllowed(htmlContentAllowed);
setType(type);
}
private void setType(Type type) {
- styleName = type.getStyle();
+ setStyleName(type.getStyle());
switch (type) {
case WARNING_MESSAGE:
- delayMsec = 1500;
+ setDelayMsec(1500);
break;
case ERROR_MESSAGE:
- delayMsec = -1;
+ setDelayMsec(DELAY_FOREVER);
break;
case TRAY_NOTIFICATION:
- delayMsec = 3000;
- position = Position.BOTTOM_RIGHT;
+ setDelayMsec(3000);
+ setPosition(Position.BOTTOM_RIGHT);
break;
case ASSISTIVE_NOTIFICATION:
- delayMsec = 3000;
- position = Position.ASSISTIVE;
+ setDelayMsec(3000);
+ setPosition(Position.ASSISTIVE);
break;
case HUMANIZED_MESSAGE:
default:
@@ -234,35 +242,36 @@ public class Notification implements Serializable {
* @return The message caption
*/
public String getCaption() {
- return caption;
+ return getState(false).caption;
}
/**
- * Sets the caption part of the notification message
+ * Sets the caption part of the notification message.
*
* @param caption
* The message caption
*/
public void setCaption(String caption) {
- this.caption = caption;
+ getState().caption = caption;
}
/**
* Gets the description part of the notification message.
*
- * @return The message description.
+ * @return The message description
*/
public String getDescription() {
- return description;
+ return getState(false).description;
}
/**
* Sets the description part of the notification message.
*
* @param description
+ * The message description
*/
public void setDescription(String description) {
- this.description = description;
+ getState().description = description;
}
/**
@@ -271,17 +280,21 @@ public class Notification implements Serializable {
* @return The position
*/
public Position getPosition() {
- return position;
+ return getState(false).position;
}
/**
* Sets the position of the notification message.
*
* @param position
- * The desired notification position
+ * The desired notification position,
+ * not {@code null}
*/
public void setPosition(Position position) {
- this.position = position;
+ if (position == null) {
+ throw new IllegalArgumentException("Position can not be null");
+ }
+ getState().position = position;
}
/**
@@ -290,7 +303,7 @@ public class Notification implements Serializable {
* @return The message icon
*/
public Resource getIcon() {
- return icon;
+ return getResource("icon");
}
/**
@@ -300,46 +313,47 @@ public class Notification implements Serializable {
* The desired message icon
*/
public void setIcon(Resource icon) {
- this.icon = icon;
+ setResource("icon", icon);
}
/**
* Gets the delay before the notification disappears.
*
- * @return the delay in msec, -1 indicates the message has to be clicked.
+ * @return the delay in milliseconds, {@value #DELAY_FOREVER}
+ * indicates the message has to be clicked.
*/
public int getDelayMsec() {
- return delayMsec;
+ return getState(false).delay;
}
/**
* Sets the delay before the notification disappears.
*
* @param delayMsec
- * the desired delay in msec, -1 to require the user to click the
- * message
+ * the desired delay in milliseconds, {@value #DELAY_FOREVER}
+ * to require the user to click the message
*/
public void setDelayMsec(int delayMsec) {
- this.delayMsec = delayMsec;
+ getState().delay = delayMsec;
}
/**
* Sets the style name for the notification message.
*
* @param styleName
- * The desired style name.
+ * The desired style name
*/
public void setStyleName(String styleName) {
- this.styleName = styleName;
+ getState().styleName = styleName;
}
/**
* Gets the style name for the notification message.
*
- * @return
+ * @return The style name
*/
public String getStyleName() {
- return styleName;
+ return getState(false).styleName;
}
/**
@@ -353,18 +367,19 @@ public class Notification implements Serializable {
* text
*/
public void setHtmlContentAllowed(boolean htmlContentAllowed) {
- this.htmlContentAllowed = htmlContentAllowed;
+ getState().htmlContentAllowed = htmlContentAllowed;
}
/**
- * Checks whether caption and description are interpreted as html or plain
+ * Checks whether caption and description are interpreted as HTML or plain
* text.
*
- * @return true if the texts are used as html, false if used as plain text
+ * @return {@code true} if the texts are used as HTML,
+ * {@code false} if used as plain text
* @see #setHtmlContentAllowed(boolean)
*/
public boolean isHtmlContentAllowed() {
- return htmlContentAllowed;
+ return getState(false).htmlContentAllowed;
}
/**
@@ -374,8 +389,17 @@ public class Notification implements Serializable {
* The page on which the notification should be shown
*/
public void show(Page page) {
- // TODO Can avoid deprecated API when Notification extends Extension
- page.showNotification(this);
+ extend(page.getUI());
+ }
+
+ @Override
+ protected NotificationState getState() {
+ return (NotificationState) super.getState();
+ }
+
+ @Override
+ protected NotificationState getState(boolean markAsDirty) {
+ return (NotificationState) super.getState(markAsDirty);
}
/**
@@ -389,16 +413,20 @@ public class Notification implements Serializable {
*
* @param caption
* The message
+ * @return
+ * The Notification
*/
- public static void show(String caption) {
- new Notification(caption).show(Page.getCurrent());
+ public static Notification show(String caption) {
+ Notification notification = new Notification(caption);
+ notification.extend(UI.getCurrent());
+ return notification;
}
/**
* Shows a notification message the current page. The position and behavior
* of the message depends on the type, which is one of the basic types
* defined in {@link Notification}, for instance
- * Notification.TYPE_WARNING_MESSAGE.
+ * {@link Type#WARNING_MESSAGE}.
*
* The caption is rendered as plain text with HTML automatically escaped.
*
@@ -409,9 +437,13 @@ public class Notification implements Serializable {
* The message
* @param type
* The message type
+ * @return
+ * The Notification
*/
- public static void show(String caption, Type type) {
- new Notification(caption, type).show(Page.getCurrent());
+ public static Notification show(String caption, Type type) {
+ Notification notification = new Notification(caption, type);
+ notification.extend(UI.getCurrent());
+ return notification;
}
/**
@@ -431,8 +463,73 @@ public class Notification implements Serializable {
* The message description
* @param type
* The message type
+ * @return
+ * The Notification
*/
- public static void show(String caption, String description, Type type) {
- new Notification(caption, description, type).show(Page.getCurrent());
+ public static Notification show(String caption, String description, Type type) {
+ Notification notification = new Notification(caption, description, type);
+ notification.extend(UI.getCurrent());
+ return notification;
}
+
+ /**
+ * Adds a CloseListener to the Notification.
+ *
+ * @param listener
+ * the CloseListener to add, not {@code null}
+ * @since
+ */
+ public Registration addCloseListener(CloseListener listener) {
+ return addListener(CloseEvent.class, listener, CLOSE_METHOD);
+ }
+
+ private static final Method CLOSE_METHOD;
+ static {
+ try {
+ CLOSE_METHOD = CloseListener.class
+ .getDeclaredMethod("notificationClose", CloseEvent.class);
+ } catch (final NoSuchMethodException e) {
+ // This should never happen
+ throw new RuntimeException(
+ "Internal error, notification close method not found");
+ }
+ }
+
+ public static class CloseEvent extends ConnectorEvent {
+
+ /**
+ * @param source
+ */
+ public CloseEvent(Notification source) {
+ super(source);
+ }
+
+ /**
+ * Gets the Notification.
+ *
+ * @return The Notification
+ */
+ public Notification getNotification() {
+ return (Notification) getSource();
+ }
+ }
+
+ /**
+ * An interface used for listening to Notification close events. Add the
+ * CloseListener to a Notification and
+ * {@link CloseListener#notificationClose(CloseEvent)} will be called whenever the
+ * Notification is closed.
+ */
+ @FunctionalInterface
+ public interface CloseListener extends Serializable {
+ /**
+ * Use {@link CloseEvent#getNotification()} to get a reference to the
+ * {@link Notification} that was closed.
+ *
+ * @param e
+ * The triggered event
+ */
+ public void notificationClose(CloseEvent e);
+ }
+
}
diff --git a/server/src/main/java/com/vaadin/ui/Window.java b/server/src/main/java/com/vaadin/ui/Window.java
index 5a9b19f421..cd0840e517 100644
--- a/server/src/main/java/com/vaadin/ui/Window.java
+++ b/server/src/main/java/com/vaadin/ui/Window.java
@@ -504,7 +504,7 @@ public class Window extends Panel
* {@link Window} that was closed.
*
* @param e
- * Event containing
+ * The triggered event
*/
public void windowClose(CloseEvent e);
}