1
2
3
4
5
6
7
8
9
10
11
12
13 package com.eviware.soapui.support.components;
14
15 import java.awt.BorderLayout;
16 import java.awt.Component;
17 import java.awt.event.ActionEvent;
18
19 import javax.swing.AbstractAction;
20 import javax.swing.BorderFactory;
21 import javax.swing.DefaultListCellRenderer;
22 import javax.swing.DefaultListModel;
23 import javax.swing.JLabel;
24 import javax.swing.JList;
25 import javax.swing.JPanel;
26 import javax.swing.JPopupMenu;
27 import javax.swing.JScrollPane;
28 import javax.swing.SwingUtilities;
29 import javax.swing.event.ListDataEvent;
30 import javax.swing.event.TreeModelEvent;
31 import javax.swing.event.TreeModelListener;
32 import javax.swing.tree.TreePath;
33
34 import com.eviware.soapui.SoapUI;
35 import com.eviware.soapui.model.ModelItem;
36 import com.eviware.soapui.model.tree.SoapUITreeNode;
37 import com.eviware.soapui.model.tree.nodes.support.EmptyModelItem;
38 import com.eviware.soapui.support.ListDataListenerAdapter;
39 import com.eviware.soapui.support.UISupport;
40 import com.eviware.soapui.support.swing.ModelItemListMouseListener;
41 import com.eviware.soapui.ui.support.DefaultDesktopPanel;
42
43 public class ModelItemListDesktopPanel extends DefaultDesktopPanel
44 {
45 private final ModelItem[] modelItems;
46 private JList list;
47 private ItemsListModel listModel;
48 private InternalTreeModelListener treeModelListener;
49
50 public ModelItemListDesktopPanel( String title, String description, ModelItem [] modelItems )
51 {
52 super( title, description, new JPanel( new BorderLayout() ) );
53 this.modelItems = modelItems;
54
55 buildUI();
56
57 treeModelListener = new InternalTreeModelListener();
58 SoapUI.getNavigator().getMainTree().getModel().addTreeModelListener( treeModelListener );
59 }
60
61 private void buildUI()
62 {
63 JPanel p = ( JPanel ) getComponent();
64
65 p.add( UISupport.buildDescription( getTitle(), getDescription(), null ), BorderLayout.NORTH );
66 p.add( buildModelItemList(), BorderLayout.CENTER );
67 }
68
69 @Override
70 public boolean onClose( boolean canCancel )
71 {
72 SoapUI.getNavigator().getMainTree().getModel().removeTreeModelListener( treeModelListener );
73 return super.onClose( canCancel );
74 }
75
76 private Component buildModelItemList()
77 {
78 listModel = new ItemsListModel( modelItems );
79
80 list = new JList( listModel);
81 list.setCellRenderer( new ItemListCellRenderer() );
82 ModelItemListMouseListener modelItemListMouseListener = new ModelItemListMouseListener();
83 JPopupMenu popupMenu = new JPopupMenu();
84 popupMenu.add( new RemoveAction() );
85 popupMenu.add( new HighlightAction() );
86
87 modelItemListMouseListener.setPopupMenu( popupMenu );
88 list.addMouseListener( modelItemListMouseListener );
89 listModel.addListDataListener( new ListDataListenerAdapter() {
90
91 @Override
92 public void intervalRemoved( ListDataEvent e )
93 {
94 if( listModel.isEmpty() )
95 {
96 SwingUtilities.invokeLater( new Runnable() {
97
98 public void run()
99 {
100 SoapUI.getDesktop().closeDesktopPanel( ModelItemListDesktopPanel.this );
101 }} );
102 }
103 }} );
104 return new JScrollPane( list );
105 }
106
107 private class ItemsListModel extends DefaultListModel
108 {
109 public ItemsListModel( ModelItem[] modelItems )
110 {
111 for( ModelItem item : modelItems )
112 addElement( item );
113 }
114
115 public void nodesChanged()
116 {
117 fireContentsChanged( this, 0, getSize()-1 );
118 }
119 }
120
121 private class RemoveAction extends AbstractAction
122 {
123 public RemoveAction()
124 {
125 super( "Remove" );
126 putValue( SHORT_DESCRIPTION, "Removes this item from the list" );
127 }
128
129 public void actionPerformed( ActionEvent e )
130 {
131 int ix = list.getSelectedIndex();
132 if( ix != -1 && UISupport.confirm( "Remove selected item from list?", "Remove Item" ))
133 listModel.remove( ix );
134 }
135 }
136
137 private class HighlightAction extends AbstractAction
138 {
139 public HighlightAction()
140 {
141 super( "Select in Tree" );
142 putValue( SHORT_DESCRIPTION, "Selects this node in the Navigator Tree" );
143 }
144
145 public void actionPerformed( ActionEvent e )
146 {
147 int ix = list.getSelectedIndex();
148 if( ix != -1 )
149 UISupport.select( ( ModelItem ) listModel.getElementAt( ix ));
150 }
151 }
152
153 private final class InternalTreeModelListener implements TreeModelListener
154 {
155 public void treeNodesChanged( TreeModelEvent e )
156 {
157 listModel.nodesChanged();
158 }
159
160 public void treeNodesInserted( TreeModelEvent e )
161 {
162 }
163
164 public void treeNodesRemoved( TreeModelEvent e )
165 {
166 SwingUtilities.invokeLater( new Runnable() {
167
168 public void run()
169 {
170 for( int c = 0; c < listModel.getSize(); c++ )
171 {
172 if( SoapUI.getNavigator().getTreePath( ( ModelItem ) listModel.elementAt( c )) == null )
173 {
174 listModel.remove( c );
175 c--;
176 }
177 }
178 }} );
179 }
180
181 public void treeStructureChanged( TreeModelEvent e )
182 {
183 }
184 }
185
186 private class ItemListCellRenderer extends DefaultListCellRenderer
187 {
188 public Component getListCellRendererComponent( JList list, Object value, int index, boolean isSelected, boolean cellHasFocus )
189 {
190 JLabel label = ( JLabel ) super.getListCellRendererComponent( list, value, index, isSelected, cellHasFocus );
191
192 if( value instanceof ModelItem )
193 {
194 ModelItem item = ( ModelItem ) value;
195 TreePath treePath = SoapUI.getNavigator().getTreePath( item );
196
197 if( treePath == null )
198 {
199 if( !(item instanceof EmptyModelItem))
200 {
201
202 }
203
204 label.setText( "<removed>" );
205 label.setToolTipText( null );
206 }
207 else
208 {
209 String str = item.getName() + " [";
210
211 for( int c = 1; c < treePath.getPathCount(); c++ )
212 {
213 SoapUITreeNode comp = ( SoapUITreeNode ) treePath.getPathComponent( c );
214 if( comp.getModelItem() instanceof EmptyModelItem )
215 continue;
216
217 if( c > 1 )
218 str += " - ";
219
220 str += comp.toString();
221 }
222
223 str += "]";
224
225 label.setText( str);
226 label.setToolTipText( item.getDescription() );
227 }
228
229 label.setIcon( item.getIcon() );
230 label.setBorder( BorderFactory.createEmptyBorder( 2, 2, 2, 2 ));
231 }
232
233 return label;
234 }
235 }
236 }