Merge develop to Release_2_8_3_Branch
[jalview.git] / src / jalview / jbgui / GStructureChooser.java
1 /*
2  * Jalview - A Sequence Alignment Editor and Viewer (Version 2.8.2)
3  * Copyright (C) 2014 The Jalview Authors
4  * 
5  * This file is part of Jalview.
6  * 
7  * Jalview is free software: you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License 
9  * as published by the Free Software Foundation, either version 3
10  * of the License, or (at your option) any later version.
11  *  
12  * Jalview is distributed in the hope that it will be useful, but 
13  * WITHOUT ANY WARRANTY; without even the implied warranty 
14  * of MERCHANTABILITY or FITNESS FOR A PARTICULAR 
15  * PURPOSE.  See the GNU General Public License for more details.
16  * 
17  * You should have received a copy of the GNU General Public License
18  * along with Jalview.  If not, see <http://www.gnu.org/licenses/>.
19  * The Jalview Authors are detailed in the 'AUTHORS' file.
20  */
21
22 package jalview.jbgui;
23
24 import jalview.datamodel.SequenceI;
25 import jalview.gui.AlignmentPanel;
26 import jalview.gui.Desktop;
27 import jalview.jbgui.PDBDocFieldPreferences.PreferenceSource;
28 import jalview.util.MessageManager;
29
30 import java.awt.BorderLayout;
31 import java.awt.CardLayout;
32 import java.awt.Dimension;
33 import java.awt.FlowLayout;
34 import java.awt.event.ActionEvent;
35 import java.awt.event.ItemEvent;
36 import java.awt.event.ItemListener;
37
38 import javax.swing.ImageIcon;
39 import javax.swing.JButton;
40 import javax.swing.JCheckBox;
41 import javax.swing.JComboBox;
42 import javax.swing.JFrame;
43 import javax.swing.JInternalFrame;
44 import javax.swing.JLabel;
45 import javax.swing.JPanel;
46 import javax.swing.JScrollPane;
47 import javax.swing.JTabbedPane;
48 import javax.swing.JTable;
49 import javax.swing.JTextField;
50 import javax.swing.event.ChangeEvent;
51 import javax.swing.event.ChangeListener;
52 import javax.swing.event.DocumentEvent;
53 import javax.swing.event.DocumentListener;
54
55 @SuppressWarnings("serial")
56 /**
57  * GUI layout for structure chooser 
58  * @author tcnofoegbu
59  *
60  */
61 public abstract class GStructureChooser extends JPanel implements
62         ItemListener
63 {
64   protected String frameTitle = MessageManager
65           .getString("label.structure_chooser");
66
67   protected JInternalFrame mainFrame = new JInternalFrame(frameTitle);
68
69   protected JComboBox<FilterOption> cmb_filterOption = new JComboBox<FilterOption>();
70
71   protected AlignmentPanel ap;
72
73   protected JLabel lbl_result = new JLabel(
74           MessageManager.getString("label.select"));
75
76   protected JButton btn_view = new JButton();
77
78   protected JButton btn_cancel = new JButton();
79
80   protected JButton btn_pdbFromFile = new JButton();
81
82   protected JTextField txt_search = new JTextField(14);
83
84   private JPanel pnl_actions = new JPanel();
85
86   private JPanel pnl_filter = new JPanel();
87
88   private JPanel pnl_idInput = new JPanel(new FlowLayout());
89
90   private JPanel pnl_fileChooser = new JPanel(new FlowLayout());
91
92   private JPanel pnl_idInputBL = new JPanel(new BorderLayout());
93
94   private JPanel pnl_fileChooserBL = new JPanel(new BorderLayout());
95
96   protected JPanel pnl_switchableViews = new JPanel(new CardLayout());
97
98   protected CardLayout layout_switchableViews = (CardLayout) (pnl_switchableViews
99           .getLayout());
100
101   private BorderLayout mainLayout = new BorderLayout();
102
103   protected JCheckBox chk_rememberSettings = new JCheckBox(
104           MessageManager.getString("label.dont_ask_me_again"));
105
106   protected JCheckBox chk_invertFilter = new JCheckBox(
107           MessageManager.getString("label.invert"));
108
109   protected ImageIcon loadingImage = new ImageIcon(getClass().getResource(
110           "/images/loading.gif"));
111
112   protected ImageIcon goodImage = new ImageIcon(getClass().getResource(
113           "/images/good.png"));
114
115   protected ImageIcon errorImage = new ImageIcon(getClass().getResource(
116           "/images/error.png"));
117
118   protected JLabel lbl_loading = new JLabel(loadingImage);
119
120   protected JLabel lbl_pdbManualFetchStatus = new JLabel(errorImage);
121
122   protected JLabel lbl_fromFileStatus = new JLabel(errorImage);
123
124
125   protected AssciateSeqPanel idInputAssSeqPanel = new AssciateSeqPanel();
126
127   protected AssciateSeqPanel fileChooserAssSeqPanel = new AssciateSeqPanel();
128
129   protected static final String VIEWS_FILTER = "VIEWS_FILTER";
130
131   protected static final String VIEWS_FROM_FILE = "VIEWS_FROM_FILE";
132
133   protected static final String VIEWS_ENTER_ID = "VIEWS_ENTER_ID";
134
135   protected JTable tbl_summary = new JTable();
136
137   protected JScrollPane scrl_foundStructures = new JScrollPane(
138           tbl_summary);
139
140   private JTabbedPane tabbedPane = new JTabbedPane();
141
142   private PDBDocFieldPreferences pdbDocFieldPrefs = new PDBDocFieldPreferences(
143           PreferenceSource.STRUCTURE_CHOOSER);
144
145   public GStructureChooser()
146   {
147     try
148     {
149       jbInit();
150       mainFrame.setVisible(false);
151       mainFrame.invalidate();
152       mainFrame.pack();
153     } catch (Exception e)
154     {
155       e.printStackTrace();
156     }
157   }
158
159   /**
160    * Initializes the GUI default properties
161    * 
162    * @throws Exception
163    */
164   private void jbInit() throws Exception
165   {
166     tbl_summary.setAutoCreateRowSorter(true);
167     btn_view.setFont(new java.awt.Font("Verdana", 0, 12));
168     btn_view.setText(MessageManager.getString("action.view"));
169     btn_view.addActionListener(new java.awt.event.ActionListener()
170     {
171       public void actionPerformed(ActionEvent e)
172       {
173         ok_ActionPerformed();
174       }
175     });
176     btn_cancel.setFont(new java.awt.Font("Verdana", 0, 12));
177     btn_cancel.setText(MessageManager.getString("action.cancel"));
178     btn_cancel.addActionListener(new java.awt.event.ActionListener()
179     {
180       public void actionPerformed(ActionEvent e)
181       {
182         mainFrame.dispose();
183       }
184     });
185
186     btn_pdbFromFile.setFont(new java.awt.Font("Verdana", 0, 12));
187     String btn_title = MessageManager.getString("label.select_pdb_file");
188     btn_pdbFromFile.setText(btn_title + "              ");
189     btn_pdbFromFile.addActionListener(new java.awt.event.ActionListener()
190     {
191       public void actionPerformed(ActionEvent e)
192       {
193         pdbFromFile_actionPerformed();
194       }
195     });
196
197     scrl_foundStructures.setPreferredSize(new Dimension(500, 300));
198     scrl_foundStructures
199             .setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
200
201     cmb_filterOption.setFont(new java.awt.Font("Verdana", 0, 12));
202     chk_invertFilter.setFont(new java.awt.Font("Verdana", 0, 12));
203     chk_rememberSettings.setFont(new java.awt.Font("Verdana", 0, 12));
204
205
206     txt_search.setToolTipText(MessageManager
207             .getString("label.enter_pdb_id"));
208     cmb_filterOption.setToolTipText(MessageManager
209             .getString("info.select_filter_option"));
210     txt_search.getDocument().addDocumentListener(new DocumentListener()
211     {
212       @Override
213       public void insertUpdate(DocumentEvent e)
214       {
215         txt_search_ActionPerformed();
216       }
217
218       @Override
219       public void removeUpdate(DocumentEvent e)
220       {
221         txt_search_ActionPerformed();
222       }
223
224       @Override
225       public void changedUpdate(DocumentEvent e)
226       {
227         txt_search_ActionPerformed();
228       }
229     });
230
231     cmb_filterOption.addItemListener(this);
232     chk_invertFilter.addItemListener(this);
233
234     pnl_actions.add(chk_rememberSettings);
235     pnl_actions.add(btn_view);
236     pnl_actions.add(btn_cancel);
237
238     // pnl_filter.add(lbl_result);
239     pnl_filter.add(cmb_filterOption);
240     pnl_filter.add(lbl_loading);
241     pnl_filter.add(chk_invertFilter);
242     lbl_loading.setVisible(false);
243
244     pnl_idInput.add(txt_search);
245     pnl_idInput.add(lbl_pdbManualFetchStatus);
246
247     pnl_fileChooser.add(btn_pdbFromFile);
248     pnl_fileChooser.add(lbl_fromFileStatus);
249
250     pnl_fileChooserBL.add(fileChooserAssSeqPanel, BorderLayout.NORTH);
251     pnl_fileChooserBL.add(pnl_fileChooser, BorderLayout.CENTER);
252
253     pnl_idInputBL.add(idInputAssSeqPanel, BorderLayout.NORTH);
254     pnl_idInputBL.add(pnl_idInput, BorderLayout.CENTER);
255     
256     final String foundStructureSummary = MessageManager
257             .getString("label.found_structures_summary");
258
259     ChangeListener changeListener = new ChangeListener()
260     {
261       public void stateChanged(ChangeEvent changeEvent)
262       {
263         JTabbedPane sourceTabbedPane = (JTabbedPane) changeEvent
264                 .getSource();
265         int index = sourceTabbedPane.getSelectedIndex();
266         if (sourceTabbedPane.getTitleAt(index)
267                 .equals(foundStructureSummary))
268         {
269           tabRefresh();
270         }
271       }
272     };
273     tabbedPane.addChangeListener(changeListener);
274     tabbedPane.setPreferredSize(new Dimension(500, 300));
275     tabbedPane.add(foundStructureSummary, scrl_foundStructures);
276     tabbedPane.add(
277             MessageManager.getString("label.configure_displayed_columns"),
278             pdbDocFieldPrefs);
279     
280
281     pnl_switchableViews.add(pnl_fileChooserBL, VIEWS_FROM_FILE);
282     pnl_switchableViews.add(pnl_idInputBL, VIEWS_ENTER_ID);
283     pnl_switchableViews.add(tabbedPane, VIEWS_FILTER);
284     
285     this.setLayout(mainLayout);
286     this.add(pnl_filter, java.awt.BorderLayout.NORTH);
287     this.add(pnl_switchableViews, java.awt.BorderLayout.CENTER);
288     this.add(pnl_actions, java.awt.BorderLayout.SOUTH);
289
290     mainFrame.setVisible(true);
291     mainFrame.setContentPane(this);
292     mainFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
293     Desktop.addInternalFrame(mainFrame, frameTitle, 800, 400);
294   }
295
296   
297   @Override
298   /**
299    * Event listener for the 'filter' combo-box and 'invert' check-box
300    */
301   public void itemStateChanged(ItemEvent e)
302   {
303     stateChanged(e);
304   }
305
306   /**
307    * This inner class provides the data model for the structure filter combo-box
308    * 
309    * @author tcnofoegbu
310    *
311    */
312   public class FilterOption
313   {
314     private String name;
315
316     private String value;
317
318     private String view;
319
320     public FilterOption(String name, String value, String view)
321     {
322       this.name = name;
323       this.value = value;
324       this.view = view;
325     }
326
327     public String getName()
328     {
329       return name;
330     }
331
332     public void setName(String name)
333     {
334       this.name = name;
335     }
336
337     public String getValue()
338     {
339       return value;
340     }
341
342     public void setValue(String value)
343     {
344       this.value = value;
345     }
346
347     public String getView()
348     {
349       return view;
350     }
351
352     public void setView(String view)
353     {
354       this.view = view;
355     }
356
357     public String toString()
358     {
359       return this.name;
360     }
361   }
362
363   /**
364    * This inner class provides the provides the data model for associate
365    * sequence combo-box - cmb_assSeq
366    * 
367    * @author tcnofoegbu
368    *
369    */
370   public class AssociateSeqOptions
371   {
372     private SequenceI sequence;
373     private String name;
374
375     public AssociateSeqOptions(SequenceI seq)
376     {
377       this.sequence = seq;
378       this.name = (seq.getName().length() >= 23) ? seq.getName().substring(
379               0, 23) : seq.getName();
380     }
381
382     public AssociateSeqOptions(String name, SequenceI seq)
383     {
384       this.name = name;
385       this.sequence = seq;
386     }
387
388     public String toString()
389     {
390       return name;
391     }
392
393     public String getName()
394     {
395       return name;
396     }
397
398     public void setName(String name)
399     {
400       this.name = name;
401     }
402
403     public SequenceI getSequence()
404     {
405       return sequence;
406     }
407
408     public void setSequence(SequenceI sequence)
409     {
410       this.sequence = sequence;
411     }
412
413   }
414
415   /**
416    * This inner class holds the Layout and configuration of the panel which
417    * handles association of manually fetched structures to a unique sequence
418    * when more than one sequence selection is made
419    * 
420    * @author tcnofoegbu
421    *
422    */
423   public class AssciateSeqPanel extends JPanel implements ItemListener
424   {
425     private JComboBox<AssociateSeqOptions> cmb_assSeq = new JComboBox<AssociateSeqOptions>();
426
427     private JLabel lbl_associateSeq = new JLabel();
428
429     public AssciateSeqPanel()
430     {
431       this.setLayout(new FlowLayout());
432       this.add(cmb_assSeq);
433       this.add(lbl_associateSeq);
434       cmb_assSeq.setToolTipText(MessageManager
435               .getString("info.associate_wit_sequence"));
436       cmb_assSeq.addItemListener(this);
437     }
438
439     public void loadCmbAssSeq()
440     {
441       populateCmbAssociateSeqOptions(cmb_assSeq, lbl_associateSeq);
442     }
443
444     public JComboBox<AssociateSeqOptions> getCmb_assSeq()
445     {
446       return cmb_assSeq;
447     }
448
449     public void setCmb_assSeq(JComboBox<AssociateSeqOptions> cmb_assSeq)
450     {
451       this.cmb_assSeq = cmb_assSeq;
452     }
453
454     @Override
455     public void itemStateChanged(ItemEvent e)
456     {
457       if (e.getStateChange() == ItemEvent.SELECTED)
458       {
459         cmbAssSeqStateChanged();
460       }
461     }
462   }
463
464   public JComboBox<FilterOption> getCmbFilterOption()
465   {
466     return cmb_filterOption;
467   }
468
469   protected abstract void stateChanged(ItemEvent e);
470
471   protected abstract void updateCurrentView();
472
473   protected abstract void populateFilterComboBox();
474
475   protected abstract void ok_ActionPerformed();
476
477   protected abstract void pdbFromFile_actionPerformed();
478
479   protected abstract void txt_search_ActionPerformed();
480
481   public abstract void populateCmbAssociateSeqOptions(
482           JComboBox<AssociateSeqOptions> cmb_assSeq, JLabel lbl_associateSeq);
483
484   public abstract void cmbAssSeqStateChanged();
485
486   public abstract void tabRefresh();
487 }