1
14
15 package gate.gui;
16
17 import java.awt.*;
18 import java.awt.event.*;
19 import java.io.IOException;
20 import java.util.*;
21 import java.util.List;
22
23 import javax.swing.*;
24 import javax.swing.border.BevelBorder;
25 import javax.swing.event.ChangeEvent;
26 import javax.swing.table.*;
27
28 import gate.*;
29 import gate.creole.*;
30 import gate.event.CreoleEvent;
31 import gate.event.CreoleListener;
32 import gate.swing.XJTable;
33 import gate.util.*;
34
35
41 public class ResourceParametersEditor extends XJTable implements CreoleListener{
42
43 public ResourceParametersEditor(){
44 initLocalData();
45 initGuiComponents();
46 initListeners();
47 setSortable(true);
48 setSortedColumn(0);
49 setComparator(0, new ParameterDisjunctionComparator());
50 }
51
52
58 public void init(Resource resource, List parameters){
59 cleanup();
60 this.resource = resource;
61 if(parameters != null){
62 parameterDisjunctions = new ArrayList(parameters.size());
63 for(int i = 0; i < parameters.size(); i++){
64 parameterDisjunctions.add(
65 new ParameterDisjunction(resource,
66 (List)parameters.get(i)));
67 }
68 }else{
69 parameterDisjunctions = null;
70 }
71 tableModel.fireTableDataChanged();
72 }
74
75 protected void initLocalData(){
76 resource = null;
77 parameterDisjunctions = null;
78 }
80 protected void initGuiComponents(){
81 setModel(tableModel = new ParametersTableModel());
82 getColumnModel().getColumn(0).
83 setCellRenderer(new ParameterDisjunctionRenderer());
84 getColumnModel().getColumn(1).
85 setCellRenderer(new DefaultTableCellRenderer());
86 getColumnModel().getColumn(2).
87 setCellRenderer(new BooleanRenderer());
88 getColumnModel().getColumn(3).
89 setCellRenderer(new ParameterValueRenderer());
90 getColumnModel().getColumn(0).
91 setCellEditor(new ParameterDisjunctionEditor());
92 getColumnModel().getColumn(3).
93 setCellEditor(new ParameterValueEditor());
94 setIntercellSpacing(new Dimension(5, 5));
95 setAutoResizeMode(AUTO_RESIZE_LAST_COLUMN);
96
97 setSurrendersFocusOnKeystroke(true);
98 }
100
101 protected void initListeners(){
102 Gate.getCreoleRegister().addCreoleListener(this);
103 addKeyListener(new KeyAdapter() {
104 public void keyTyped(KeyEvent e) {
105 if(e.getKeyCode() == KeyEvent.VK_ENTER){
106 if(getEditingColumn() == -1 && getEditingRow() == -1){
107 getParent().dispatchEvent(e);
108 }
109 }
110 }
111
112 public void keyPressed(KeyEvent e) {
113 }
114
115 public void keyReleased(KeyEvent e) {
116 }
117 });
118 }
119
120
123 public void cleanup(){
124 Gate.getCreoleRegister().removeCreoleListener(this);
125 if(parameterDisjunctions != null && parameterDisjunctions.size() > 0){
126 for (int i = 0; i < parameterDisjunctions.size(); i++){
127 ((ParameterDisjunction)parameterDisjunctions.get(i)).cleanup();
128 }
129 }
130 resource = null;
131 }
132
133
150
153
154
158 public void setParameters() throws ResourceInstantiationException{
159 if(resource == null || parameterDisjunctions == null) return;
160 if(getEditingColumn() != -1 && getEditingRow() != -1){
162 editingStopped(new ChangeEvent(getCellEditor(getEditingRow(),
163 getEditingColumn())));
164 }
165 for(int i = 0; i < parameterDisjunctions.size(); i++){
167 ParameterDisjunction pDisj = (ParameterDisjunction)
168 parameterDisjunctions.get(i);
169 resource.setParameterValue(pDisj.getName(), pDisj.getValue());
170 }
171 }
172
173
176
177 public Resource getResource() {
178 return resource;
179 }
180
181
186 public FeatureMap getParameterValues(){
187 if(getEditingColumn() != -1 && getEditingRow() != -1){
189 editingStopped(new ChangeEvent(getCellEditor(getEditingRow(),
190 getEditingColumn())));
191 }
192 FeatureMap values = Factory.newFeatureMap();
194 if(parameterDisjunctions != null){
195 for(int i = 0; i < parameterDisjunctions.size(); i++){
196 ParameterDisjunction pDisj = (ParameterDisjunction)
197 parameterDisjunctions.get(i);
198 values.put(pDisj.getName(), pDisj.getValue());
199 }
200 }
201 return values;
202 }
203
204 public void resourceLoaded(CreoleEvent e) {
205 repaint();
206 }
207 public void resourceUnloaded(CreoleEvent e) {
208 repaint();
209 }
210
211 public void resourceRenamed(Resource resource, String oldName,
212 String newName){
213 repaint();
214 }
215 public void datastoreOpened(CreoleEvent e) {
216 }
217 public void datastoreCreated(CreoleEvent e) {
218 }
219 public void datastoreClosed(CreoleEvent e) {
220 }
221
222 public void setEditable(boolean editable) {
223 this.editable = editable;
224 }
225
226 public boolean isEditable() {
227 return editable;
228 }
229
230
234 void removeCreoleListenerLink(){
235 Gate.getCreoleRegister().removeCreoleListener(this);
238 if(parameterDisjunctions != null && parameterDisjunctions.size() > 0){
239 for (int i = 0; i < parameterDisjunctions.size(); i++){
240 ((ParameterDisjunction)parameterDisjunctions.get(i)).removeCreoleListenerLink();
241 }
242 }
243
244 }
245
246 ParametersTableModel tableModel;
247 Resource resource;
248
249
250
251
254 protected List parameterDisjunctions;
255 protected boolean editable = true;
256
257 protected class ParametersTableModel extends AbstractTableModel{
259
260 public int getColumnCount(){return 4;}
261
262 public Class getColumnClass(int columnIndex){
263 switch(columnIndex){
264 case 0: return ParameterDisjunction.class;
265 case 1: return String.class;
266 case 2: return Boolean.class;
267 case 3: return Object.class;
268 default: return Object.class;
269 }
270 }
272 public String getColumnName(int columnIndex){
273 switch(columnIndex){
274 case 0: return "Name";
275 case 1: return "Type";
276 case 2: return "Required";
277 case 3: return "Value";
278 default: return "?";
279 }
280 }
282 public boolean isCellEditable(int rowIndex,
283 int columnIndex) {
284 switch(columnIndex){
285 case 0: return ((ParameterDisjunction)
286 parameterDisjunctions.get(rowIndex)).size() > 1;
287 case 1: return false;
288 case 2: return false;
289 case 3: return editable;
290 default: return false;
291 }
292 }
294 public int getRowCount(){
295 return (parameterDisjunctions == null) ? 0 : parameterDisjunctions.size();
296 }
297
298 public Object getValueAt(int rowIndex,
299 int columnIndex) {
300 ParameterDisjunction pDisj = (ParameterDisjunction)
301 parameterDisjunctions.get(rowIndex);
302 switch(columnIndex){
303 case 0: return pDisj;
304 case 1: return pDisj.getType();
305 case 2: return pDisj.isRequired();
306 case 3: return pDisj.getValue();
307 default: return "?";
308 }
309 }
311 public void setValueAt(Object aValue, int rowIndex, int columnIndex){
312 ParameterDisjunction pDisj = (ParameterDisjunction)
313 parameterDisjunctions.get(rowIndex);
314 switch(columnIndex){
315 case 0:{
316 pDisj.setSelectedIndex(((Integer)aValue).intValue());
317 break;
318 }
319 case 1:{
320 break;
321 }
322 case 2:{
323 break;
324 }
325 case 3:{
326 pDisj.setValue(aValue);
327 break;
328 }
329 default:{}
330 }
331 } }
334 class ParameterDisjunctionRenderer extends DefaultTableCellRenderer {
335 public ParameterDisjunctionRenderer(){
336 combo = new JComboBox();
337 class CustomRenderer extends JLabel implements ListCellRenderer {
338 public Component getListCellRendererComponent(JList list,
339 Object value,
340 int index,
341 boolean isSelected,
342 boolean cellHasFocus){
343
344 setText(text);
345 setIcon(MainFrame.getIcon(iconName));
346 return this;
347 }
348 };
349 combo.setRenderer(new CustomRenderer());
350 }
351
352 public Component getTableCellRendererComponent(JTable table,
353 Object value,
354 boolean isSelected,
355 boolean hasFocus,
356 int row,
357 int column) {
358 ParameterDisjunction pDisj = (ParameterDisjunction)value;
359 text = pDisj.getName();
360 String type = pDisj.getType();
361 iconName = "param.gif";
362 if(Gate.isGateType(type)){
363 ResourceData rData = (ResourceData)Gate.getCreoleRegister().get(type);
364 if(rData != null) iconName = rData.getIcon();
365 }
366 if(pDisj.size() > 1){
367 combo.setModel(new DefaultComboBoxModel(new Object[]{text}));
368 return combo;
369 }
370 Component comp = super.getTableCellRendererComponent(table,
372 text,
373 isSelected, hasFocus,
374 row, column);
375 setIcon(MainFrame.getIcon(iconName));
376 return this;
377 }
379 JComboBox combo;
381 String iconName;
382 String text;
383 }
385
386
390 class ParameterValueRenderer extends ObjectRenderer {
391 ParameterValueRenderer() {
392 fileButton = new JButton(MainFrame.getIcon("loadFile.gif"));
393 fileButton.setToolTipText("Set from file...");
394 listButton = new JButton(MainFrame.getIcon("editList.gif"));
395 listButton.setToolTipText("Edit the list");
396 textField = new JTextField();
397 textButtonBox = new JPanel();
398 textButtonBox.setLayout(new BoxLayout(textButtonBox, BoxLayout.X_AXIS));
399 textButtonBox.setOpaque(false);
400
401 combo = new JComboBox();
402 combo.setRenderer(new ResourceRenderer());
403 }
405 public Component getTableCellRendererComponent(JTable table,
406 Object value,
407 boolean isSelected,
408 boolean hasFocus,
409 int row,
410 int column) {
411
412 String type = ((ParameterDisjunction)table.getValueAt(row, 0)).getType();
413
414 if(Gate.isGateType(type)){
415 if(ResourceParametersEditor.this.isEditable()){
417 combo.setModel(new DefaultComboBoxModel(new Object[]{value == null ?
418 "<none>" :
419 value }));
420 return combo;
421 }else{
422 String text = value == null ? "<none>" : value.toString();
425 textField.setText(text);
428 return textField;
429 }
430 }else{
431 Class typeClass = null;
432 try{
433 typeClass = Class.forName(type);
434 }catch(ClassNotFoundException cnfe){
435 }
436 String text = (value == null) ?
438 " " +
439 " " :
440 value.toString();
441 textField.setText(text);
443
446 if(type.equals("java.net.URL")){
447 if(ResourceParametersEditor.this.isEditable()){
448 textButtonBox.removeAll();
449 textField.setText(text);
450 textButtonBox.add(textField);
452 textButtonBox.add(Box.createHorizontalStrut(5));
455 textButtonBox.add(fileButton);
456 return textButtonBox;
457 }else{
458 return textField;
460 }
461 }else if(typeClass != null &&
462 List.class.isAssignableFrom(typeClass)){
463 textField.setText(textForList((List)value));
466 if(ResourceParametersEditor.this.isEditable()){
467 textButtonBox.removeAll();
468 textButtonBox.add(textField);
470 textButtonBox.add(Box.createHorizontalStrut(5));
473 textButtonBox.add(listButton);
474 return textButtonBox;
475 }else{
476 return textField;
478 }
479 }else return textField;
480 }
481 }
483
486 protected String textForList(List list){
487 if(list == null || list.isEmpty()) return "[]";
488 StringBuffer res = new StringBuffer("[");
489 Iterator elemIter = list.iterator();
490 while(elemIter.hasNext()){
491 Object elem = elemIter.next();
492 res.append( ((elem instanceof NameBearer) ?
493 ((NameBearer)elem).getName() :
494 elem.toString()) + ", ");
495 }
496 res.delete(res.length() - 2, res.length() - 1);
497 res.append("]");
498 return res.toString();
499 }
500
501 JButton fileButton;
502 JButton listButton;
503 JComboBox combo;
504 JPanel textButtonBox;
505 JTextField textField;
506 }
508 class ParameterDisjunctionComparator implements Comparator{
509 public int compare(Object o1, Object o2){
510 ParameterDisjunction pDisj1 = (ParameterDisjunction)o1;
511 ParameterDisjunction pDisj2 = (ParameterDisjunction)o2;
512 return pDisj1.getName().compareTo(pDisj2.getName());
513 }
514 }
515
516 class ParameterDisjunctionEditor extends DefaultCellEditor{
517 public ParameterDisjunctionEditor(){
518 super(new JComboBox());
519 combo = (JComboBox)super.getComponent();
520 class CustomRenderer extends JLabel implements ListCellRenderer {
521 public CustomRenderer(){
522 setOpaque(true);
523 }
524 public Component getListCellRendererComponent(JList list,
525 Object value,
526 int index,
527 boolean isSelected,
528 boolean cellHasFocus){
529 if (isSelected) {
530 setBackground(list.getSelectionBackground());
531 setForeground(list.getSelectionForeground());
532 }
533 else {
534 setBackground(list.getBackground());
535 setForeground(list.getForeground());
536 }
537
538 setFont(list.getFont());
539
540 setText((String)value);
541
542 String iconName = "param.gif";
543 Parameter[] params = pDisj.getParameters();
544 for(int i = 0; i < params.length; i++){
545 Parameter param = (Parameter)params[i];
546 if(param.getName().equals(value)){
547 String type = param.getTypeName();
548 if(Gate.getCreoleRegister().containsKey(type)){
549 ResourceData rData = (ResourceData)
550 Gate.getCreoleRegister().get(type);
551 if(rData != null) iconName = rData.getIcon();
552 }
553 break;
554 } }
557 setIcon(MainFrame.getIcon(iconName));
558 return this;
559 }
560 }; combo.setRenderer(new CustomRenderer());
562 combo.addActionListener(new ActionListener() {
563 public void actionPerformed(ActionEvent e) {
564 stopCellEditing();
565 }
566 });
567 }
569 public Component getTableCellEditorComponent(JTable table,
570 Object value,
571 boolean isSelected,
572 int row,
573 int column){
574 pDisj = (ParameterDisjunction)value;
575 combo.setModel(new DefaultComboBoxModel(pDisj.getNames()));
576 return combo;
577 }
579 public Object getCellEditorValue(){
580 return new Integer(combo.getSelectedIndex());
581 }
582
583 public boolean stopCellEditing(){
584 combo.hidePopup();
585 return super.stopCellEditing();
586 }
587
588 JComboBox combo;
589 ParameterDisjunction pDisj;
590 }
592 class ParameterValueEditor extends AbstractCellEditor
593 implements TableCellEditor{
594 ParameterValueEditor(){
595 combo = new JComboBox();
596 combo.setRenderer(new ResourceRenderer());
597 combo.setEditable(false);
598
599 textField = new JTextField();
600
601 fileChooser = MainFrame.getFileChooser();
602 fileButton = new JButton(MainFrame.getIcon("loadFile.gif"));
603 fileButton.setToolTipText("Set from file...");
604 fileButton.addActionListener(new ActionListener() {
605 public void actionPerformed(ActionEvent e) {
606 fileChooser.setFileSelectionMode(JFileChooser.FILES_AND_DIRECTORIES);
607 fileChooser.setDialogTitle("Select a file");
608 int res = fileChooser.showOpenDialog(ResourceParametersEditor.this);
609 if(res == JFileChooser.APPROVE_OPTION){
610 try {
611 textField.setText(fileChooser.getSelectedFile().
612 toURL().toExternalForm());
613 } catch(IOException ioe){}
614 fireEditingStopped();
615 }else{
616 fireEditingCanceled();
617 }
618 }
619 });
620
621 listButton = new JButton(MainFrame.getIcon("editList.gif"));
622 listButton.setToolTipText("Edit the list");
623 listButton.addActionListener(new ActionListener() {
624 public void actionPerformed(ActionEvent e) {
625 List returnedList = listEditor.showDialog();
626 if(returnedList != null){
627 listValue = returnedList;
628 fireEditingStopped();
629 }else{
630 fireEditingCanceled();
631 }
632 }
633 });
634
635 textButtonBox = new JPanel();
636 textButtonBox.setLayout(new BoxLayout(textButtonBox, BoxLayout.X_AXIS));
637 textButtonBox.setOpaque(false);
638 textFieldBoolean = new JTextField();
645 textFieldBoolean.setEditable(false);
646 textFieldBoolean.addMouseListener(new MouseAdapter() {
647 public void mouseClicked(MouseEvent e) {
648 Boolean value = new Boolean(textFieldBoolean.getText());
649 value = new Boolean(!value.booleanValue());
650 textFieldBoolean.setText(value.toString());
651 }
652 });
653 textFieldBoolean.addKeyListener(new KeyAdapter() {
654 public void keyTyped(KeyEvent e) {
655 Boolean value = new Boolean(textFieldBoolean.getText());
656 value = new Boolean(!value.booleanValue());
657 textFieldBoolean.setText(value.toString());
658 }
659 });
660
661 textButtonBox.addFocusListener(new FocusAdapter() {
662 public void focusGained(FocusEvent e) {
663 if(comboUsed){
664
665 }else{
666 textField.requestFocusInWindow();
667 }
668 }
669
670 public void focusLost(FocusEvent e) {
671 }
672 });
673
674 }
676 public Component getTableCellEditorComponent(JTable table,
677 Object value,
678 boolean isSelected,
679 int row,
680 int column){
681 comboUsed = false;
682 listUsed = false;
683 ParameterDisjunction pDisj = (ParameterDisjunction)
684 table.getValueAt(row, 0);
685 type = pDisj.getType();
686
688 if(Gate.isGateType(type)){
689 comboUsed = true;
691 ArrayList values = new ArrayList();
692 try{
693 values.addAll(Gate.getCreoleRegister().
694 getAllInstances(type));
695 }catch(GateException ge){
696 ge.printStackTrace(Err.getPrintWriter());
697 }
698 values.add(0, "<none>");
699 combo.setModel(new DefaultComboBoxModel(values.toArray()));
700 combo.setSelectedItem(value == null ? "<none>" : value);
701 return combo;
702 }else{
703 Class typeClass = null;
705 try{
706 typeClass = Class.forName(type);
707 }catch(ClassNotFoundException cnfe){
708 }
709
710 textField.setText((value == null) ? "" : value.toString());
711 if(type.equals("java.net.URL")){
712 fileChooser.resetChoosableFileFilters();
714 fileChooser.setAcceptAllFileFilterUsed(true);
715 fileChooser.setFileFilter(fileChooser.getAcceptAllFileFilter());
716 Parameter param = pDisj.getParameter();
717 Set sufixes = param.getSuffixes();
718 if(sufixes != null){
719 ExtensionFileFilter fileFilter = new ExtensionFileFilter();
720 Iterator sufIter = sufixes.iterator();
721 while(sufIter.hasNext()){
722 fileFilter.addExtension((String)sufIter.next());
723 }
724 fileFilter.setDescription("Known file types " + sufixes.toString());
725 fileChooser.addChoosableFileFilter(fileFilter);
726 fileChooser.setFileFilter(fileFilter);
727 }
728
729 textField.setEditable(true);
730 textButtonBox.removeAll();
731 textButtonBox.add(textField);
732 textButtonBox.add(Box.createHorizontalStrut(5));
733 textButtonBox.add(fileButton);
734 return textButtonBox;
735 }else if(type.equals("java.lang.Boolean")){
736 textFieldBoolean.setText(value == null ? "false" : value.toString());
737 return textFieldBoolean;
738 }else if(typeClass != null &&
739 List.class.isAssignableFrom(typeClass)){
740 listUsed = true;
742 Parameter param = pDisj.getParameter();
743 Set sufixes = param.getSuffixes();
744
745 listValue = (List)value;
746 listEditor = new ListEditorDialog(
747 SwingUtilities.getAncestorOfClass(
748 Window.class, ResourceParametersEditor.this),
749 (List)value, param.getItemClassName());
750
751 textField.setEditable(false);
752 textField.setText(textForList((List)value));
753 textButtonBox.removeAll();
754 textButtonBox.add(textField);
755 textButtonBox.add(Box.createHorizontalStrut(5));
756 textButtonBox.add(listButton);
757 return textButtonBox;
758 }else{
759 textField.setEditable(true);
760 return textField;
761 }
762 }
763 }
765
768 protected String textForList(List list){
769 if(list == null || list.isEmpty()) return "[]";
770 StringBuffer res = new StringBuffer("[");
771 Iterator elemIter = list.iterator();
772 while(elemIter.hasNext()){
773 Object elem = elemIter.next();
774 res.append( ((elem instanceof NameBearer) ?
775 ((NameBearer)elem).getName() :
776 elem.toString()) + ", ");
777 }
778 res.delete(res.length() - 2, res.length() - 1);
779 res.append("]");
780 return res.toString();
781 }
782
783 public Object getCellEditorValue(){
784 if(comboUsed){
785 Object value = combo.getSelectedItem();
786 return value == "<none>" ? null : value;
787 }
788 else if(listUsed){
789 return listValue;
790 }else{
791 if(type.equals("java.lang.Boolean")){
792 return new Boolean(textFieldBoolean.getText());
794 }else{
795 return textField.getText();
797 }
800 }
801 }
803
806 String type;
807
808
811 JComboBox combo;
812
813
818
821 JTextField textField;
822
823
826 JTextField textFieldBoolean;
827
830 JFileChooser fileChooser;
831
832 ListEditorDialog listEditor = null;
833 List listValue;
834
835 boolean comboUsed;
836 boolean listUsed;
837 JButton fileButton;
838 JButton listButton;
839 JPanel textButtonBox;
840 }}