2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
\r
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
\r
5 * This file is part of Jalview.
\r
7 * Jalview is free software: you can redistribute it and/or
\r
8 * modify it under the terms of the GNU General Public License
\r
9 * as published by the Free Software Foundation, either version 3
\r
10 * of the License, or (at your option) any later version.
\r
12 * Jalview is distributed in the hope that it will be useful, but
\r
13 * WITHOUT ANY WARRANTY; without even the implied warranty
\r
14 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
\r
15 * PURPOSE. See the GNU General Public License for more details.
\r
17 * You should have received a copy of the GNU General Public License
\r
18 * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
\r
19 * The Jalview Authors are detailed in the 'AUTHORS' file.
\r
21 package jalview.appletgui;
\r
23 import jalview.bin.JalviewLite;
\r
24 import jalview.datamodel.Alignment;
\r
25 import jalview.datamodel.AlignmentView;
\r
26 import jalview.datamodel.ColumnSelection;
\r
27 import jalview.datamodel.SeqCigar;
\r
28 import jalview.datamodel.SequenceI;
\r
29 import jalview.util.MessageManager;
\r
30 import jalview.viewmodel.PCAModel;
\r
32 import java.awt.BorderLayout;
\r
33 import javax.swing.JButton;
\r
34 import javax.swing.JCheckBoxMenuItem;
\r
35 import java.awt.Color;
\r
36 import java.awt.FlowLayout;
\r
37 import javax.swing.JFrame;
\r
38 import javax.swing.JLabel;
\r
39 import javax.swing.JMenu;
\r
40 import javax.swing.JMenuBar;
\r
41 import javax.swing.JMenuItem;
\r
42 import javax.swing.JPanel;
\r
43 import java.awt.event.ActionEvent;
\r
44 import java.awt.event.ActionListener;
\r
45 import java.awt.event.ItemEvent;
\r
46 import java.awt.event.ItemListener;
\r
48 public class PCAPanel extends EmbmenuFrame implements Runnable,
\r
49 ActionListener, ItemListener
\r
59 public PCAPanel(AlignViewport av)
\r
64 } catch (Exception e)
\r
66 e.printStackTrace();
\r
69 for (int i = 1; i < 8; i++)
\r
71 xCombobox.addItem("dim " + i);
\r
72 yCombobox.addItem("dim " + i);
\r
73 zCombobox.addItem("dim " + i);
\r
77 boolean selected = av.getSelectionGroup() != null
\r
78 && av.getSelectionGroup().getSize() > 0;
\r
79 AlignmentView seqstrings = av.getAlignmentView(selected);
\r
80 boolean nucleotide = av.getAlignment().isNucleotide();
\r
84 seqs = av.getAlignment().getSequencesArray();
\r
88 seqs = av.getSelectionGroup().getSequencesInOrder(av.getAlignment());
\r
90 SeqCigar sq[] = seqstrings.getSequences();
\r
91 int length = sq[0].getWidth();
\r
93 for (int i = 0; i < seqs.length; i++)
\r
95 if (sq[i].getWidth() != length)
\r
98 .println("Sequences must be equal length for PCA analysis");
\r
102 pcaModel = new PCAModel(seqstrings, seqs, nucleotide);
\r
104 rc = new RotatableCanvas(av);
\r
105 embedMenuIfNeeded(rc);
\r
106 add(rc, BorderLayout.CENTER);
\r
108 JalviewLite.addFrame(this,
\r
109 MessageManager.getString("label.principal_component_analysis"),
\r
112 Thread worker = new Thread(this);
\r
121 // TODO progress indicator
\r
122 calcSettings.setEnabled(false);
\r
123 rc.setEnabled(false);
\r
126 nuclSetting.setState(pcaModel.isNucleotide());
\r
127 protSetting.setState(!pcaModel.isNucleotide());
\r
129 // ////////////////
\r
130 xCombobox.select(0);
\r
131 yCombobox.select(1);
\r
132 zCombobox.select(2);
\r
134 pcaModel.updateRc(rc);
\r
135 // rc.invalidate();
\r
136 top = pcaModel.getTop();
\r
137 } catch (OutOfMemoryError x)
\r
139 System.err.println("Out of memory when calculating PCA.");
\r
142 calcSettings.setEnabled(true);
\r
144 // TODO revert progress indicator
\r
145 rc.setEnabled(true);
\r
150 void doDimensionChange()
\r
157 int dim1 = top - xCombobox.getSelectedIndex();
\r
158 int dim2 = top - yCombobox.getSelectedIndex();
\r
159 int dim3 = top - zCombobox.getSelectedIndex();
\r
160 pcaModel.updateRcView(dim1, dim2, dim3);
\r
162 rc.rotmat.setIdentity();
\r
164 rc.paint(rc.getGraphics());
\r
167 public void actionPerformed(ActionEvent evt)
\r
169 if (evt.getSource() == inputData)
\r
171 showOriginalData();
\r
173 if (evt.getSource() == resetButton)
\r
175 xCombobox.select(0);
\r
176 yCombobox.select(1);
\r
177 zCombobox.select(2);
\r
178 doDimensionChange();
\r
180 if (evt.getSource() == values)
\r
182 values_actionPerformed();
\r
186 public void itemStateChanged(ItemEvent evt)
\r
188 if (evt.getSource() == xCombobox)
\r
190 xCombobox_actionPerformed();
\r
192 else if (evt.getSource() == yCombobox)
\r
194 yCombobox_actionPerformed();
\r
196 else if (evt.getSource() == zCombobox)
\r
198 zCombobox_actionPerformed();
\r
200 else if (evt.getSource() == labels)
\r
202 labels_itemStateChanged(evt);
\r
204 else if (evt.getSource() == nuclSetting)
\r
206 if (!pcaModel.isNucleotide())
\r
208 pcaModel.setNucleotide(true);
\r
209 new Thread(this).start();
\r
212 else if (evt.getSource() == protSetting)
\r
214 if (pcaModel.isNucleotide())
\r
216 pcaModel.setNucleotide(false);
\r
217 new Thread(this).start();
\r
222 protected void xCombobox_actionPerformed()
\r
224 doDimensionChange();
\r
227 protected void yCombobox_actionPerformed()
\r
229 doDimensionChange();
\r
232 protected void zCombobox_actionPerformed()
\r
234 doDimensionChange();
\r
237 public void values_actionPerformed()
\r
240 CutAndPasteTransfer cap = new CutAndPasteTransfer(false, null);
\r
241 JFrame frame = new JFrame();
\r
243 JalviewLite.addFrame(frame,
\r
244 MessageManager.getString("label.pca_details"), 500, 500);
\r
246 cap.setText(pcaModel.getDetails());
\r
249 void showOriginalData()
\r
251 // decide if av alignment is sufficiently different to original data to
\r
252 // warrant a new window to be created
\r
253 // create new alignmnt window with hidden regions (unhiding hidden regions
\r
254 // yields unaligned seqs)
\r
255 // or create a selection box around columns in alignment view
\r
256 // test Alignment(SeqCigar[])
\r
260 // we try to get the associated view's gap character
\r
261 // but this may fail if the view was closed...
\r
262 gc = av.getGapCharacter();
\r
263 } catch (Exception ex)
\r
267 Object[] alAndColsel = pcaModel.getSeqtrings()
\r
268 .getAlignmentAndColumnSelection(gc);
\r
270 if (alAndColsel != null && alAndColsel[0] != null)
\r
272 Alignment al = new Alignment((SequenceI[]) alAndColsel[0]);
\r
273 AlignFrame af = new AlignFrame(al, av.applet,
\r
274 "Original Data for PCA", false);
\r
276 af.viewport.setHiddenColumns((ColumnSelection) alAndColsel[1]);
\r
280 public void labels_itemStateChanged(ItemEvent itemEvent)
\r
282 rc.showLabels(labels.isSelected());
\r
285 JPanel jPanel2 = new JPanel();
\r
287 JLabel jLabel1 = new JLabel();
\r
289 JLabel jLabel2 = new JLabel();
\r
291 JLabel jLabel3 = new JLabel();
\r
293 protected Choice xCombobox = new Choice();
\r
295 protected Choice yCombobox = new Choice();
\r
297 protected Choice zCombobox = new Choice();
\r
299 protected JButton resetButton = new JButton();
\r
301 FlowLayout flowLayout1 = new FlowLayout();
\r
303 BorderLayout borderLayout1 = new BorderLayout();
\r
305 JMenuBar menuBar1 = new JMenuBar();
\r
307 JMenu menu1 = new JMenu();
\r
309 JMenu menu2 = new JMenu();
\r
311 JMenu calcSettings = new JMenu();
\r
313 protected JCheckBoxMenuItem labels = new JCheckBoxMenuItem();
\r
315 protected JCheckBoxMenuItem protSetting = new JCheckBoxMenuItem();
\r
317 protected JCheckBoxMenuItem nuclSetting = new JCheckBoxMenuItem();
\r
319 JMenuItem values = new JMenuItem();
\r
321 JMenuItem inputData = new JMenuItem();
\r
323 private void jbInit() throws Exception
\r
325 this.setLayout(borderLayout1);
\r
326 jPanel2.setLayout(flowLayout1);
\r
327 jLabel1.setFont(new java.awt.Font("Verdana", 0, 12));
\r
328 jLabel1.setText("x=");
\r
329 jLabel2.setFont(new java.awt.Font("Verdana", 0, 12));
\r
330 jLabel2.setText("y=");
\r
331 jLabel3.setFont(new java.awt.Font("Verdana", 0, 12));
\r
332 jLabel3.setText("z=");
\r
333 jPanel2.setBackground(Color.white);
\r
334 zCombobox.setFont(new java.awt.Font("Verdana", 0, 12));
\r
335 zCombobox.addItemListener(this);
\r
336 yCombobox.setFont(new java.awt.Font("Verdana", 0, 12));
\r
337 yCombobox.addItemListener(this);
\r
338 xCombobox.setFont(new java.awt.Font("Verdana", 0, 12));
\r
339 xCombobox.addItemListener(this);
\r
340 resetButton.setFont(new java.awt.Font("Verdana", 0, 12));
\r
341 resetButton.setLabel(MessageManager.getString("action.reset"));
\r
342 resetButton.addActionListener(this);
\r
343 this.setJMenuBar(menuBar1);
\r
344 menu1.setLabel(MessageManager.getString("action.file"));
\r
345 menu2.setLabel(MessageManager.getString("action.view"));
\r
346 calcSettings.setLabel(MessageManager.getString("action.change_params"));
\r
347 labels.setLabel(MessageManager.getString("label.labels"));
\r
348 labels.addItemListener(this);
\r
349 values.setLabel(MessageManager.getString("label.output_values"));
\r
350 values.addActionListener(this);
\r
351 inputData.setLabel(MessageManager.getString("label.input_data"));
\r
352 nuclSetting.setLabel(MessageManager
\r
353 .getString("label.nucleotide_matrix"));
\r
354 nuclSetting.addItemListener(this);
\r
355 protSetting.setLabel(MessageManager.getString("label.protein_matrix"));
\r
356 protSetting.addItemListener(this);
\r
357 this.add(jPanel2, BorderLayout.SOUTH);
\r
358 jPanel2.add(jLabel1, null);
\r
359 jPanel2.add(xCombobox, null);
\r
360 jPanel2.add(jLabel2, null);
\r
361 jPanel2.add(yCombobox, null);
\r
362 jPanel2.add(jLabel3, null);
\r
363 jPanel2.add(zCombobox, null);
\r
364 jPanel2.add(resetButton, null);
\r
365 menuBar1.add(menu1);
\r
366 menuBar1.add(menu2);
\r
367 menuBar1.add(calcSettings);
\r
370 menu1.add(inputData);
\r
371 calcSettings.add(nuclSetting);
\r
372 calcSettings.add(protSetting);
\r
373 inputData.addActionListener(this);
\r