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 2006-2009 Sun Microsystems, Inc. 015 * Portions Copyright 2013-2015 ForgeRock AS. 016 */ 017package org.opends.quicksetup.ui; 018 019import java.awt.Component; 020import java.awt.GridBagConstraints; 021import java.awt.GridBagLayout; 022import java.awt.event.ActionEvent; 023import java.awt.event.ActionListener; 024import java.awt.event.FocusEvent; 025import java.awt.event.FocusListener; 026 027import javax.swing.*; 028import javax.swing.event.HyperlinkEvent; 029import javax.swing.event.HyperlinkListener; 030 031import org.opends.quicksetup.ButtonName; 032import org.opends.quicksetup.ProgressStep; 033import org.opends.quicksetup.event.ButtonEvent; 034import org.opends.quicksetup.ProgressDescriptor; 035import org.forgerock.i18n.LocalizableMessage; 036import static org.opends.messages.QuickSetupMessages.*; 037 038/** 039 * This panel is used to show the progress of the application. 040 * 041 */ 042public class ProgressPanel extends QuickSetupStepPanel 043{ 044 private static final long serialVersionUID = 8129425068163357170L; 045 046 private JEditorPane progressBarLabel; 047 048 private JProgressBar progressBar; 049 050 private JButton btnCancel; 051 052 private JEditorPane detailsTextArea; 053 054 private LocalizableMessage lastText; 055 056 private Component lastFocusComponent; 057 058 /** 059 * ProgressPanel constructor. 060 * @param application Application this panel represents 061 */ 062 public ProgressPanel(GuiApplication application) 063 { 064 super(application); 065 } 066 067 /** {@inheritDoc} */ 068 protected Component createInputPanel() 069 { 070 JPanel panel = new JPanel(new GridBagLayout()); 071 panel.setOpaque(false); 072 073 GridBagConstraints gbc = new GridBagConstraints(); 074 075 gbc.insets = UIFactory.getEmptyInsets(); 076 gbc.anchor = GridBagConstraints.NORTHWEST; 077 gbc.gridwidth = GridBagConstraints.REMAINDER; 078 gbc.weightx = 1.0; 079 gbc.fill = GridBagConstraints.HORIZONTAL; 080 081 progressBarLabel = UIFactory.makeHtmlPane( 082 null, 083 UIFactory.PROGRESS_FONT); 084 progressBarLabel.setOpaque(false); 085 progressBarLabel.setEditable(false); 086 progressBarLabel.setFocusable(false); 087 progressBarLabel.setFocusCycleRoot(false); 088 CustomHTMLEditorKit htmlEditor = new CustomHTMLEditorKit(); 089 htmlEditor.addActionListener(new ActionListener() 090 { 091 public void actionPerformed(ActionEvent ev) 092 { 093 // Assume is the authentication button. 094 ButtonEvent be = new ButtonEvent(ev.getSource(), 095 ButtonName.LAUNCH_STATUS_PANEL); 096 notifyButtonListeners(be); 097 } 098 }); 099 progressBarLabel.setEditorKit(htmlEditor); 100 String summaryText = UIFactory.applyFontToHtml( 101 String.valueOf(INFO_PROGRESSBAR_INITIAL_LABEL.get()), 102 UIFactory.PROGRESS_FONT); 103 progressBarLabel.setText(summaryText); 104 progressBarLabel.addHyperlinkListener(this); 105 panel.add(progressBarLabel, gbc); 106 107 gbc.insets.top = UIFactory.TOP_INSET_PROGRESS_BAR; 108 gbc.insets.bottom = UIFactory.BOTTOM_INSET_PROGRESS_BAR; 109 panel.add(createProgressBarPanel(), gbc); 110 progressBar.setToolTipText(INFO_PROGRESSBAR_TOOLTIP.get().toString()); 111 112 JLabel l = 113 UIFactory.makeJLabel(UIFactory.IconType.NO_ICON, 114 INFO_PROGRESS_DETAILS_LABEL.get(), 115 UIFactory.TextStyle.SECONDARY_FIELD_VALID); 116 117 gbc.insets = UIFactory.getEmptyInsets(); 118 panel.add(l, gbc); 119 120 JScrollPane scroll = new JScrollPane(); 121 detailsTextArea = UIFactory.makeProgressPane(scroll); 122 detailsTextArea.setBackground( 123 UIFactory.CURRENT_STEP_PANEL_BACKGROUND); 124 detailsTextArea.addHyperlinkListener(new HyperlinkListener() 125 { 126 public void hyperlinkUpdate(HyperlinkEvent e) 127 { 128 if (e.getEventType() == HyperlinkEvent.EventType.ACTIVATED) 129 { 130 String url = e.getURL().toString(); 131 lastText = getFormatter().getFormattedAfterUrlClick(url, 132 lastText); 133 detailsTextArea.setText(lastText.toString()); 134 } 135 } 136 }); 137 detailsTextArea.setAutoscrolls(true); 138 scroll.setViewportView(detailsTextArea); 139 140 scroll.setBorder(UIFactory.TEXT_AREA_BORDER); 141 scroll.setWheelScrollingEnabled(true); 142 l.setLabelFor(detailsTextArea); 143 gbc.insets.top = UIFactory.TOP_INSET_PROGRESS_TEXTAREA; 144 gbc.fill = GridBagConstraints.BOTH; 145 gbc.weighty = 1.0; 146 panel.add(scroll, gbc); 147 148 addFocusListeners(); 149 150 return panel; 151 } 152 153 /** {@inheritDoc} */ 154 protected LocalizableMessage getInstructions() 155 { 156 return null; 157 } 158 159 /** {@inheritDoc} */ 160 protected LocalizableMessage getTitle() 161 { 162 return INFO_PROGRESS_PANEL_TITLE.get(); 163 } 164 165 /** {@inheritDoc} */ 166 protected boolean requiresScroll() 167 { 168 return false; 169 } 170 171 /** {@inheritDoc} */ 172 public void endDisplay() 173 { 174 if (lastFocusComponent != null) 175 { 176 lastFocusComponent.requestFocusInWindow(); 177 } 178 } 179 180 /** {@inheritDoc} */ 181 public void displayProgress(ProgressDescriptor descriptor) 182 { 183 ProgressStep status = descriptor.getProgressStep(); 184 String summaryText = UIFactory.applyFontToHtml( 185 String.valueOf(descriptor.getProgressBarMsg()), 186 UIFactory.PROGRESS_FONT); 187 188 if (status.isLast()) { 189 progressBar.setVisible(false); 190 progressBarLabel.setFocusable(true); 191 btnCancel.setVisible(false); 192 if (!status.isError()) { 193 summaryText = "<form>"+summaryText+"</form>"; 194 } 195 } 196 197 progressBarLabel.setText(summaryText); 198 199 Integer v = descriptor.getProgressBarRatio(); 200 if (v != null && v > 0) 201 { 202 progressBar.setIndeterminate(false); 203 progressBar.setValue(v); 204 } 205 lastText = descriptor.getDetailsMsg(); 206 detailsTextArea.setText(lastText.toString()); 207 } 208 209 /** 210 * Creates the progress bar panel. 211 * @return the created panel. 212 */ 213 private JPanel createProgressBarPanel() 214 { 215 JPanel panel = new JPanel(new GridBagLayout()); 216 panel.setOpaque(false); 217 GridBagConstraints gbc = new GridBagConstraints(); 218 gbc.insets = UIFactory.getEmptyInsets(); 219 gbc.fill = GridBagConstraints.HORIZONTAL; 220 221 btnCancel = UIFactory.makeJButton( 222 INFO_CANCEL_BUTTON_LABEL.get(), 223 INFO_CANCEL_BUTTON_TOOLTIP.get()); 224 btnCancel.addActionListener(new ActionListener() { 225 public void actionPerformed(ActionEvent e) { 226 GuiApplication app = getApplication(); 227 QuickSetup qs = getQuickSetup(); 228 if (app.confirmCancel(qs)) { 229 app.cancel(); 230 btnCancel.setEnabled(false); 231 } 232 } 233 }); 234 235 progressBar = new JProgressBar(); 236 progressBar.setIndeterminate(true); 237 // The ProgressDescriptor provides the ratio in % 238 progressBar.setMaximum(100); 239 240 gbc.gridwidth = GridBagConstraints.RELATIVE; 241 gbc.weightx = 0.0; 242 panel.add(Box.createHorizontalStrut(UIFactory.PROGRESS_BAR_SIZE), gbc); 243 gbc.gridwidth = GridBagConstraints.REMAINDER; 244 gbc.weightx = 1.0; 245 panel.add(Box.createHorizontalGlue(), gbc); 246 247 gbc.gridwidth = GridBagConstraints.RELATIVE; 248 gbc.weightx = 0.0; 249 panel.add(progressBar, gbc); 250 251 if (getApplication().isCancellable()) { 252 gbc.insets.left = 15; 253 gbc.fill = GridBagConstraints.NONE; 254 gbc.anchor = GridBagConstraints.LINE_START; 255 gbc.gridwidth = 1; 256 panel.add(btnCancel, gbc); 257 } 258 259 gbc.gridwidth = GridBagConstraints.REMAINDER; 260 gbc.fill = GridBagConstraints.HORIZONTAL; 261 gbc.weightx = 1.0; 262 panel.add(Box.createHorizontalGlue(), gbc); 263 264 265 266 return panel; 267 } 268 269 /** 270 * Adds the required focus listeners to the fields. 271 */ 272 private void addFocusListeners() 273 { 274 final FocusListener l = new FocusListener() 275 { 276 public void focusGained(FocusEvent e) 277 { 278 lastFocusComponent = e.getComponent(); 279 } 280 281 public void focusLost(FocusEvent e) 282 { 283 } 284 }; 285 286 JComponent[] comps = 287 { 288 progressBarLabel, 289 progressBar, 290 btnCancel, 291 detailsTextArea 292 }; 293 for (JComponent comp : comps) { 294 comp.addFocusListener(l); 295 } 296 297 lastFocusComponent = detailsTextArea; 298 } 299}