001// License: GPL. For details, see LICENSE file.
002package org.openstreetmap.josm.gui;
003
004import java.awt.Component;
005
006import javax.swing.Icon;
007import javax.swing.JOptionPane;
008import javax.swing.UIManager;
009
010import org.openstreetmap.josm.Main;
011import org.openstreetmap.josm.gui.widgets.JMultilineLabel;
012
013/**
014 * A Notification Message similar to a popup window, but without disrupting the
015 * user's workflow.
016 *
017 * Non-modal info panel that vanishes after a certain time.
018 *
019 * This class only holds the data for a notification, {@link NotificationManager}
020 * is responsible for building the message panel and displaying it on screen.
021 *
022 * example:
023 * <pre>
024 *      Notification note = new Notification("Hi there!");
025 *      note.setIcon(JOptionPane.INFORMATION_MESSAGE); // optional
026 *      note.setDuration(Notification.TIME_SHORT); // optional
027 *      note.show();
028 * </pre>
029 */
030public class Notification {
031
032    public static final int DEFAULT_CONTENT_WIDTH = 350;
033
034    // some standard duration values (in milliseconds)
035
036    /**
037     * Very short and very easy to grasp message (3 s).
038     * E.g. "Please select at least one node".
039     */
040    public static final int TIME_SHORT = Main.pref.getInteger("notification-time-short-ms", 3000);
041
042    /**
043     * Short message of one or two lines (5 s).
044     */
045    public static final int TIME_DEFAULT = Main.pref.getInteger("notification-time-default-ms", 5000);
046
047    /**
048     * Somewhat longer message (10 s).
049     */
050    public static final int TIME_LONG = Main.pref.getInteger("notification-time-long-ms", 10000);
051
052    /**
053     * Long text.
054     * (Make sure is still sensible to show as a notification)
055     */
056    public static final int TIME_VERY_LONG = Main.pref.getInteger("notification-time-very_long-ms", 20000);
057
058    private Component content;
059    private int duration;
060    private Icon icon;
061    private String helpTopic;
062
063    /**
064     * Constructs a new {@code Notification} without content.
065     */
066    public Notification() {
067        duration = NotificationManager.defaultNotificationTime;
068    }
069
070    /**
071     * Constructs a new {@code Notification} with the given textual content.
072     * @param msg The text to display
073     */
074    public Notification(String msg) {
075        this();
076        setContent(msg);
077    }
078
079    /**
080     * Set the content of the message.
081     *
082     * @param content any Component to be shown
083     *
084     * @see #setContent(java.lang.String)
085     * @return the current Object, for convenience
086     */
087    public Notification setContent(Component content) {
088        this.content = content;
089        return this;
090    }
091
092    /**
093     * Set the notification text. (Convenience method)
094     *
095     * @param msg the message String. Will be wrapped in &lt;html&gt;, so
096     * you can use &lt;br&gt; and other markup directly.
097     *
098     * @see #Notification(java.lang.String)
099     * @return the current Object, for convenience
100     */
101    public Notification setContent(String msg) {
102        JMultilineLabel lbl = new JMultilineLabel(msg);
103        lbl.setMaxWidth(DEFAULT_CONTENT_WIDTH);
104        content = lbl;
105        return this;
106    }
107
108    /**
109     * Set the time after which the message is hidden.
110     *
111     * @param duration the time (in milliseconds)
112     * Preset values {@link #TIME_SHORT}, {@link #TIME_DEFAULT}, {@link #TIME_LONG}
113     * and {@link #TIME_VERY_LONG} can be used.
114     * @return the current Object, for convenience
115     */
116    public Notification setDuration(int duration) {
117        this.duration = duration;
118        return this;
119    }
120
121    /**
122     * Set an icon to display on the left part of the message window.
123     *
124     * @param icon the icon (null means no icon is displayed)
125     * @return the current Object, for convenience
126     */
127    public Notification setIcon(Icon icon) {
128        this.icon = icon;
129        return this;
130    }
131
132    /**
133     * Set an icon to display on the left part of the message window by
134     * choosing from the default JOptionPane icons.
135     *
136     * @param messageType one of the following: JOptionPane.ERROR_MESSAGE,
137     * JOptionPane.INFORMATION_MESSAGE, JOptionPane.WARNING_MESSAGE,
138     * JOptionPane.QUESTION_MESSAGE, JOptionPane.PLAIN_MESSAGE
139     * @return the current Object, for convenience
140     */
141    public Notification setIcon(int messageType) {
142        switch (messageType) {
143            case JOptionPane.ERROR_MESSAGE:
144                return setIcon(UIManager.getIcon("OptionPane.errorIcon"));
145            case JOptionPane.INFORMATION_MESSAGE:
146                return setIcon(UIManager.getIcon("OptionPane.informationIcon"));
147            case JOptionPane.WARNING_MESSAGE:
148                return setIcon(UIManager.getIcon("OptionPane.warningIcon"));
149            case JOptionPane.QUESTION_MESSAGE:
150                return setIcon(UIManager.getIcon("OptionPane.questionIcon"));
151            case JOptionPane.PLAIN_MESSAGE:
152                return setIcon(null);
153            default:
154                throw new IllegalArgumentException("Unknown message type!");
155        }
156    }
157
158    /**
159     * Display a help button at the bottom of the notification window.
160     * @param helpTopic the help topic
161     * @return the current Object, for convenience
162     */
163    public Notification setHelpTopic(String helpTopic) {
164        this.helpTopic = helpTopic;
165        return this;
166    }
167
168    public Component getContent() {
169        return content;
170    }
171
172    public int getDuration() {
173        return duration;
174    }
175
176    public Icon getIcon() {
177        return icon;
178    }
179
180    public String getHelpTopic() {
181        return helpTopic;
182    }
183
184    /**
185     * Display the notification.
186     */
187    public void show() {
188        NotificationManager.getInstance().showNotification(this);
189    }
190}