2 * Jalview - A Sequence Alignment Editor and Viewer
\r
3 * Copyright (C) 2005 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle
\r
5 * This program is free software; you can redistribute it and/or
\r
6 * modify it under the terms of the GNU General Public License
\r
7 * as published by the Free Software Foundation; either version 2
\r
8 * of the License, or (at your option) any later version.
\r
10 * This program is distributed in the hope that it will be useful,
\r
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
\r
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
\r
13 * GNU General Public License for more details.
\r
15 * You should have received a copy of the GNU General Public License
\r
16 * along with this program; if not, write to the Free Software
\r
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
\r
21 /*///////////////////////////////////////////////////////////////////
\r
22 // This file was taken from java forum
\r
23 // Re: JFileChooser functioning like normal Windows Apps FileChooser
\r
25 // http://forum.java.sun.com/thread.jspa?forumID=57&threadID=327712
\r
26 *///////////////////////////////////////////////////////////////////
\r
31 import java.awt.event.*;
\r
35 import javax.swing.*;
\r
36 import javax.swing.plaf.*;
\r
37 import javax.swing.plaf.basic.*;
\r
38 import javax.swing.plaf.metal.*;
\r
39 import javax.swing.table.*;
\r
41 public class JalviewFileChooser extends JFileChooser
\r
44 private static final int COLUMN_FILENAME = 0;
\r
45 private static final int COLUMN_FILESIZE = 1;
\r
46 private static final int COLUMN_FILETYPE = 2;
\r
47 private static final int COLUMN_FILEDATE = 3;
\r
48 private static final int COLUMN_FILEATTR = 4;
\r
49 private static final int COLUMN_COLCOUNT = 5;
\r
50 private static String[] COLUMNS = null;
\r
53 public JalviewFileChooser(String dir, String [] suffix, String [] desc, String selected)
\r
57 JalviewFileFilter chosen = null;
\r
58 for(int i=0; i<suffix.length; i++)
\r
60 JalviewFileFilter jvf = new JalviewFileFilter(suffix[i], desc[i]);
\r
61 addChoosableFileFilter(jvf);
\r
62 if(selected!=null && selected.equalsIgnoreCase(desc[i]))
\r
66 setFileFilter(chosen);
\r
70 public String getSelectedFormat()
\r
73 String format = getFileFilter().getDescription();
\r
75 if (format.toUpperCase().startsWith("JALVIEW"))
\r
77 else if (format.toUpperCase().startsWith("FASTA"))
\r
79 else if (format.toUpperCase().startsWith("MSF"))
\r
81 else if (format.toUpperCase().startsWith("CLUSTAL"))
\r
83 else if (format.toUpperCase().startsWith("BLC"))
\r
85 else if (format.toUpperCase().startsWith("PIR"))
\r
87 else if (format.toUpperCase().startsWith("PFAM"))
\r
92 public JalviewFileChooser(String dir)
\r
98 public int showSaveDialog(Component parent) throws HeadlessException {
\r
99 setDialogType(SAVE_DIALOG);
\r
100 int ret = showDialog(parent, null);
\r
102 if(getFileFilter() instanceof JalviewFileFilter)
\r
104 JalviewFileFilter jvf = (JalviewFileFilter) getFileFilter();
\r
105 if (!jvf.accept(getSelectedFile()))
\r
107 String withExtension = getSelectedFile() + "." + jvf.getAcceptableExtension();
\r
108 setSelectedFile(new File(withExtension));
\r
112 if(ret == JalviewFileChooser.APPROVE_OPTION && getSelectedFile().exists() )
\r
114 int confirm = JOptionPane.showConfirmDialog(parent,
\r
115 "Overwrite existing file?",
\r
117 JOptionPane.YES_NO_OPTION);
\r
118 if(confirm!=JOptionPane.YES_OPTION)
\r
119 ret = this.CANCEL_OPTION;
\r
127 if (COLUMNS == null)
\r
129 Locale l = getLocale();
\r
130 COLUMNS = new String[]{
\r
131 UIManager.getString("FileChooser.fileNameHeaderText",l),
\r
132 UIManager.getString("FileChooser.fileSizeHeaderText",l),
\r
133 UIManager.getString("FileChooser.fileTypeHeaderText",l),
\r
134 UIManager.getString("FileChooser.fileDateHeaderText",l),
\r
135 UIManager.getString("FileChooser.fileAttrHeaderText",l)
\r
140 /**************************************************************************
\r
141 * Always create the local UI
\r
143 *************************************************************************/
\r
144 public final void setUI(ComponentUI comp)
\r
146 super.setUI(new UI(this));
\r
149 /**************************************************************************
\r
150 * Internal implementation of Metal LookAndFeel to create the table sorting
\r
152 *************************************************************************/
\r
153 private final static class UI extends MetalFileChooserUI
\r
155 private DirectoryModel model;
\r
157 /**************************************************************************
\r
158 * Must be overridden to extend
\r
160 *************************************************************************/
\r
161 public UI(JFileChooser e)
\r
166 /**************************************************************************
\r
167 * Overridden to create our own model
\r
168 *************************************************************************/
\r
169 protected final void createModel()
\r
171 model = new DirectoryModel(getFileChooser());
\r
174 /**************************************************************************
\r
175 * Overridden to get our own model
\r
177 *************************************************************************/
\r
178 public final BasicDirectoryModel getModel() { return model; }
\r
180 /**************************************************************************
\r
181 * Calls the default method then adds a MouseListener to the JTable
\r
184 *************************************************************************/
\r
185 protected final JPanel createDetailsView(JFileChooser chooser)
\r
187 final JPanel panel = super.createDetailsView(chooser);
\r
189 //Since we can't access MetalFileChooserUI's private member detailsTable
\r
190 //directly, we have to find it in the JPanel
\r
191 final JTable tbl = findJTable(panel.getComponents());
\r
194 //Fix the columns so they can't be rearranged, if we don't do this
\r
195 //we would need to keep track when each column is moved
\r
196 tbl.getTableHeader().setReorderingAllowed(false);
\r
198 //Add a mouselistener to listen for clicks on column headers
\r
199 tbl.getTableHeader().addMouseListener(new MouseAdapter(){
\r
200 public void mouseClicked(MouseEvent e)
\r
202 //Only process single clicks
\r
203 if (e.getClickCount() > 1) return;
\r
205 final int col = tbl.getTableHeader().columnAtPoint(e.getPoint());
\r
206 if (col == COLUMN_FILENAME || col == COLUMN_FILESIZE ||
\r
207 col == COLUMN_FILEDATE)
\r
208 model.sort(col,tbl);
\r
215 /**************************************************************************
\r
216 * Finds the JTable in the panel so we can add MouseListener
\r
219 *************************************************************************/
\r
220 private final static JTable findJTable(Component[] comp)
\r
222 for (int i=0;i<comp.length;i++)
\r
224 if (comp[i] instanceof JTable)
\r
226 return (JTable)comp[i];
\r
228 if (comp[i] instanceof Container)
\r
230 JTable tbl = findJTable(((Container)comp[i]).getComponents());
\r
231 if (tbl != null) return tbl;
\r
238 /***************************************************************************
\r
239 * Implementation of BasicDirectoryModel that sorts the Files by column
\r
240 **************************************************************************/
\r
241 private final static class DirectoryModel extends BasicDirectoryModel
\r
246 /**************************************************************************
\r
247 * Must be overridden to extend BasicDirectoryModel
\r
249 *************************************************************************/
\r
250 DirectoryModel(JFileChooser chooser)
\r
256 /**************************************************************************
\r
257 * Supposedly this is not used anymore, hopefully not. We implemented
\r
258 * some basic attempt at sorting just in case
\r
262 *************************************************************************/
\r
263 protected final boolean lt(File a, File b)
\r
265 System.out.println("DEBUG:LT called?");
\r
266 boolean less = false;
\r
269 case COLUMN_FILEDATE:
\r
270 less = a.lastModified() > b.lastModified();
\r
272 case COLUMN_FILESIZE:
\r
273 less = a.length() > b.length();
\r
276 less = a.getName().compareToIgnoreCase(b.getName()) > 0;
\r
279 if (ascending) return less = !less;
\r
283 /**************************************************************************
\r
284 * Resorts the JFileChooser table based on new column
\r
286 *************************************************************************/
\r
287 protected final void sort(int c, JTable tbl)
\r
289 //Set column and order
\r
291 ascending = !ascending;
\r
292 String indicator = " (^)";
\r
294 indicator = " (v)";
\r
296 final JTableHeader th = tbl.getTableHeader();
\r
297 final TableColumnModel tcm = th.getColumnModel();
\r
299 for (int i=0;i<JalviewFileChooser.COLUMN_COLCOUNT;i++)
\r
301 final TableColumn tc = tcm.getColumn( i ); // the column to change
\r
302 tc.setHeaderValue( COLUMNS[i] );
\r
305 final TableColumn tc = tcm.getColumn( col ); // the column to change
\r
306 tc.setHeaderValue( COLUMNS[col] + indicator );
\r
310 //Requery the file listing
\r
311 validateFileCache();
\r
314 /**************************************************************************
\r
315 * Sorts the data based on current column setting
\r
317 *************************************************************************/
\r
318 protected final void sort(Vector data)
\r
322 case COLUMN_FILEDATE:
\r
323 Collections.sort(data,new Comparator(){
\r
324 public int compare(Object o1,Object o2)
\r
327 final File a = (File)o1;
\r
328 final File b = (File)o2;
\r
329 if (a.lastModified() > b.lastModified())
\r
331 else if (a.lastModified() == b.lastModified())
\r
341 case COLUMN_FILESIZE:
\r
342 Collections.sort(data,new Comparator(){
\r
343 public int compare(Object o1,Object o2)
\r
346 final File a = (File)o1;
\r
347 final File b = (File)o2;
\r
348 if (a.length() > b.length())
\r
350 else if (a.length() == b.length())
\r
360 case COLUMN_FILENAME:
\r
361 Collections.sort(data,new Comparator(){
\r
362 public int compare(Object o1,Object o2)
\r
364 final File a = (File)o1;
\r
365 final File b = (File)o2;
\r
367 return a.getName().compareToIgnoreCase(b.getName());
\r
369 return -1 * a.getName().compareToIgnoreCase(b.getName());
\r