fiore@0
|
1 package uk.ac.qmul.eecs.ccmi.gui;
|
fiore@0
|
2
|
fiore@0
|
3 import java.awt.Frame;
|
fiore@0
|
4 import java.io.BufferedInputStream;
|
fiore@0
|
5 import java.io.BufferedOutputStream;
|
fiore@0
|
6 import java.io.File;
|
fiore@0
|
7 import java.io.FileInputStream;
|
fiore@0
|
8 import java.io.FileNotFoundException;
|
fiore@0
|
9 import java.io.FileOutputStream;
|
fiore@0
|
10 import java.io.IOException;
|
fiore@0
|
11 import java.io.InputStream;
|
fiore@0
|
12 import java.io.OutputStream;
|
fiore@0
|
13 import java.util.ResourceBundle;
|
fiore@0
|
14
|
fiore@0
|
15 import javax.swing.JFileChooser;
|
fiore@0
|
16 import javax.swing.JOptionPane;
|
fiore@0
|
17
|
fiore@0
|
18 import uk.ac.qmul.eecs.ccmi.gui.filechooser.FileChooser;
|
fiore@0
|
19 import uk.ac.qmul.eecs.ccmi.gui.filechooser.FileChooserFactory;
|
fiore@0
|
20 import uk.ac.qmul.eecs.ccmi.sound.SoundEvent;
|
fiore@0
|
21 import uk.ac.qmul.eecs.ccmi.sound.SoundFactory;
|
fiore@0
|
22 import uk.ac.qmul.eecs.ccmi.utils.PreferencesService;
|
fiore@0
|
23
|
fiore@0
|
24 public abstract class FileService
|
fiore@0
|
25 {
|
fiore@0
|
26
|
fiore@0
|
27 /**
|
fiore@0
|
28 * An Open object encapsulates the stream, name and path of the file that the user selected for opening.
|
fiore@0
|
29 */
|
fiore@0
|
30 public interface Open
|
fiore@0
|
31 {
|
fiore@0
|
32 /**
|
fiore@0
|
33 * Gets the input stream corresponding to the user selection.
|
fiore@0
|
34 * @return the input stream, or null if the user cancels the file selection task
|
fiore@0
|
35 */
|
fiore@0
|
36 InputStream getInputStream() throws IOException ;
|
fiore@0
|
37 /**
|
fiore@0
|
38 * Gets the name of the file that the user selected.
|
fiore@0
|
39 * @return the file name, or null if the user cancels the file selection task
|
fiore@0
|
40 */
|
fiore@0
|
41 String getName() throws IOException ;
|
fiore@0
|
42
|
fiore@0
|
43 /**
|
fiore@0
|
44 * Gets the path of the file that the user selected.
|
fiore@0
|
45 * @return the file path , or null if the user cancels the file selection task
|
fiore@0
|
46 */
|
fiore@0
|
47 String getPath() throws IOException;
|
fiore@0
|
48
|
fiore@0
|
49 }
|
fiore@0
|
50
|
fiore@0
|
51 /**
|
fiore@0
|
52 * A Save object encapsulates the stream and name of the file that the user selected for saving.
|
fiore@0
|
53 */
|
fiore@0
|
54 public interface Save
|
fiore@0
|
55 {
|
fiore@0
|
56 /**
|
fiore@0
|
57 * Gets the output stream corresponding to the user selection.
|
fiore@0
|
58 * @return the output stream, or null if the user cancels the file selection task
|
fiore@0
|
59 */
|
fiore@0
|
60 OutputStream getOutputStream();
|
fiore@0
|
61 /**
|
fiore@0
|
62 * Gets the name of the file that the user selected.
|
fiore@0
|
63 * @return the file name, or null if the user cancels the file selection task
|
fiore@0
|
64 */
|
fiore@0
|
65 String getName();
|
fiore@0
|
66 /**
|
fiore@0
|
67 * Gets the path of the file that the user selected.
|
fiore@0
|
68 * @return the file path, or null if the user cancels the file selection task
|
fiore@0
|
69 */
|
fiore@0
|
70 String getPath();
|
fiore@0
|
71 }
|
fiore@0
|
72
|
fiore@0
|
73 /**
|
fiore@0
|
74 * This class implements a FileService with a JFileChooser
|
fiore@0
|
75 */
|
fiore@0
|
76 public static class ChooserService
|
fiore@0
|
77 {
|
fiore@0
|
78 public ChooserService(File initialDirectory){
|
fiore@0
|
79 useAccessible = Boolean.parseBoolean(PreferencesService.getInstance().get("use_accessible_filechooser", "true"));
|
fiore@0
|
80 fileChooser = FileChooserFactory.getFileChooser(useAccessible);
|
fiore@0
|
81 fileChooser.setCurrentDirectory(initialDirectory);
|
fiore@0
|
82 }
|
fiore@0
|
83
|
fiore@0
|
84 /* If the user cancels the task (presses cancel button or the X at the top left) *
|
fiore@0
|
85 * the CANCEl sound is played (together with the registered playerListeenr if any) */
|
fiore@0
|
86 public FileService.Open open(String defaultDirectory, String defaultFile,
|
fiore@0
|
87 ExtensionFilter filter, Frame frame) throws FileNotFoundException {
|
fiore@0
|
88 fileChooser.resetChoosableFileFilters();
|
fiore@0
|
89 fileChooser.setFileFilter(filter);
|
fiore@0
|
90 if (defaultDirectory != null)
|
fiore@0
|
91 fileChooser.setCurrentDirectory(new File(defaultDirectory));
|
fiore@0
|
92 if (defaultFile == null)
|
fiore@0
|
93 fileChooser.setSelectedFile(null);
|
fiore@0
|
94 else
|
fiore@0
|
95 fileChooser.setSelectedFile(new File(defaultFile));
|
fiore@0
|
96 int response = fileChooser.showOpenDialog(frame);
|
fiore@0
|
97 if (response == JFileChooser.APPROVE_OPTION)
|
fiore@0
|
98 return new OpenImpl(fileChooser.getSelectedFile());
|
fiore@0
|
99 else{
|
fiore@0
|
100 if(useAccessible)
|
fiore@0
|
101 SoundFactory.getInstance().play(SoundEvent.CANCEL);
|
fiore@0
|
102 return new OpenImpl(null);
|
fiore@0
|
103 }
|
fiore@0
|
104 }
|
fiore@0
|
105
|
fiore@0
|
106
|
fiore@0
|
107 /* If the user cancels the task (presses cancel button or the X at the top left) *
|
fiore@0
|
108 * the CANCEl sound is played (together with the registered playerListeenr if any) */
|
fiore@0
|
109 public FileService.Save save(String defaultDirectory, String defaultFile,
|
fiore@0
|
110 ExtensionFilter filter, String removeExtension, String addExtension) throws FileNotFoundException {
|
fiore@0
|
111 fileChooser.resetChoosableFileFilters();
|
fiore@0
|
112 fileChooser.setFileFilter(filter);
|
fiore@0
|
113 if (defaultDirectory == null)
|
fiore@0
|
114 fileChooser.setCurrentDirectory(new File("."));
|
fiore@0
|
115 else
|
fiore@0
|
116 fileChooser.setCurrentDirectory(new File(defaultDirectory));
|
fiore@0
|
117 if (defaultFile != null){
|
fiore@0
|
118 File f = new File(editExtension(defaultFile, removeExtension, addExtension));
|
fiore@0
|
119 if(f.exists())
|
fiore@0
|
120 fileChooser.setSelectedFile(f);
|
fiore@0
|
121 else
|
fiore@0
|
122 fileChooser.setSelectedFile(null);
|
fiore@0
|
123 }else
|
fiore@0
|
124 fileChooser.setSelectedFile(null);
|
fiore@0
|
125 int response = fileChooser.showSaveDialog(null);
|
fiore@0
|
126 if (response == JFileChooser.APPROVE_OPTION){
|
fiore@0
|
127 File f = fileChooser.getSelectedFile();
|
fiore@0
|
128 if (addExtension != null && f.getName().indexOf(".") < 0) // no extension supplied
|
fiore@0
|
129 f = new File(f.getPath() + addExtension);
|
fiore@0
|
130 if (!f.exists()) return new SaveImpl(f);
|
fiore@0
|
131
|
fiore@0
|
132 /* file with this name already exists, we must ask the user to confirm */
|
fiore@0
|
133 ResourceBundle resources = ResourceBundle.getBundle(EditorFrame.class.getName());
|
fiore@0
|
134 if(useAccessible){
|
fiore@0
|
135 int result = SpeechOptionPane.showConfirmDialog(
|
fiore@0
|
136 null,
|
fiore@0
|
137 resources.getString("dialog.overwrite"),
|
fiore@0
|
138 SpeechOptionPane.YES_NO_OPTION);
|
fiore@0
|
139 if (result == SpeechOptionPane.YES_OPTION)
|
fiore@0
|
140 return new SaveImpl(f);
|
fiore@0
|
141 }else{
|
fiore@0
|
142 int result = JOptionPane.showConfirmDialog(
|
fiore@0
|
143 null,
|
fiore@0
|
144 resources.getString("dialog.overwrite"),
|
fiore@0
|
145 null,
|
fiore@0
|
146 JOptionPane.YES_NO_OPTION);
|
fiore@0
|
147 if (result == JOptionPane.YES_OPTION)
|
fiore@0
|
148 return new SaveImpl(f);
|
fiore@0
|
149 }
|
fiore@0
|
150 }
|
fiore@0
|
151 if(useAccessible)
|
fiore@0
|
152 SoundFactory.getInstance().play(SoundEvent.CANCEL);
|
fiore@0
|
153 return new SaveImpl(null);
|
fiore@0
|
154 }
|
fiore@0
|
155
|
fiore@0
|
156 private FileChooser fileChooser;
|
fiore@0
|
157 private boolean useAccessible;
|
fiore@0
|
158 }
|
fiore@0
|
159
|
fiore@0
|
160 public static class DirectService {
|
fiore@0
|
161 public Open open(File file) throws IOException{
|
fiore@0
|
162 return new OpenImpl(file);
|
fiore@0
|
163 }
|
fiore@0
|
164
|
fiore@0
|
165 public Save save(File file) throws IOException{
|
fiore@0
|
166 return new SaveImpl(file);
|
fiore@0
|
167 }
|
fiore@0
|
168 }
|
fiore@0
|
169
|
fiore@0
|
170 private static class SaveImpl implements FileService.Save{
|
fiore@0
|
171 public SaveImpl(File f) throws FileNotFoundException{
|
fiore@0
|
172 if (f != null){
|
fiore@0
|
173 path = f.getPath();
|
fiore@0
|
174 name = getFileNameFromPath(path,false);
|
fiore@0
|
175 out = new BufferedOutputStream(new FileOutputStream(f));
|
fiore@0
|
176 }
|
fiore@0
|
177 }
|
fiore@0
|
178
|
fiore@0
|
179 @Override
|
fiore@0
|
180 public String getName() { return name; }
|
fiore@0
|
181 @Override
|
fiore@0
|
182 public String getPath() {return path; }
|
fiore@0
|
183 @Override
|
fiore@0
|
184 public OutputStream getOutputStream() { return out; }
|
fiore@0
|
185
|
fiore@0
|
186 private String name;
|
fiore@0
|
187 private String path;
|
fiore@0
|
188 private OutputStream out;
|
fiore@0
|
189 }
|
fiore@0
|
190
|
fiore@0
|
191 private static class OpenImpl implements FileService.Open
|
fiore@0
|
192 {
|
fiore@0
|
193 public OpenImpl(File f) throws FileNotFoundException{
|
fiore@0
|
194 if (f != null){
|
fiore@0
|
195 path = f.getPath();
|
fiore@0
|
196 name = getFileNameFromPath(path,false);
|
fiore@0
|
197 in = new BufferedInputStream(new FileInputStream(f));
|
fiore@0
|
198 }
|
fiore@0
|
199 }
|
fiore@0
|
200
|
fiore@0
|
201 @Override
|
fiore@0
|
202 public String getName() { return name; }
|
fiore@0
|
203 @Override
|
fiore@0
|
204 public String getPath() { return path; }
|
fiore@0
|
205 @Override
|
fiore@0
|
206 public InputStream getInputStream() { return in; }
|
fiore@0
|
207
|
fiore@0
|
208 private String path;
|
fiore@0
|
209 private String name;
|
fiore@0
|
210 private InputStream in;
|
fiore@0
|
211 }
|
fiore@0
|
212
|
fiore@0
|
213 /**
|
fiore@0
|
214 Edits the file path so that it ends in the desired
|
fiore@0
|
215 extension.
|
fiore@0
|
216 @param original the file to use as a starting point
|
fiore@0
|
217 @param toBeRemoved the extension that is to be
|
fiore@0
|
218 removed before adding the desired extension. Use
|
fiore@0
|
219 null if nothing needs to be removed.
|
fiore@0
|
220 @param desired the desired extension (e.g. ".png"),
|
fiore@0
|
221 or a | separated list of extensions
|
fiore@0
|
222 @return original if it already has the desired
|
fiore@0
|
223 extension, or a new file with the edited file path
|
fiore@0
|
224 */
|
fiore@0
|
225 public static String editExtension(String original,
|
fiore@0
|
226 String toBeRemoved, String desired){
|
fiore@0
|
227 if (original == null) return null;
|
fiore@0
|
228 int n = desired.indexOf('|');
|
fiore@0
|
229 if (n >= 0) desired = desired.substring(0, n);
|
fiore@0
|
230 String path = original;
|
fiore@0
|
231 if (!path.toLowerCase().endsWith(desired.toLowerCase())){
|
fiore@0
|
232 if (toBeRemoved != null && path.toLowerCase().endsWith(
|
fiore@0
|
233 toBeRemoved.toLowerCase()))
|
fiore@0
|
234 path = path.substring(0, path.length() - toBeRemoved.length());
|
fiore@0
|
235 path = path + desired;
|
fiore@0
|
236 }
|
fiore@0
|
237 return path;
|
fiore@0
|
238 }
|
fiore@0
|
239
|
fiore@0
|
240 public static String getFileNameFromPath(String path,boolean keepExtension){
|
fiore@0
|
241 int index = path.lastIndexOf(System.getProperty("file.separator"));
|
fiore@0
|
242 String name;
|
fiore@0
|
243 if(index == -1)
|
fiore@0
|
244 name = path;
|
fiore@0
|
245 else
|
fiore@0
|
246 name = path.substring(index+1);
|
fiore@0
|
247 if(!keepExtension){
|
fiore@0
|
248 index = name.lastIndexOf('.');
|
fiore@0
|
249 if(index != -1)
|
fiore@0
|
250 name = name.substring(0, index);
|
fiore@0
|
251 }
|
fiore@0
|
252 return name;
|
fiore@0
|
253 }
|
fiore@0
|
254 }
|