001/*
002 * The contents of this file are subject to the terms of the Common Development and
003 * Distribution License (the License). You may not use this file except in compliance with the
004 * License.
005 *
006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
007 * specific language governing permission and limitations under the License.
008 *
009 * When distributing Covered Software, include this CDDL Header Notice in each file and include
010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
011 * Header, with the fields enclosed by brackets [] replaced by your own identifying
012 * information: "Portions Copyright [year] [name of copyright owner]".
013 *
014 * Copyright 2008-2009 Sun Microsystems, Inc.
015 * Portions Copyright 2014-2016 ForgeRock AS.
016 */
017
018package org.opends.guitools.controlpanel.ui;
019
020import static org.opends.messages.AdminToolMessages.*;
021
022import java.awt.Component;
023import java.awt.GridBagConstraints;
024import java.awt.GridBagLayout;
025import java.awt.Insets;
026import java.awt.event.ActionEvent;
027import java.awt.event.ActionListener;
028
029import javax.swing.BorderFactory;
030import javax.swing.Box;
031import javax.swing.JButton;
032import javax.swing.JPanel;
033
034import org.opends.guitools.controlpanel.datamodel.ControlPanelInfo;
035import org.opends.guitools.controlpanel.event.ConfigurationChangeEvent;
036import org.opends.guitools.controlpanel.util.Utilities;
037import org.forgerock.i18n.LocalizableMessage;
038
039/**
040 * Dialog used to inform the user that there are unsaved changes in a panel.
041 * It proposes the user to save the changes, do not save them or cancel the
042 * action that make the dialog appear (for instance when the user is editing
043 * an entry and clicks on another node, this dialog appears).
044 */
045public class UnsavedChangesDialog extends GenericDialog
046{
047  /** The different input that the user can provide. */
048  public enum Result
049  {
050    /** The user asks to save the changes. */
051    SAVE,
052    /** The user asks to not to save the changes. */
053    DO_NOT_SAVE,
054    /** The user asks to cancel the operation that made this dialog to appear. */
055    CANCEL
056  }
057  private static final long serialVersionUID = -4436794801035162388L;
058
059  /**
060   * Constructor of the dialog.
061   * @param parentDialog the parent dialog.
062   * @param info the control panel info.
063   */
064  public UnsavedChangesDialog(Component parentDialog,
065      ControlPanelInfo info)
066  {
067    super(Utilities.getFrame(parentDialog), getPanel(info));
068    Utilities.centerGoldenMean(this, parentDialog);
069    getRootPane().setDefaultButton(
070        ((UnsavedChangesPanel)panel).saveButton);
071    setModal(true);
072  }
073
074  /**
075   * Sets the message to be displayed in this dialog.
076   * @param title the title of the message.
077   * @param details the details of the message.
078   */
079  public void setMessage(LocalizableMessage title, LocalizableMessage details)
080  {
081    panel.updateConfirmationPane(panel.errorPane, title,
082        ColorAndFontConstants.errorTitleFont, details,
083        ColorAndFontConstants.defaultFont);
084    invalidate();
085    pack();
086  }
087
088  @Override
089  public void setVisible(boolean visible)
090  {
091    if (visible)
092    {
093      ((UnsavedChangesPanel)panel).result = Result.CANCEL;
094    }
095    super.setVisible(visible);
096  }
097
098  /**
099   * Returns the option the user gave when closing this dialog.
100   * @return the option the user gave when closing this dialog.
101   */
102  public Result getResult()
103  {
104    return ((UnsavedChangesPanel)panel).result;
105  }
106
107  /**
108   * Creates the panel to be displayed inside the dialog.
109   * @param info the control panel info.
110   * @return the panel to be displayed inside the dialog.
111   */
112  private static StatusGenericPanel getPanel(ControlPanelInfo info)
113  {
114    UnsavedChangesPanel panel = new UnsavedChangesPanel();
115    panel.setInfo(info);
116    return panel;
117  }
118
119  /** The panel to be displayed inside the dialog. */
120  private static class UnsavedChangesPanel extends StatusGenericPanel
121  {
122    private static final long serialVersionUID = -1528939816762604059L;
123
124    private JButton saveButton;
125    private JButton doNotSaveButton;
126    private JButton cancelButton;
127
128    private Result result;
129
130    /** Default constructor. */
131    public UnsavedChangesPanel()
132    {
133      super();
134      GridBagConstraints gbc = new GridBagConstraints();
135      gbc.gridx = 0;
136      gbc.gridy = 0;
137      gbc.gridwidth = 1;
138      addErrorPane(gbc);
139      errorPane.setVisible(true);
140      gbc.gridy ++;
141      gbc.fill = GridBagConstraints.VERTICAL;
142      gbc.weighty = 1.0;
143      add(Box.createVerticalGlue(), gbc);
144      gbc.fill = GridBagConstraints.HORIZONTAL;
145//    The button panel
146      gbc.gridy ++;
147      gbc.weighty = 0.0;
148      gbc.insets = new Insets(0, 0, 0, 0);
149      add(createButtonsPanel(), gbc);
150    }
151
152    @Override
153    public boolean requiresBorder()
154    {
155      return false;
156    }
157
158    @Override
159    public boolean requiresScroll()
160    {
161      return false;
162    }
163
164    private JPanel createButtonsPanel()
165    {
166      JPanel buttonsPanel = new JPanel(new GridBagLayout());
167      GridBagConstraints gbc = new GridBagConstraints();
168      gbc.gridx = 0;
169      gbc.gridy = 0;
170      gbc.anchor = GridBagConstraints.WEST;
171      gbc.fill = GridBagConstraints.HORIZONTAL;
172      gbc.gridwidth = 1;
173      gbc.gridy = 0;
174      doNotSaveButton =
175        Utilities.createButton(INFO_CTRL_PANEL_DO_NOT_SAVE_BUTTON_LABEL.get());
176      doNotSaveButton.setOpaque(false);
177      gbc.insets = new Insets(10, 10, 10, 10);
178      buttonsPanel.add(doNotSaveButton, gbc);
179      doNotSaveButton.addActionListener(new ActionListener()
180      {
181        @Override
182        public void actionPerformed(ActionEvent ev)
183        {
184          result = Result.DO_NOT_SAVE;
185          cancelClicked();
186        }
187      });
188      gbc.weightx = 1.0;
189      gbc.gridx ++;
190      buttonsPanel.add(Box.createHorizontalStrut(150));
191      buttonsPanel.add(Box.createHorizontalGlue(), gbc);
192      buttonsPanel.setOpaque(true);
193      buttonsPanel.setBackground(ColorAndFontConstants.greyBackground);
194      gbc.gridx ++;
195      gbc.weightx = 0.0;
196      buttonsPanel.add(Box.createHorizontalStrut(100));
197      gbc.gridx ++;
198      cancelButton = Utilities.createButton(
199          INFO_CTRL_PANEL_CANCEL_BUTTON_LABEL.get());
200      cancelButton.setOpaque(false);
201      gbc.insets.right = 0;
202      buttonsPanel.add(cancelButton, gbc);
203      cancelButton.addActionListener(new ActionListener()
204      {
205        @Override
206        public void actionPerformed(ActionEvent ev)
207        {
208          result = Result.CANCEL;
209          cancelClicked();
210        }
211      });
212      saveButton = Utilities.createButton(
213          INFO_CTRL_PANEL_SAVE_BUTTON_LABEL.get());
214      saveButton.setOpaque(false);
215      gbc.gridx ++;
216      gbc.insets.left = 5;
217      gbc.insets.right = 10;
218      buttonsPanel.add(saveButton, gbc);
219      saveButton.addActionListener(new ActionListener()
220      {
221        @Override
222        public void actionPerformed(ActionEvent ev)
223        {
224          result = Result.SAVE;
225          cancelClicked();
226        }
227      });
228
229      buttonsPanel.setBorder(BorderFactory.createMatteBorder(1, 0, 0, 0,
230          ColorAndFontConstants.defaultBorderColor));
231
232      return buttonsPanel;
233    }
234
235    @Override
236    public Component getPreferredFocusComponent()
237    {
238      return doNotSaveButton;
239    }
240
241    @Override
242    public void okClicked()
243    {
244    }
245
246    @Override
247    public LocalizableMessage getTitle()
248    {
249      return INFO_CTRL_PANEL_UNSAVED_CHANGES_DIALOG_TITLE.get();
250    }
251
252    @Override
253    public void configurationChanged(ConfigurationChangeEvent ev)
254    {
255    }
256
257    @Override
258    public GenericDialog.ButtonType getButtonType()
259    {
260      return GenericDialog.ButtonType.NO_BUTTON;
261    }
262
263    @Override
264    public boolean isDisposeOnClose()
265    {
266      return true;
267    }
268  }
269}