OSDN Git Service

Spiという名前をすべてServiceに変更した.
[stigmata/stigmata.git] / src / main / java / jp / sourceforge / stigmata / ui / swing / BirthmarkDefinitionPane.java
1 package jp.sourceforge.stigmata.ui.swing;
2
3 import java.awt.BorderLayout;
4 import java.awt.Dimension;
5 import java.awt.event.ActionEvent;
6 import java.awt.event.ActionListener;
7 import java.awt.event.ItemEvent;
8 import java.awt.event.ItemListener;
9 import java.util.ArrayList;
10 import java.util.Iterator;
11 import java.util.List;
12
13 import javax.swing.Box;
14 import javax.swing.DefaultListModel;
15 import javax.swing.JButton;
16 import javax.swing.JCheckBox;
17 import javax.swing.JComboBox;
18 import javax.swing.JList;
19 import javax.swing.JPanel;
20 import javax.swing.JScrollPane;
21 import javax.swing.JTextArea;
22 import javax.swing.JTextField;
23 import javax.swing.ListModel;
24 import javax.swing.border.TitledBorder;
25 import javax.swing.event.DocumentEvent;
26 import javax.swing.event.DocumentListener;
27 import javax.swing.event.ListSelectionEvent;
28 import javax.swing.event.ListSelectionListener;
29
30 import jp.sourceforge.stigmata.BirthmarkEnvironment;
31 import jp.sourceforge.stigmata.spi.BirthmarkComparatorService;
32 import jp.sourceforge.stigmata.spi.BirthmarkExtractorService;
33 import jp.sourceforge.stigmata.spi.BirthmarkService;
34 import jp.sourceforge.stigmata.spi.ReflectedBirthmarkService;
35 import jp.sourceforge.talisman.i18n.Messages;
36
37 /**
38  * 
39  * @author Haruaki TAMADA
40  */
41 public class BirthmarkDefinitionPane extends JPanel{
42     private static final long serialVersionUID = 3932637653297802978L;
43
44     private StigmataFrame stigmata;
45     private DefaultListModel model;
46     private InformationPane information;
47     private JList serviceList;
48     private JButton newService;
49     private JButton removeService;
50     private List<BirthmarkService> addedService = new ArrayList<BirthmarkService>();
51     private List<BirthmarkServiceListener> listeners = new ArrayList<BirthmarkServiceListener>();
52
53     public BirthmarkDefinitionPane(StigmataFrame stigmata){
54         this.stigmata = stigmata;
55
56         initLayouts();
57         initData();
58
59         updateView();
60     }
61
62     public void addBirthmarkServiceListener(BirthmarkServiceListener listener){
63         listeners.add(listener);
64     }
65
66     public void removeBirthmarkServiceListener(BirthmarkServiceListener listener){
67         listeners.remove(listener);
68     }
69
70     public void reset(){
71         for(BirthmarkService service: addedService){
72             model.removeElement(service);
73         }
74     }
75
76     public void updateEnvironment(BirthmarkEnvironment environment){
77         for(BirthmarkService service: addedService){
78             if(environment.getService(service.getType()) == null){
79                 environment.addService(service);
80             }
81         }
82     }
83
84     private void initData(){
85         information.initData();
86         model.addElement(stigmata.getMessages().get("newservice.definition.label"));
87
88         for(BirthmarkService service: stigmata.getEnvironment().findServices()){
89             model.addElement(service);
90         }
91     }
92
93     private void initLayouts(){
94         Messages messages = stigmata.getMessages();
95         JPanel panel = new JPanel(new BorderLayout());
96         serviceList = new JList(model = new DefaultListModel());
97         serviceList.setCellRenderer(new BirthmarkServiceListCellRenderer(new Dimension(250, 20), 60));
98         JScrollPane scroll = new JScrollPane(serviceList);
99
100         scroll.setBorder(new TitledBorder(messages.get("servicelist.border")));
101         serviceList.setToolTipText(messages.get("servicelist.tooltip"));
102
103         panel.add(scroll, BorderLayout.WEST);
104         panel.add(information = new InformationPane(stigmata, this), BorderLayout.CENTER);
105
106         Box buttonPanel = Box.createHorizontalBox();
107         newService = GUIUtility.createButton(messages, "newservice");
108         removeService = GUIUtility.createButton(messages, "removeservice");
109         buttonPanel.add(Box.createHorizontalGlue());
110         buttonPanel.add(newService);
111         buttonPanel.add(Box.createHorizontalGlue());
112         buttonPanel.add(removeService);
113         buttonPanel.add(Box.createHorizontalGlue());
114
115         setLayout(new BorderLayout());
116         add(panel, BorderLayout.CENTER);
117         add(buttonPanel, BorderLayout.SOUTH);
118
119         removeService.setEnabled(false);
120
121         serviceList.addListSelectionListener(new ListSelectionListener(){
122             @Override
123             public void valueChanged(ListSelectionEvent e){
124                 listValueChanged(e);
125             }
126         });
127
128         newService.addActionListener(new ActionListener(){
129             @Override
130             public void actionPerformed(ActionEvent e){
131                 addNewService();
132             }
133         });
134
135         removeService.addActionListener(new ActionListener(){
136             @Override
137             public void actionPerformed(ActionEvent e){
138                 removeService();
139             }
140         });
141     }
142
143     private void removeService(){
144         int index = serviceList.getSelectedIndex();
145         if(index > 0){
146             BirthmarkService service = (BirthmarkService)model.getElementAt(index);
147             if(service != null && service.isUserDefined()){
148                 model.remove(index);
149                 for(BirthmarkServiceListener listener: listeners){
150                     listener.serviceRemoved(service);
151                 }
152             }
153         }
154         stigmata.setNeedToSaveSettings(true);
155         updateView();
156     }
157
158     private void addNewService(){
159         BirthmarkService service = information.createService();
160         model.addElement(service);
161         addedService.add(service);
162
163         for(BirthmarkServiceListener listener: listeners){
164             listener.serviceAdded(service);
165         }
166         stigmata.setNeedToSaveSettings(true);
167         updateView();
168     }
169
170     private void listValueChanged(ListSelectionEvent e){
171         int index = serviceList.getSelectedIndex();
172         if(index > 0){
173             BirthmarkService service = (BirthmarkService)model.getElementAt(index);
174             if(service != null){
175                 information.setService(service);
176             }
177         }
178         else if(index == 0){
179             information.clear();
180         }
181         updateView();
182     }
183
184     /**
185      * remove: enabled when selected index is greater than 0 and selected service is defined by user.
186      * new service: enabled when selected index is less equals than 0 or selected service is defined by user and information pane is show available service.
187      *
188      */
189     private void updateView(){
190         int index = serviceList.getSelectedIndex();
191         ListModel model = serviceList.getModel();
192         BirthmarkService service = null;
193         if(index > 0){
194             service = (BirthmarkService)model.getElementAt(index); 
195         }
196         newService.setEnabled(
197             (index <= 0 || service.isUserDefined()) && 
198             information.isAvailableService() &&
199             isAvailableServiceName(information.getType())
200         );
201         removeService.setEnabled(index > 0 && service.isUserDefined());
202         information.setEnabled(index <= 0 || service.isUserDefined());
203     }
204
205     private boolean isAvailableServiceName(String name){
206         for(BirthmarkService service: addedService){
207             if(service.getType().equals(name)){
208                 return false;
209             }
210         }
211         return true;
212     }
213
214     private static class InformationPane extends JPanel{
215         private static final long serialVersionUID = 37906542932362L;
216
217         private StigmataFrame stigmata;
218         private BirthmarkDefinitionPane thisPane;
219         private JTextField type;
220         private JTextArea description;
221         private JComboBox extractor;
222         private JComboBox comparator;
223         private JCheckBox experimental;
224         private JCheckBox userDefined;
225
226         public InformationPane(StigmataFrame stigmata, BirthmarkDefinitionPane thisPane){
227             this.stigmata = stigmata;
228             this.thisPane = thisPane;
229             initLayouts();
230         }
231
232         public String getType(){
233             return type.getText();
234         }
235
236         @Override
237         public void setEnabled(boolean flag){
238             super.setEnabled(flag);
239
240             type.setEnabled(flag);
241             description.setEnabled(flag);
242             extractor.setEnabled(flag);
243             comparator.setEnabled(flag);
244         }
245
246         public BirthmarkService createService(){
247             BirthmarkService service = new ReflectedBirthmarkService(
248                 type.getText(), description.getText(),
249                 extractor.getSelectedItem().toString(),
250                 comparator.getSelectedItem().toString()
251             );
252
253             return service;
254         }
255
256         public void clear(){
257             type.setText("");
258             description.setText("");
259             extractor.getModel().setSelectedItem(null);
260             comparator.getModel().setSelectedItem(null);
261             userDefined.setSelected(true);
262             experimental.setSelected(true);
263         }
264
265         public boolean isAvailableService(){
266             String newType = type.getText();
267             Object selectedExtractor = extractor.getSelectedItem();
268             String extractorClass = "";;
269             if(selectedExtractor != null){
270                 extractorClass = selectedExtractor.toString();
271             }
272             Object selectedComparator = comparator.getSelectedItem();
273             String comparatorClass = "";
274             if(selectedComparator != null){
275                 comparatorClass = selectedComparator.toString();
276             }
277             BirthmarkEnvironment environment = stigmata.getEnvironment();
278
279             boolean flag = newType.length() > 0
280                     && extractorClass.length() > 0
281                     && comparatorClass.length() > 0;
282
283             // check inputed type is free
284             flag = flag && environment.getService(newType) == null;
285
286             // check extractor/comparator classes are available
287             flag = flag
288                 && environment.getClasspathContext().findEntry(extractorClass) != null
289                 && environment.getClasspathContext().findEntry(comparatorClass) != null;
290
291             return flag;
292         }
293
294         public void setService(BirthmarkService service){
295             type.setText(service.getType());
296             description.setText(service.getDescription());
297             selectComboBoxItem(extractor, service.getExtractor().getClass().getName());
298             selectComboBoxItem(comparator, service.getComparator().getClass().getName());
299             userDefined.setSelected(service.isUserDefined());
300             experimental.setSelected(service.isExperimental());
301
302             setEnabled(service.isUserDefined());
303         }
304
305         public void initData(){
306             comparator.addItem("");
307             for(Iterator<BirthmarkComparatorService> i = stigmata.getEnvironment().lookupProviders(BirthmarkComparatorService.class); i.hasNext();){
308                 BirthmarkComparatorService service = i.next();
309                 comparator.addItem(service.getType());
310                 // TODO: 比較器の名前を引っ張る方法を考える.
311             }
312             extractor.addItem("");
313             for(Iterator<BirthmarkExtractorService> i = stigmata.getEnvironment().lookupProviders(BirthmarkExtractorService.class); i.hasNext();){
314                 BirthmarkExtractorService service = i.next();
315                 extractor.addItem(service.getType());
316                 // TODO: 考える.
317             }
318         }
319
320         private void selectComboBoxItem(JComboBox box, String item){
321             box.getModel().setSelectedItem(item);
322         }
323
324         private void initLayouts(){
325             Messages messages = stigmata.getMessages();
326             type = new JTextField();
327             extractor = new JComboBox();
328             comparator = new JComboBox();
329             experimental = new JCheckBox(messages.get("define.experimental.label"));
330             userDefined = new JCheckBox(messages.get("define.userdef.label"));
331             description = new JTextArea();
332             JScrollPane scroll = new JScrollPane(description);
333             type.setColumns(10);
334             description.setColumns(40);
335             description.setRows(10);
336
337             JPanel typePane = new JPanel(new BorderLayout());
338             JPanel displayTypePane = new JPanel(new BorderLayout());
339             typePane.add(type, BorderLayout.CENTER);
340
341             JPanel box1 = new JPanel(new BorderLayout());
342             box1.add(typePane, BorderLayout.WEST);
343             box1.add(displayTypePane, BorderLayout.CENTER);
344
345             Box box2 = Box.createHorizontalBox();
346             box2.add(Box.createHorizontalGlue());
347             box2.add(experimental);
348             box2.add(Box.createHorizontalGlue());
349             box2.add(userDefined);
350             box2.add(Box.createHorizontalGlue());
351
352             JPanel extractorPane = new JPanel(new BorderLayout());
353             extractorPane.add(extractor, BorderLayout.CENTER);
354             JPanel comparatorPane = new JPanel(new BorderLayout());
355             comparatorPane.add(comparator, BorderLayout.CENTER);
356
357             Box panel = Box.createVerticalBox();
358             panel.add(box1);
359             panel.add(extractorPane);
360             panel.add(comparatorPane);
361             panel.add(box2);
362
363             setLayout(new BorderLayout());
364             add(panel, BorderLayout.NORTH);
365             add(scroll, BorderLayout.CENTER);
366
367             GUIUtility.decorateJComponent(messages, typePane, "define.type");
368             GUIUtility.decorateJComponent(messages, displayTypePane, "define.displaytype");
369             GUIUtility.decorateJComponent(messages, scroll, "define.description");
370             GUIUtility.decorateJComponent(messages, extractorPane, "define.extractor");
371             GUIUtility.decorateJComponent(messages, comparatorPane, "define.comparator");
372             GUIUtility.decorateJComponent(messages, experimental, "define.experimental");
373             GUIUtility.decorateJComponent(messages, userDefined, "define.userdef");
374
375             userDefined.setEnabled(false);
376             experimental.setEnabled(false);
377             userDefined.setSelected(true);
378             experimental.setSelected(true);
379
380             extractor.setEditable(true);
381             comparator.setEditable(true);
382
383             DocumentListener listener = new DocumentListener(){
384                 @Override
385                 public void insertUpdate(DocumentEvent e){
386                     thisPane.updateView();
387                 }
388
389                 @Override
390                 public void removeUpdate(DocumentEvent e){
391                     thisPane.updateView();
392                 }
393
394                 @Override
395                 public void changedUpdate(DocumentEvent e){
396                     thisPane.updateView();
397                 }
398             };
399
400             type.getDocument().addDocumentListener(listener);
401             description.getDocument().addDocumentListener(listener);
402             ItemListener itemListener = new ItemListener(){
403                 @Override
404                 public void itemStateChanged(ItemEvent e){
405                     thisPane.updateView();
406                 }
407             };
408             comparator.addItemListener(itemListener);
409             extractor.addItemListener(itemListener);
410             ActionListener actionListener = new ActionListener(){
411                 @Override
412                 public void actionPerformed(ActionEvent e){
413                     thisPane.updateView();
414                 }
415             };
416             comparator.getEditor().addActionListener(actionListener);
417             extractor.getEditor().addActionListener(actionListener);
418         }
419     }
420 }