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