/*************************************************** * * cismet GmbH, Saarbruecken, Germany * * ... and it just works. * ****************************************************/ /* * To change this license header, choose License Headers in Project Properties. * To change this template file, choose Tools | Templates * and open the template in the editor. */ package de.cismet.commons.gui.protocol; import com.jgoodies.looks.HeaderStyle; import com.jgoodies.looks.Options; import lombok.AccessLevel; import lombok.Getter; import org.jfree.ui.ExtensionFileFilter; import java.awt.Component; import java.awt.GridBagConstraints; import java.awt.Insets; import java.io.File; import java.util.HashMap; import java.util.List; import java.util.Map; import javax.swing.Action; import javax.swing.Box; import javax.swing.JFileChooser; import javax.swing.SwingUtilities; import javax.swing.SwingWorker; import javax.swing.filechooser.FileFilter; import de.cismet.commons.gui.protocol.listener.ProtocolHandlerAdapter; import de.cismet.commons.gui.protocol.listener.ProtocolHandlerListenerEvent; import de.cismet.tools.gui.StaticSwingTools; /** * DOCUMENT ME! * * @author jruiz * @version $Revision$, $Date$ */ public class ProtocolPanel extends javax.swing.JPanel { //~ Static fields/initializers --------------------------------------------- private static final transient org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(ProtocolPanel.class); private static final transient String FILE_SUFFIX = "prot"; //~ Instance fields -------------------------------------------------------- @Getter(AccessLevel.PRIVATE) private final ProtocolHandler handler; @Getter(AccessLevel.PRIVATE) private final FileFilter fileFilter = new ExtensionFileFilter(org.openide.util.NbBundle.getMessage( ProtocolPanel.class, "ProtocolPanel.filefilter.jsonfiledesc"), FILE_SUFFIX); @Getter(AccessLevel.PRIVATE) private final Map<ProtocolStep, ProtocolStepPanelWrapper> protocolStepToWrapperMap = new HashMap<ProtocolStep, ProtocolStepPanelWrapper>(); @Getter(AccessLevel.PRIVATE) private final GridBagConstraints wrapperConstraints = createWrapperConstraints(); @Getter(AccessLevel.PRIVATE) private final GridBagConstraints fillerConstraints = createFillerConstraints(); // Variables declaration - do not modify//GEN-BEGIN:variables private javax.swing.JButton btnClear; private javax.swing.JButton btnLoad; private javax.swing.JButton btnSave; private javax.swing.JFileChooser fchMain; private javax.swing.Box.Filler filToolbar; private javax.swing.JPanel panMain; private javax.swing.JPanel panSteps; private javax.swing.JPanel panStepsFiller; private javax.swing.JPanel panToolbarFiller; private javax.swing.JScrollPane scpSteps; private javax.swing.JToolBar.Separator sep1; private javax.swing.JToolBar.Separator sep2; private javax.swing.JToggleButton tbtRecordOnOff; private javax.swing.JToolBar tlbMain; // End of variables declaration//GEN-END:variables //~ Constructors ----------------------------------------------------------- /** * Creates new form ProtocolPanel. */ public ProtocolPanel() { this(null); } /** * Creates a new ProtocolPanel object. * * @param handler DOCUMENT ME! */ public ProtocolPanel(final ProtocolHandler handler) { if (handler != null) { this.handler = handler; } else { this.handler = ProtocolHandler.getInstance(); } initComponents(); getHandler().addProtocolHandlerListener(new ProtocolHandlerListenerImpl()); addSteps(getHandler().getAllSteps(), true); addToolbarItems(getHandler().getToolbarItems()); } //~ Methods ---------------------------------------------------------------- /** * DOCUMENT ME! * * @return DOCUMENT ME! */ private static GridBagConstraints createWrapperConstraints() { final GridBagConstraints constraints = new GridBagConstraints(); constraints.fill = GridBagConstraints.BOTH; constraints.weightx = 1; constraints.gridx = 0; constraints.gridy = GridBagConstraints.RELATIVE; constraints.insets = new Insets(5, 5, 5, 5); return constraints; } /** * DOCUMENT ME! * * @return DOCUMENT ME! */ private static GridBagConstraints createFillerConstraints() { final GridBagConstraints constraints = createWrapperConstraints(); constraints.weighty = 1; return constraints; } /** * This method is called from within the constructor to initialize the form. WARNING: Do NOT modify this code. The * content of this method is always regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents private void initComponents() { java.awt.GridBagConstraints gridBagConstraints; fchMain = new javax.swing.JFileChooser(); tlbMain = new javax.swing.JToolBar(); tbtRecordOnOff = new javax.swing.JToggleButton(); sep1 = new javax.swing.JToolBar.Separator(); btnLoad = new javax.swing.JButton(); btnSave = new javax.swing.JButton(); sep2 = new javax.swing.JToolBar.Separator(); btnClear = new javax.swing.JButton(); panToolbarFiller = new javax.swing.JPanel(); filToolbar = (javax.swing.Box.Filler)Box.createHorizontalGlue(); panMain = new javax.swing.JPanel(); scpSteps = new javax.swing.JScrollPane(); panSteps = new javax.swing.JPanel(); panStepsFiller = new javax.swing.JPanel(); fchMain.setFileFilter(getFileFilter()); setLayout(new java.awt.BorderLayout()); tlbMain.setFloatable(false); tlbMain.setRollover(true); tlbMain.setFocusable(false); tbtRecordOnOff.setIcon(new javax.swing.ImageIcon( getClass().getResource("/de/cismet/commons/gui/protocol/record_off.png"))); // NOI18N tbtRecordOnOff.setSelected(getHandler().isRecordEnabled()); org.openide.awt.Mnemonics.setLocalizedText( tbtRecordOnOff, org.openide.util.NbBundle.getMessage(ProtocolPanel.class, "ProtocolPanel.tbtRecordOnOff.text")); // NOI18N tbtRecordOnOff.setToolTipText(org.openide.util.NbBundle.getMessage( ProtocolPanel.class, "ProtocolPanel.tbtRecordOnOff.toolTipText")); // NOI18N tbtRecordOnOff.setBorderPainted(false); tbtRecordOnOff.setFocusPainted(false); tbtRecordOnOff.setFocusable(false); tbtRecordOnOff.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER); tbtRecordOnOff.setSelectedIcon(new javax.swing.ImageIcon( getClass().getResource("/de/cismet/commons/gui/protocol/record_on.png"))); // NOI18N tbtRecordOnOff.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM); tbtRecordOnOff.addActionListener(new java.awt.event.ActionListener() { @Override public void actionPerformed(final java.awt.event.ActionEvent evt) { tbtRecordOnOffActionPerformed(evt); } }); tlbMain.add(tbtRecordOnOff); tlbMain.add(sep1); btnLoad.setIcon(new javax.swing.ImageIcon(getClass().getResource("/de/cismet/commons/gui/protocol/load.png"))); // NOI18N org.openide.awt.Mnemonics.setLocalizedText( btnLoad, org.openide.util.NbBundle.getMessage(ProtocolPanel.class, "ProtocolPanel.btnLoad.text")); // NOI18N btnLoad.setToolTipText(org.openide.util.NbBundle.getMessage( ProtocolPanel.class, "ProtocolPanel.btnLoad.toolTipText")); // NOI18N btnLoad.setFocusPainted(false); btnLoad.setFocusable(false); btnLoad.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER); btnLoad.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM); btnLoad.addActionListener(new java.awt.event.ActionListener() { @Override public void actionPerformed(final java.awt.event.ActionEvent evt) { btnLoadActionPerformed(evt); } }); tlbMain.add(btnLoad); btnSave.setIcon(new javax.swing.ImageIcon(getClass().getResource("/de/cismet/commons/gui/protocol/save.png"))); // NOI18N org.openide.awt.Mnemonics.setLocalizedText( btnSave, org.openide.util.NbBundle.getMessage(ProtocolPanel.class, "ProtocolPanel.btnSave.text")); // NOI18N btnSave.setToolTipText(org.openide.util.NbBundle.getMessage( ProtocolPanel.class, "ProtocolPanel.btnSave.toolTipText")); // NOI18N btnSave.setFocusPainted(false); btnSave.setFocusable(false); btnSave.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER); btnSave.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM); btnSave.addActionListener(new java.awt.event.ActionListener() { @Override public void actionPerformed(final java.awt.event.ActionEvent evt) { btnSaveActionPerformed(evt); } }); tlbMain.add(btnSave); tlbMain.add(sep2); btnClear.setIcon(new javax.swing.ImageIcon( getClass().getResource("/de/cismet/commons/gui/protocol/remove_all.png"))); // NOI18N org.openide.awt.Mnemonics.setLocalizedText( btnClear, org.openide.util.NbBundle.getMessage(ProtocolPanel.class, "ProtocolPanel.btnClear.text")); // NOI18N btnClear.setToolTipText(org.openide.util.NbBundle.getMessage( ProtocolPanel.class, "ProtocolPanel.btnClear.toolTipText")); // NOI18N btnClear.setFocusPainted(false); btnClear.setFocusable(false); btnClear.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER); btnClear.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM); btnClear.addActionListener(new java.awt.event.ActionListener() { @Override public void actionPerformed(final java.awt.event.ActionEvent evt) { btnClearActionPerformed(evt); } }); tlbMain.add(btnClear); panToolbarFiller.setOpaque(false); panToolbarFiller.add(filToolbar); tlbMain.add(panToolbarFiller); tlbMain.putClientProperty(Options.HEADER_STYLE_KEY, HeaderStyle.BOTH); add(tlbMain, java.awt.BorderLayout.NORTH); panMain.setLayout(new java.awt.GridBagLayout()); panSteps.setLayout(new java.awt.GridBagLayout()); panStepsFiller.setPreferredSize(new java.awt.Dimension(100, 1)); final javax.swing.GroupLayout panStepsFillerLayout = new javax.swing.GroupLayout(panStepsFiller); panStepsFiller.setLayout(panStepsFillerLayout); panStepsFillerLayout.setHorizontalGroup( panStepsFillerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING).addGap( 0, 100, Short.MAX_VALUE)); panStepsFillerLayout.setVerticalGroup( panStepsFillerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING).addGap( 0, 300, Short.MAX_VALUE)); gridBagConstraints = new java.awt.GridBagConstraints(); gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; gridBagConstraints.weighty = 1.0; panSteps.add(panStepsFiller, gridBagConstraints); scpSteps.setViewportView(panSteps); gridBagConstraints = new java.awt.GridBagConstraints(); gridBagConstraints.gridx = 0; gridBagConstraints.gridy = 1; gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; gridBagConstraints.weightx = 1.0; gridBagConstraints.weighty = 1.0; panMain.add(scpSteps, gridBagConstraints); add(panMain, java.awt.BorderLayout.CENTER); } // </editor-fold>//GEN-END:initComponents /** * DOCUMENT ME! * * @param evt DOCUMENT ME! */ private void btnClearActionPerformed(final java.awt.event.ActionEvent evt) { //GEN-FIRST:event_btnClearActionPerformed getHandler().clearSteps(); } //GEN-LAST:event_btnClearActionPerformed /** * DOCUMENT ME! * * @param evt DOCUMENT ME! */ private void tbtRecordOnOffActionPerformed(final java.awt.event.ActionEvent evt) { //GEN-FIRST:event_tbtRecordOnOffActionPerformed getHandler().setRecordEnabled(tbtRecordOnOff.isSelected()); } //GEN-LAST:event_tbtRecordOnOffActionPerformed /** * DOCUMENT ME! * * @param evt DOCUMENT ME! */ private void btnSaveActionPerformed(final java.awt.event.ActionEvent evt) { //GEN-FIRST:event_btnSaveActionPerformed final int status = fchMain.showSaveDialog(StaticSwingTools.getParentFrame(this)); if (status == JFileChooser.APPROVE_OPTION) { final File selectedFile = fchMain.getSelectedFile(); new SwingWorker<Void, Void>() { @Override protected Void doInBackground() throws Exception { try { final File fileToSave; if (selectedFile.getName().toLowerCase().endsWith("." + FILE_SUFFIX)) { fileToSave = selectedFile; } else { fileToSave = new File(selectedFile.getAbsolutePath() + "." + FILE_SUFFIX); } getHandler().writeToFile(fileToSave); } catch (final Exception ex) { LOG.error(ex, ex); } return null; } @Override protected void done() { } }.execute(); } else if (status == JFileChooser.CANCEL_OPTION) { } } //GEN-LAST:event_btnSaveActionPerformed /** * DOCUMENT ME! * * @param evt DOCUMENT ME! */ private void btnLoadActionPerformed(final java.awt.event.ActionEvent evt) { //GEN-FIRST:event_btnLoadActionPerformed final int status = fchMain.showOpenDialog(StaticSwingTools.getParentFrame(this)); if (status == JFileChooser.APPROVE_OPTION) { final File selectedFile = fchMain.getSelectedFile(); new SwingWorker<Void, Void>() { @Override protected Void doInBackground() throws Exception { try { getHandler().readFromFile(selectedFile); } catch (final Exception ex) { LOG.error(ex, ex); } return null; } @Override protected void done() { } }.execute(); } else if (status == JFileChooser.CANCEL_OPTION) { } } //GEN-LAST:event_btnLoadActionPerformed /** * DOCUMENT ME! * * @param step DOCUMENT ME! */ private void removeStep(final ProtocolStep step) { final ProtocolStepPanelWrapper wrapper = protocolStepToWrapperMap.get(step); if (wrapper != null) { panSteps.remove(wrapper); panSteps.revalidate(); repaint(); } } /** * DOCUMENT ME! * * @param toolbarItems DOCUMENT ME! */ private void addToolbarItems(final List<ProtocolStepToolbarItem> toolbarItems) { for (final ProtocolStepToolbarItem toolbarItem : toolbarItems) { if (toolbarItem instanceof Component) { tlbMain.add((Component)toolbarItem); } else if (toolbarItem instanceof Action) { tlbMain.add((Action)toolbarItem); } else { LOG.warn("toolbar item not added. was neither Component nor Action"); } } } /** * DOCUMENT ME! * * @param steps DOCUMENT ME! * @param showImmediate DOCUMENT ME! */ private void addSteps(final List<ProtocolStep> steps, final boolean showImmediate) { if (SwingUtilities.isEventDispatchThread()) { for (final ProtocolStep step : steps) { try { addStep(step, showImmediate); } catch (final Exception ex) { LOG.warn("exception while adding step", ex); } } } else { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { addSteps(steps, showImmediate); } }); } } /** * DOCUMENT ME! * * @param step DOCUMENT ME! * @param showImmediate DOCUMENT ME! */ private void addStep(final ProtocolStep step, final boolean showImmediate) { if (SwingUtilities.isEventDispatchThread()) { if (LOG.isDebugEnabled()) { LOG.debug("adding GUI for protocol " + step.getMetaInfo().getKey() + "' and rendering it immediately: " + showImmediate); } final ProtocolStepPanelWrapper wrapper = new ProtocolStepPanelWrapper(step, showImmediate); panSteps.remove(panStepsFiller); panSteps.add(wrapper, getWrapperConstraints()); panSteps.add(panStepsFiller, getFillerConstraints()); panSteps.revalidate(); protocolStepToWrapperMap.put(step, wrapper); scpSteps.getVerticalScrollBar().setValue(scpSteps.getVerticalScrollBar().getMaximum()); repaint(); } else { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { addStep(step, showImmediate); } }); } } /** * DOCUMENT ME! */ private void clearSteps() { if (SwingUtilities.isEventDispatchThread()) { panSteps.removeAll(); panSteps.revalidate(); repaint(); } else { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { clearSteps(); } }); } } //~ Inner Classes ---------------------------------------------------------- /** * DOCUMENT ME! * * @version $Revision$, $Date$ */ private class ProtocolHandlerListenerImpl extends ProtocolHandlerAdapter { //~ Methods ------------------------------------------------------------ @Override public void recordStateChanged(final ProtocolHandlerListenerEvent event) { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { tbtRecordOnOff.setSelected(event.getSourceProtocolHander().isRecordEnabled()); } }); } @Override public void stepAdded(final ProtocolHandlerListenerEvent event) { addStep((ProtocolStep)event.getEventObject(), false); } @Override public void stepRemoved(final ProtocolHandlerListenerEvent event) { removeStep((ProtocolStep)event.getEventObject()); } @Override public void stepsCleared(final ProtocolHandlerListenerEvent event) { clearSteps(); } @Override public void stepsRestored(final ProtocolHandlerListenerEvent event) { clearSteps(); addSteps(event.getSourceProtocolHander().getAllSteps(), true); } } }