View Javadoc

1   /*
2    * Copyright (c) 2005, The K-Wf Grid Consortium
3    * Fraunhofer Institute for Computer Architecture and Software Technology
4    * See http://www.kwfgrid.eu and http://www.first.fraunhofer.de for more details.
5    */
6   package net.kwfgrid.gwui.gui;
7   
8   import net.kwfgrid.gworkflowdl.protocol.structure.*;
9   import net.kwfgrid.gworkflowdl.structure.*;
10  import net.kwfgrid.gwui.workflow.XMLUtilities;
11  
12  import org.glassbox.executor.Executor;
13  import org.apache.log4j.Logger;
14  
15  import java.awt.*;
16  import java.awt.event.*;
17  import java.util.List;
18  import javax.swing.*;
19  import javax.swing.event.TableModelListener;
20  import javax.swing.event.TableModelEvent;
21  import javax.swing.table.*;
22  
23  public class OperationCandidateEditor extends AbstractWorkflowElementEditor implements ActionListener {
24  
25      private static final Logger logger = Logger.getLogger(OperationCandidateEditor.class);
26  
27      ///
28      /// Controller for the table.
29      /// ....................................................................................................
30  
31      private class PeTableController implements SimpleEditTableModel.Controller, TableModelListener {
32  	public void tableChanged(TableModelEvent e) {
33  	    if (e.getType() == TableModelEvent.UPDATE) {
34  		int column = e.getColumn();
35  		int row = e.getFirstRow();
36  		final Object value = _petablemodel.getValueAt(row, column);
37  		final OperationCandidate operationCandidate = _operationClass.getOperationCandidates()[row];
38  		
39  		setPerformingTask(true);
40  		if (column == COLUMN_INDEX_OPERATION) {
41  		    getExecutor().execute(new GUIMethodCallTask("Setting new operation name...",
42  								getExecutor(), 
43  								OperationCandidateEditor.this) {
44  			    protected void execute() {
45  				operationCandidate.setOperationName((String)value);
46  			    }
47  			});	
48  		} else if (column == COLUMN_INDEX_RESOURCE) {
49  		    getExecutor().execute(new GUIMethodCallTask("Setting new resource name...",
50  								getExecutor(), 
51  								OperationCandidateEditor.this) {
52  			    protected void execute() {
53  				operationCandidate.setResourceName((String)value);
54  			    }
55  			});	
56  		} else if (column == COLUMN_INDEX_QUALITY) {
57  		    getExecutor().execute(new GUIMethodCallTask("Setting new quality...",
58  								getExecutor(), 
59  								OperationCandidateEditor.this) {
60  			    protected void execute() {
61  				Float q = (Float)value;
62  				float quality = q==null?0.0f:q.floatValue();
63  				operationCandidate.setQuality(quality);
64  			    }
65  			});	
66  		} else if (column == COLUMN_INDEX_SELECTED) {		    
67  		    getExecutor().execute(new GUIMethodCallTask("Changing selection...",
68  								getExecutor(), 
69  								OperationCandidateEditor.this) {
70  			    protected void execute() {
71  				Boolean b = (Boolean)value;
72  				boolean selected = b==null?false:b.booleanValue();
73  				operationCandidate.setSelected(selected);
74  			    }
75  			});	
76  		}
77  	    }
78  	}
79  
80  	public void rowAdded(Object[] row) {
81  	    String operationName = (String)row[COLUMN_INDEX_OPERATION];
82  	    String resourceName = (String)row[COLUMN_INDEX_RESOURCE];
83          String type = (String)row[COLUMN_INDEX_TYPE];
84          Float q = (Float)row[COLUMN_INDEX_QUALITY];
85  	    float quality = q==null?0.0f:q.floatValue();	    
86  	    Boolean b = (Boolean)row[COLUMN_INDEX_SELECTED];
87  	    boolean selected = b==null?false:b.booleanValue();
88  
89          final OperationCandidate operationCandidate = Factory.newOperationCandidate();
90          operationCandidate.setType(type);
91  	    operationCandidate.setOperationName(operationName);
92  	    operationCandidate.setResourceName(resourceName);
93  	    operationCandidate.setQuality(quality);
94  	    operationCandidate.setSelected(selected);
95  
96  	    setPerformingTask(true);
97  	    getExecutor().execute(new GUIMethodCallTask("Adding new operation candidate ...",
98  							getExecutor(), 
99  							OperationCandidateEditor.this) {
100 		    protected void execute() {
101 			_operationClass.addOperationCandidate(operationCandidate);
102 		    }
103 		});	
104 	}
105 	
106 	public void rowsDeleted(final int[] deletion) {
107 	    setPerformingTask(true);
108 	    getExecutor().execute(new GUIMethodCallTask("Removing selected operation candidates...",
109 							getExecutor(),
110 							OperationCandidateEditor.this) {
111 		    protected void execute() {
112 			for (int i=0; i<deletion.length; i++) {
113 			    deletion[i] = _petablesorter.modelIndex(deletion[i]);
114 			}
115 			for (int i=0; i<deletion.length; i++) {
116 			    _operationClass.removeOperationCandidate(deletion[i]);
117 			    for (int j=i+1; j<deletion.length; j++) {
118 				if (deletion[j] > deletion[i]) deletion[j]--;
119 			    }
120 			}
121 		    }
122 		});
123 	}
124     }
125     
126     private static final int COLUMN_INDEX_OPERATION = 0;
127     private static final int COLUMN_INDEX_RESOURCE = 1;
128     private static final int COLUMN_INDEX_TYPE = 2;
129     private static final int COLUMN_INDEX_QUALITY = 3;
130     private static final int COLUMN_INDEX_SELECTED = 4;
131     private static final String[] COLUMN_NAMES = new String[] { "Operation", "Resource", "Type", "Quality", "Selected" };
132     private static final String OCN_COMMAND = "ocn";
133 
134     private JPanel _view;
135     private JTextField _ocnfield;
136     private JTable _petable;
137     private TableSorter _petablesorter;
138     private TableModel _petablemodel;
139     private PeTableController _petablecontroller;
140     private OperationClass _operationClass;
141 
142     public OperationCandidateEditor(Executor executor, ProtocolWorkflow workflow, ProtocolTransition transition) {
143 	super(executor, workflow, transition);
144 	_view = null;
145 	_ocnfield = null;
146 	_petable = null;
147 	_petablesorter = null;
148 	_petablemodel = null;
149 	_petablecontroller = null;
150 	Operation operation = transition.getOperation();
151 	_operationClass = (OperationClass)operation.get();
152     }
153 
154     public void actionPerformed(ActionEvent e) {
155 	    final String operationClassName = _ocnfield.getText();
156 	    setPerformingTask(true);	    
157 	    getExecutor().execute(new GUIMethodCallTask("Setting new operation class name ...",
158 							getExecutor(),
159 							OperationCandidateEditor.this) {
160 		    protected void execute() {
161 			_operationClass.setName(operationClassName);
162 		    }
163 		});		    
164     }
165 
166     public void objectsAdded(IStructureObject parent, String namespace, String name, List objects) {
167 	if (addRemoveAffectsPeTableModel(parent, namespace, name)) updatePeTableModel();
168 	else if (addRemoveAffectsSoftwareClass(parent, namespace, name)) updateOperationClassName();
169     }
170 
171     public void objectsRemoved(IStructureObject parent, String namespace, String name, List objects) {
172 	if (addRemoveAffectsPeTableModel(parent, namespace, name)) updatePeTableModel();
173 	else if (addRemoveAffectsSoftwareClass(parent, namespace, name)) updateOperationClassName();
174     }
175     
176     public void propertyChanged(IStructureObject parent, String namespace, String name, Object newvalue) {
177 	if (propertyChangeAffectsPeTableModel(parent, namespace, name)) updatePeTableModel();
178 	else if (propertyChangeAffectsSoftwareClass(parent, namespace, name)) updateOperationClassName();
179     }
180 
181     private boolean addRemoveAffectsPeTableModel(IStructureObject parent, String namespace, String name) {
182 	return (parent == _operationClass &&
183 		ProtocolOperationCandidate.NAME.equals(name) &&
184 		XMLUtilities.equalNamespace(namespace, ProtocolOperationCandidate.NAMESPACE));
185     }
186     
187     private boolean propertyChangeAffectsPeTableModel(IStructureObject parent, String namespace, String name) {
188 	return (parent instanceof OperationCandidate &&
189 		((IChildObject)parent).getParent() == _operationClass);
190     }
191 
192     private void updatePeTableModel() {
193 	_petablemodel = createPeTableModel(_operationClass.getOperationCandidates());
194 	_petablemodel.addTableModelListener(_petablecontroller);
195 	_petablesorter.setTableModel(_petablemodel);
196 	updateView();
197     }
198 
199     private boolean addRemoveAffectsSoftwareClass(IStructureObject parent, String namespace, String name) {
200 	return (parent == _operationClass &&
201 		name.equals("name") &&
202 		XMLUtilities.equalNamespace(namespace, ProtocolOperationClass.NAMESPACE));
203     }
204     
205     private boolean propertyChangeAffectsSoftwareClass(IStructureObject parent, String namespace, String name) {
206 	return (parent == _operationClass &&
207 		name.equals("name") &&
208 		XMLUtilities.equalNamespace(namespace, ProtocolOperationClass.NAMESPACE));
209     }
210 
211     private void updateOperationClassName() {
212 	_ocnfield.setText(_operationClass.getName());
213     }
214 
215     private TableModel createPeTableModel(OperationCandidate[] candidates) {
216 	if (candidates == null) candidates = new OperationCandidate[0];
217 	Object[][] data = new Object[candidates.length][5];
218 	for (int i=0; i<candidates.length; i++) {
219 	    data[i][COLUMN_INDEX_OPERATION] = candidates[i].getOperationName();
220 	    data[i][COLUMN_INDEX_RESOURCE] = candidates[i].getResourceName();
221         data[i][COLUMN_INDEX_TYPE] = candidates[i].getType();
222         data[i][COLUMN_INDEX_QUALITY] = new Float(candidates[i].getQuality());
223 	    data[i][COLUMN_INDEX_SELECTED] = candidates[i].isSelected()?Boolean.TRUE:Boolean.FALSE;
224 	}
225 	return new DefaultTableModel(data, COLUMN_NAMES) {
226 		public Class getColumnClass(int c) {
227 		    if (c == COLUMN_INDEX_SELECTED) {
228 			return Boolean.class;
229 		    } else if (c == COLUMN_INDEX_QUALITY) {
230 			return Float.class;
231 		    } else {
232 			return String.class;
233 		    }
234 		}
235 	    };
236     }
237 
238     protected void updateState() {
239 	_petable.setEnabled(isEnabled() && isEditable() && !isPerformingTask());
240 	_ocnfield.setEnabled(isEnabled() && isEditable() && !isPerformingTask());
241     }
242 
243     protected void updateView() {
244 	updateState();
245 	// _view.invalidate();
246 	// _view.setSize(_view.getLayout().preferredLayoutSize(_view));
247 	// _view.doLayout();
248 	// _view.validate();	
249     }
250 
251     public JComponent getView() {
252 	if (_view == null) {
253 
254 	    _ocnfield = new JTextField(40);
255 	    _ocnfield.setText(_operationClass.getName());
256 	    _ocnfield.addActionListener(this);
257 	    _ocnfield.setActionCommand(OCN_COMMAND);
258 
259 	    _petablecontroller = new PeTableController();
260 	    _petablemodel = createPeTableModel(_operationClass.getOperationCandidates());
261 	    _petablemodel.addTableModelListener(_petablecontroller);
262 	    _petablesorter = new TableSorter(_petablemodel);
263 	    SimpleEditTableModel peeditor = new SimpleEditTableModel(_petablesorter, _petablecontroller, 0, "Add new operation candidate ...");
264 	    _petable = new JTable(peeditor);
265 	    _petablesorter.setTableHeader(_petable.getTableHeader());
266 	    _petable.addKeyListener(peeditor.getDeleteKeyHandler(_petable));
267 	    _petable.setDefaultRenderer(String.class, SimpleEditTableModel.getCellRendererForString());
268 	    _petable.setDefaultEditor(String.class, SimpleEditTableModel.getCellEditorForString());	    
269 
270 	    _view = new JPanel();
271 	    _view.setBorder(createBorder("Operation"));
272 	    _view.setLayout(new GridBagLayout());
273 	    
274 	    GridBagConstraints c = new GridBagConstraints();
275 	    
276 	    c.insets = new Insets(5, 0, 0, 0);
277 	    c.weightx = 1.0;
278 	    c.weighty = 0.0;
279 	    c.gridx = 0;
280 	    c.gridy = 0;
281 	    c.anchor = GridBagConstraints.WEST;
282 	    c.fill = GridBagConstraints.NONE;
283 	    c.gridwidth = GridBagConstraints.REMAINDER;
284 
285 	    _view.add(new JLabel("Operation Class Name"), c);
286 
287 	    c.gridy = 1;
288 	    c.insets = new Insets(2, 0, 0, 0);
289 	    c.anchor = GridBagConstraints.CENTER;
290 	    c.fill = GridBagConstraints.HORIZONTAL;
291 	    
292 	    _view.add(_ocnfield, c);
293 	    
294 	    c.gridy = 2;
295 	    c.anchor = GridBagConstraints.WEST;
296 	    c.fill = GridBagConstraints.NONE;
297 	    c.insets = new Insets(5, 0, 0, 0);
298 	    c.fill = GridBagConstraints.HORIZONTAL;
299 
300 	    _view.add(new JLabel("Operation Candidates"), c);
301 
302 	    c.gridy = 3;
303 	    c.insets = new Insets(2, 0, 0, 0);
304 	    c.anchor = GridBagConstraints.CENTER;
305 	    c.fill = GridBagConstraints.HORIZONTAL;
306 
307 	    _view.add(_petable.getTableHeader(), c);
308 	    
309 	    c.weighty = 1.0;
310 	    c.gridy = 4;
311 	    c.insets = new Insets(0, 0, 0, 0);
312 	    c.fill = GridBagConstraints.BOTH;
313 
314 	    _view.add(_petable, c);
315 
316 	    c.gridy = 5;
317 	    c.insets = new Insets(5, 0, 0, 0);
318 	    c.fill = GridBagConstraints.HORIZONTAL;
319 	    c.weighty = 0.0;
320 
321 	    _view.add(new JSeparator(), c);
322 
323 	    c.gridy = 6;
324 	    c.anchor = GridBagConstraints.WEST;
325 	    c.fill = GridBagConstraints.NONE;
326 
327 	}
328 	return _view;
329     }
330 }