Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.plugin / org.gvsig.app / org.gvsig.app.mainplugin / src / main / java / org / gvsig / app / extension / ProjectExtension.java @ 41076

History | View | Annotate | Download (22.1 KB)

1
/**
2
 * gvSIG. Desktop Geographic Information System.
3
 *
4
 * Copyright (C) 2007-2013 gvSIG Association.
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 3
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 * For any additional information, do not hesitate to contact us
22
 * at info AT gvsig.com, or visit our website www.gvsig.com.
23
 */
24
package org.gvsig.app.extension;
25

    
26
import java.awt.Component;
27
import java.io.File;
28
import java.text.MessageFormat;
29
import java.util.ArrayList;
30
import java.util.Iterator;
31
import java.util.List;
32
import java.util.prefs.Preferences;
33

    
34
import javax.swing.JOptionPane;
35
import javax.swing.SwingUtilities;
36

    
37
import org.slf4j.Logger;
38
import org.slf4j.LoggerFactory;
39
import org.apache.commons.io.FilenameUtils;
40
import org.gvsig.andami.IconThemeHelper;
41
import org.gvsig.andami.Launcher;
42
import org.gvsig.andami.Launcher.TerminationProcess;
43
import org.gvsig.andami.PluginServices;
44
import org.gvsig.andami.messages.NotificationManager;
45
import org.gvsig.andami.plugins.Extension;
46
import org.gvsig.andami.plugins.IExtension;
47
import org.gvsig.andami.plugins.status.IExtensionStatus;
48
import org.gvsig.andami.plugins.status.IUnsavedData;
49
import org.gvsig.andami.plugins.status.UnsavedData;
50
import org.gvsig.andami.ui.mdiManager.IWindow;
51
import org.gvsig.andami.ui.mdiManager.WindowInfo;
52
import org.gvsig.andami.ui.wizard.UnsavedDataPanel;
53
import org.gvsig.app.ApplicationLocator;
54
import org.gvsig.app.ApplicationManager;
55
import org.gvsig.app.project.Project;
56
import org.gvsig.app.project.ProjectManager;
57
import org.gvsig.app.project.documents.gui.ProjectWindow;
58
import org.gvsig.app.project.documents.view.ViewManager;
59
import org.gvsig.gui.beans.swing.JFileChooser;
60
import org.gvsig.tools.ToolsLocator;
61
import org.gvsig.tools.extensionpoint.ExtensionPointManager;
62
import org.gvsig.tools.persistence.exception.PersistenceException;
63
import org.gvsig.utils.GenericFileFilter;
64
import org.gvsig.utils.save.AfterSavingListener;
65
import org.gvsig.utils.save.BeforeSavingListener;
66
import org.gvsig.utils.save.SaveEvent;
67
import org.gvsig.utils.swing.threads.IMonitorableTask;
68

    
69
/**
70
 * Extension que proporciona controles para crear proyectos nuevos, abrirlos y
71
 * guardarlos. Adem?s los tipos de tabla que soporta el proyecto son a?adidos en
72
 * esta clase.
73
 * 
74
 * @author Fernando Gonz?lez Cort?s
75
 */
76
public class ProjectExtension extends Extension implements IExtensionStatus {
77
        private static final Logger LOG = LoggerFactory
78
                        .getLogger(ProjectExtension.class);
79

    
80
        private static String projectPath = null;
81
        private ProjectWindow projectFrame;
82
        private Project p;
83
        private String lastSavePath;
84
        private WindowInfo seedProjectWindow;
85
        public static final String PROJECT_FILE_CHOOSER_ID = "PROJECT_FILECHOOSER_ID";
86
        /**
87
         * Use UTF-8 for encoding, as it can represent characters from any language.
88
         * 
89
         * Another sensible option would be encoding =
90
         * System.getProperty("file.encoding"); but this would need some extra
91
         * testing.
92
         * 
93
         * @deprecated see PersistentManager
94
         */
95
        public static String PROJECTENCODING = "UTF-8";
96

    
97
        private List<BeforeSavingListener> beforeSavingListeners = new ArrayList<BeforeSavingListener>();
98

    
99
        private List<AfterSavingListener> afterSavingListeners = new ArrayList<AfterSavingListener>();
100

    
101
        /**
102
         * @see com.iver.mdiApp.plugins.IExtension#initialize()
103
         */
104
        public void initialize() {
105
                // try {
106
                // Class.forName("javax.media.jai.EnumeratedParameter");
107
                // } catch (ClassNotFoundException e) {
108
                // NotificationManager
109
                // .addError(
110
                // "La m?quina virtual con la que se ejecuta gvSIG no tiene JAI instalado",
111
                // e);
112
                // }
113

    
114
                initializeDocumentActionsExtensionPoint();
115
                registerIcons();
116
        }
117

    
118
        private void registerIcons() {
119
                IconThemeHelper.registerIcon("action", "application-project-new", this);
120
                IconThemeHelper
121
                                .registerIcon("action", "application-project-open", this);
122
                IconThemeHelper
123
                                .registerIcon("action", "application-project-save", this);
124
                IconThemeHelper.registerIcon("action", "application-project-save-as",
125
                                this);
126

    
127
                IconThemeHelper.registerIcon("project", "project-icon", this);
128
        }
129

    
130
        private void loadInitialProject() {
131
                String[] theArgs = PluginServices.getArguments();
132
                String lastArg = theArgs[theArgs.length - 1];
133
                if (lastArg != null) {
134
                        if (lastArg.toLowerCase().endsWith(
135
                                        Project.FILE_EXTENSION.toLowerCase())) {
136
                                LOG.info("Loading project '" + lastArg + "'.");
137
                                try {
138
                                        File projectFile = new File(lastArg);
139
                                        setProject(readProject(projectFile));
140
                                        PluginServices.getMainFrame().setTitle(
141
                                                        projectFile.getName());
142
                                        projectPath = projectFile.getAbsolutePath();
143
                                        return;
144
                                } catch (Exception ex) {
145
                                        LOG.warn("Can't load project from file '" + lastArg + "'.",
146
                                                        ex);
147
                                        ApplicationManager application = ApplicationLocator
148
                                                        .getManager();
149
                                        application.messageDialog("_Can_not_open_the_project",
150
                                                        "_Open_project", JOptionPane.WARNING_MESSAGE);
151
                                }
152
                        }
153
                }
154
                setProject(ProjectManager.getInstance().createProject());
155
                p.setName(PluginServices.getText(this, "untitled"));
156
                p.setModified(false);
157
                PluginServices.getMainFrame().setTitle(
158
                                PluginServices.getText(this, "sin_titulo"));
159
                setProject(p);
160
                showProjectWindow();
161
        }
162

    
163
        /**
164
         * @see com.iver.mdiApp.plugins.IExtension#postInitialize()
165
         */
166
        public void postInitialize() {
167
                registerDocuments();
168
                SwingUtilities.invokeLater(new Runnable() {
169
                        public void run() {
170
                                loadInitialProject();
171
                        }
172
                });
173
        }
174

    
175
        public ProjectWindow getProjectFrame() {
176
                if (projectFrame == null) {
177
                        projectFrame = new ProjectWindow();
178
                }
179
                return projectFrame;
180
        }
181

    
182
        /**
183
         * Muestra la ventana con el gestor de proyectos.
184
         */
185
        public void showProjectWindow() {
186
                if (seedProjectWindow != null) {
187
                        if (seedProjectWindow.isClosed()) {
188
                                // if it was closed, we just don't open the window now
189
                                seedProjectWindow.setClosed(false);
190
                                return;
191
                        }
192
                        WindowInfo winProps = seedProjectWindow;
193
                        seedProjectWindow = null;
194
                        PluginServices.getMDIManager().addWindow(getProjectFrame());
195
                        PluginServices.getMDIManager().changeWindowInfo(getProjectFrame(),
196
                                        winProps);
197
                } else {
198
                        PluginServices.getMDIManager().addWindow(getProjectFrame());
199
                }
200
        }
201

    
202
        /**
203
         * Muestra la ventana con el gestor de proyectos, con las propiedades de
204
         * ventana especificadas.
205
         */
206
        public void showProjectWindow(WindowInfo wi) {
207
                seedProjectWindow = wi;
208
                showProjectWindow();
209
        }
210

    
211
        /**
212
         * Guarda el proyecto actual en disco.
213
         */
214
        private boolean saveProject() {
215
                boolean saved = false;
216
                // if (p.getPath() == null) {
217
                if (projectPath == null) {
218
                        saved = saveAsProject(null);
219
                } else {
220
                        long t1, t2;
221
                        t1 = System.currentTimeMillis();
222
                        saved = writeProject(new File(projectPath), p, false);
223
                        t2 = System.currentTimeMillis();
224
                        PluginServices.getLogger().info(
225
                                        "Project saved. " + (t2 - t1) + " miliseconds");
226
                        getProjectFrame().refreshControls();
227
                }
228
                return saved;
229
        }
230

    
231
        private boolean saveAsProject(File file) {
232
                boolean saved = false;
233

    
234
                if (lastSavePath == null) {
235
                        lastSavePath = projectPath;
236
                }
237

    
238
                if (file == null) {
239
                        Preferences prefs = Preferences.userRoot().node("gvsig.foldering");
240
                        JFileChooser jfc = new JFileChooser(PROJECT_FILE_CHOOSER_ID,
241
                                        prefs.get("ProjectsFolder", null));
242

    
243
                        jfc.setDialogTitle(PluginServices.getText(this, "guardar_proyecto"));
244
                        jfc.addChoosableFileFilter(new GenericFileFilter(
245
                                        Project.FILE_EXTENSION, MessageFormat.format(PluginServices
246
                                                        .getText(this, "tipo_fichero_proyecto"),
247
                                                        Project.FILE_EXTENSION)));
248

    
249
                        if (jfc.showSaveDialog((Component) PluginServices.getMainFrame()) != JFileChooser.APPROVE_OPTION) {
250
                                return saved;
251
                        }
252
                        file = jfc.getSelectedFile();
253
                }
254

    
255
                if (!(file.getPath().toLowerCase().endsWith(Project.FILE_EXTENSION
256
                                .toLowerCase()))) {
257
                        file = new File(file.getPath() + Project.FILE_EXTENSION);
258
                }
259
                saved = writeProject(file, p);
260
                String filePath = file.getAbsolutePath();
261
                lastSavePath = filePath.substring(0,
262
                                filePath.lastIndexOf(File.separatorChar));
263

    
264
                getProjectFrame().refreshControls();
265
                return saved;
266
        }
267

    
268
        /**
269
         * Checks whether the project and related unsaved data is modified, and
270
         * allows the user to save it.
271
         * 
272
         * @return true if the data has been correctly saved, false otherwise
273
         */
274
        private boolean askSave() {
275
                if (p != null && p.hasChanged()) {
276
                        TerminationProcess process = Launcher.getTerminationProcess();
277
                        UnsavedDataPanel panel = process.getUnsavedDataPanel();
278
                        panel.setHeaderText(PluginServices.getText(this,
279
                                        "_Select_resources_to_save_before_closing_current_project"));
280
                        panel.setAcceptText(
281
                                        PluginServices.getText(this, "save_resources"),
282
                                        PluginServices
283
                                                        .getText(this,
284
                                                                        "Save_the_selected_resources_and_close_current_project"));
285
                        panel.setCancelText(PluginServices.getText(this, "Cancel"),
286
                                        PluginServices.getText(this, "Return_to_current_project"));
287
                        int closeCurrProj;
288
                        try {
289
                                closeCurrProj = process.manageUnsavedData();
290
                                if (closeCurrProj == JOptionPane.NO_OPTION) {
291
                                        // the user chose to return to current project
292
                                        return false;
293
                                }
294
                        } catch (Exception e) {
295
                                LOG.error("Some data can not be saved", e);
296
                        }
297
                }
298
                return true;
299
        }
300

    
301
        public void execute(String command) {
302
                this.execute(command, null);
303
        }
304

    
305
        public void execute(String actionCommand, Object[] args) {
306
                if (actionCommand.equals("application-project-new")) {
307
                        if (!askSave()) {
308
                                return;
309
                        }
310

    
311
                        projectPath = null;
312
                        // ProjectDocument.initializeNUMS();
313
                        PluginServices.getMDIManager().closeAllWindows();
314
                        setProject(ProjectManager.getInstance().createProject());
315
                        getProjectFrame().setProject(p);
316
                        showProjectWindow();
317
                        PluginServices.getMainFrame().setTitle(
318
                                        PluginServices.getText(this, "sin_titulo"));
319
                } else if (actionCommand.equals("application-project-open")) {
320
                        if (!askSave()) {
321
                                return;
322
                        }
323
                        File projectFile = null;
324

    
325
                        if (args != null && args.length > 0 && args[0] != null) {
326
                                if (args[0] instanceof File) {
327
                                        projectFile = (File) args[0];
328
                                } else if (args[0] instanceof String) {
329
                                        projectFile = new File((String) args[0]);
330
                                        if (!projectFile.exists()) {
331
                                                LOG.warn("Can't load project '"
332
                                                                + projectFile.getAbsolutePath()
333
                                                                + "', file not exist.");
334
                                                projectFile = null;
335
                                        }
336
                                }
337
                        }
338

    
339
                        if (projectFile == null) {
340
                                Preferences prefs = Preferences.userRoot().node(
341
                                                "gvsig.foldering");
342
                                JFileChooser jfc = new JFileChooser(PROJECT_FILE_CHOOSER_ID,
343
                                                prefs.get("ProjectsFolder", null));
344
                                jfc.addChoosableFileFilter(new GenericFileFilter(
345
                                                Project.FILE_EXTENSION, PluginServices.getText(this,
346
                                                                "tipo_fichero_proyecto")));
347

    
348
                                if (jfc.showOpenDialog((Component) PluginServices
349
                                                .getMainFrame()) != JFileChooser.APPROVE_OPTION) {
350
                                        return;
351
                                }
352
                                // ProjectDocument.initializeNUMS();
353
                                PluginServices.getMDIManager().closeAllWindows();
354

    
355
                                projectFile = jfc.getSelectedFile();
356
                        }
357

    
358
                        Project o = readProject(projectFile);
359
                        setPath(projectFile.getAbsolutePath());
360
                        // lastPath = getPath();
361
                        if (o != null) {
362
                                setProject(o);
363
                        }
364

    
365
                        getProjectFrame().setProject(p);
366
                        PluginServices.getMainFrame().setTitle(projectFile.getName());
367
                        getProjectFrame().refreshControls();
368

    
369
                        // p.restoreWindowProperties();
370

    
371
                } else if (actionCommand.equals("application-project-save")) {
372
                        saveProject();
373
                } else if (actionCommand.equals("application-project-save-as")) {
374
                        File file = null;
375
                        if (args != null && args.length > 0 && args[0] != null) {
376
                                if (args[0] instanceof File) {
377
                                        file = (File) args[0];
378
                                } else if (args[0] instanceof String) {
379
                                        file = new File((String) args[0]);
380
                                }
381
                        }
382
                        saveAsProject(file);
383
                }
384

    
385
        }
386

    
387
        /**
388
         * Escribe el proyecto en XML.
389
         * 
390
         * @param file
391
         *            Fichero.
392
         * @param p
393
         *            Proyecto.
394
         */
395
        public boolean writeProject(File file, Project p) {
396
                return writeProject(file, p, true);
397
        }
398

    
399
        /**
400
         * Escribe el proyecto en XML. Pero permite decidir si se pide confirmaci?n
401
         * para sobreescribir
402
         * 
403
         * @param file
404
         *            Fichero.
405
         * @param p
406
         *            Proyecto.
407
         * @param askConfirmation
408
         *            boolean
409
         */
410
        public boolean writeProject(File file, Project p, boolean askConfirmation) {
411
                if (askConfirmation && file.exists()) {
412
                        int resp = JOptionPane.showConfirmDialog((Component) PluginServices
413
                                        .getMainFrame(), PluginServices.getText(this,
414
                                        "fichero_ya_existe_seguro_desea_guardarlo"), PluginServices
415
                                        .getText(this, "guardar"), JOptionPane.YES_NO_OPTION);
416
                        if (resp != JOptionPane.YES_OPTION) {
417
                                return false;
418
                        }
419
                }
420
                NotificationManager.addInfo(PluginServices.getText(this,
421
                                "writinng_project") + ": " + file.getName());
422

    
423
                // write it out as XML
424
                try {
425
                        fireBeforeSavingFileEvent(new SaveEvent(this,
426
                                        SaveEvent.BEFORE_SAVING, file));
427
                        p.saveState(file);
428
                        fireAfterSavingFileEvent(new SaveEvent(this,
429
                                        SaveEvent.AFTER_SAVING, file));
430

    
431
                        PluginServices.getMainFrame().setTitle(file.getName());
432
                        setPath(file.toString());
433

    
434
                } catch (PersistenceException e) {
435
                        String messagestack = e.getLocalizedMessageStack();
436
                        NotificationManager.addError(
437
                                        PluginServices.getText(this, "error_writing_project")
438
                                                        + ": " + file.getName() + "\n" + messagestack, e);
439
                        return false;
440
                } catch (Exception e) {
441
                        NotificationManager.addError(
442
                                        PluginServices.getText(this, "error_writing_project")
443
                                                        + ": " + file.getName(), e);
444
                        return false;
445
                }
446
                NotificationManager.addInfo(PluginServices.getText(this,
447
                                "wrote_project") + ": " + file.getName());
448
                return true;
449
        }
450

    
451
        public Project readProject(String path) {
452
                Project project = ProjectManager.getInstance().createProject();
453

    
454
                project.loadState(new File(path));
455
                return (Project) project;
456
        }
457

    
458
        /**
459
         * Lee del XML el proyecto.<br>
460
         * <br>
461
         * 
462
         * Reads the XML of the project.<br>
463
         * It returns a project object holding all needed info that is not linked to
464
         * the Project Dialog. <br>
465
         * In case you want the project to be linked to the window you must set this
466
         * object to the extension:<br>
467
         * 
468
         * <b>Example:</b><br>
469
         * 
470
         * ...<br>
471
         * ...<br>
472
         * Project p = ProjectExtension.readProject(projectFile);<br>
473
         * ProjectExtension.setProject(p); ...<br>
474
         * ...<br>
475
         * 
476
         * @param file
477
         *            Fichero.
478
         * 
479
         * @return Project
480
         * 
481
         */
482
        public Project readProject(File file) {
483
                Project project = ProjectManager.getInstance().createProject();
484

    
485
                project.loadState(file);
486
                return (Project) project;
487
        }
488

    
489
        /**
490
         * Devuelve el proyecto.
491
         * 
492
         * @return Proyecto.
493
         */
494
        public Project getProject() {
495
                return p;
496
        }
497

    
498
        /**
499
         * @see org.gvsig.andami.plugins.IExtension#isEnabled()
500
         */
501
        public boolean isEnabled() {
502
                return true;
503
        }
504

    
505
        /**
506
         * @see org.gvsig.andami.plugins.IExtension#isVisible()
507
         */
508
        public boolean isVisible() {
509
                return true;
510
        }
511

    
512
        /**
513
         * Sets the project
514
         * 
515
         * @param p
516
         */
517
        public void setProject(Project p) {
518
                getProjectFrame().setProject(p);
519
                this.p = p;
520
        }
521

    
522
        private void registerDocuments() {
523
                ViewManager.register();
524
        }
525

    
526
        private void initializeDocumentActionsExtensionPoint() {
527
                ExtensionPointManager epMan = ToolsLocator.getExtensionPointManager();
528
                epMan.add(
529
                                "DocumentActions_View",
530
                                "Context menu options of the view document list"
531
                                                + " in the project window "
532
                                                + "(register instances of "
533
                                                + "org.gvsig.app.project.AbstractDocumentContextMenuAction)");
534
        }
535

    
536
        public static String getPath() {
537
                return projectPath;
538
        }
539

    
540
        public static void setPath(String path) {
541
                projectPath = path;
542
        }
543

    
544
        public IWindow getProjectWindow() {
545
                return getProjectFrame();
546
        }
547

    
548
        public IExtensionStatus getStatus() {
549
                return this;
550
        }
551

    
552
        public boolean hasUnsavedData() {
553
                return p.hasChanged();
554
        }
555

    
556
        public IUnsavedData[] getUnsavedData() {
557
                if (hasUnsavedData()) {
558
                        UnsavedProject data = new UnsavedProject(this);
559
                        IUnsavedData[] dataArray = { data };
560
                        return dataArray;
561
                } else {
562
                        return null;
563
                }
564
        }
565

    
566
        /**
567
         * Implements the IUnsavedData interface to show unsaved projects in the
568
         * Unsavad Data dialog.
569
         * 
570
         * @author Cesar Martinez Izquierdo <cesar.martinez@iver.es>
571
         */
572
        public class UnsavedProject extends UnsavedData {
573

    
574
                public UnsavedProject(IExtension extension) {
575
                        super(extension);
576
                }
577

    
578
                public String getDescription() {
579
                        if (getPath() == null) {
580
                                return PluginServices.getText(ProjectExtension.this,
581
                                                "Unnamed_new_gvsig_project_");
582
                        } else {
583
                                return PluginServices.getText(ProjectExtension.this,
584
                                                "Modified_project_");
585
                        }
586
                }
587

    
588
                public String getResourceName() {
589
                        if (getPath() == null) {
590
                                return PluginServices.getText(ProjectExtension.this, "Unnamed");
591
                        } else {
592
                                return getPath();
593
                        }
594

    
595
                }
596

    
597
                public boolean saveData() {
598
                        return saveProject();
599
                }
600

    
601
                public String getIcon() {
602
                        return "project-icon";
603
                }
604
        }
605

    
606
        public IMonitorableTask[] getRunningProcesses() {
607
                // TODO Auto-generated method stub
608
                return null;
609
        }
610

    
611
        public boolean hasRunningProcesses() {
612
                // TODO Auto-generated method stub
613
                return false;
614
        }
615

    
616
        /**
617
         * Adds the specified before saving listener to receive
618
         * "before saving file events" from this component. If l is null, no
619
         * exception is thrown and no action is performed.
620
         * 
621
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
622
         * 
623
         * @param l
624
         *            the before saving listener.
625
         * @see SaveEvent
626
         * @see BeforeSavingListener
627
         * @see #removeListener(BeforeSavingListener)
628
         * @see #getBeforeSavingListeners
629
         */
630
        public synchronized void addListener(BeforeSavingListener l) {
631
                if (l == null) {
632
                        return;
633
                }
634
                if (!this.beforeSavingListeners.contains(l)) {
635
                        this.beforeSavingListeners.add(l);
636
                }
637
        }
638

    
639
        /**
640
         * Adds the specified after saving listener to receive
641
         * "after saving file events" from this component. If l is null, no
642
         * exception is thrown and no action is performed.
643
         * 
644
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
645
         * 
646
         * @param l
647
         *            the after saving listener.
648
         * @see SaveEvent
649
         * @see AfterSavingListener
650
         * @see #removeListener(AfterSavingListener)
651
         * @see #getAfterSavingListeners()
652
         */
653
        public synchronized void addListener(AfterSavingListener l) {
654
                if (l == null) {
655
                        return;
656
                }
657

    
658
                if (!this.afterSavingListeners.contains(l)) {
659
                        this.afterSavingListeners.add(l);
660
                }
661

    
662
        }
663

    
664
        /**
665
         * Returns an array of all the before saving listeners registered on this
666
         * component.
667
         * 
668
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
669
         * 
670
         * @return all of this component's <code>BeforeSavingListener</code>s or an
671
         *         empty array if no key listeners are currently registered
672
         * 
673
         * @see #addBeforeSavingListener(BeforeSavingListener)
674
         * @see #removeBeforeSavingListener(BeforeSavingListener)
675
         */
676
        public synchronized BeforeSavingListener[] getBeforeSavingListeners() {
677
                return this.beforeSavingListeners
678
                                .toArray(new BeforeSavingListener[] {});
679
        }
680

    
681
        /**
682
         * Returns an array of all the after saving listeners registered on this
683
         * component.
684
         * 
685
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
686
         * 
687
         * @return all of this component's <code>AfterSavingListener</code>s or an
688
         *         empty array if no key listeners are currently registered
689
         * 
690
         * @see #addAfterSavingListener(AfterSavingListener)
691
         * @see #removeAfterSavingListener
692
         */
693
        public synchronized AfterSavingListener[] getAfterSavingListeners() {
694
                return this.afterSavingListeners.toArray(new AfterSavingListener[] {});
695

    
696
        }
697

    
698
        /**
699
         * Removes the specified before saving listener so that it no longer
700
         * receives save file events from this component. This method performs no
701
         * function, nor does it throw an exception, if the listener specified by
702
         * the argument was not previously added to this component. If listener
703
         * <code>l</code> is <code>null</code>, no exception is thrown and no action
704
         * is performed.
705
         * 
706
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
707
         * 
708
         * @param l
709
         *            the before saving listener
710
         * @see SaveEvent
711
         * @see BeforeSavingListener
712
         * @see #addListener(BeforeSavingListener)
713
         * @see #getBeforeSavingListeners()
714
         */
715
        public synchronized void removeListener(BeforeSavingListener l) {
716
                if (l == null) {
717
                        return;
718
                }
719

    
720
                this.beforeSavingListeners.remove(l);
721
        }
722

    
723
        /**
724
         * Removes the specified after saving listener so that it no longer receives
725
         * save file events from this component. This method performs no function,
726
         * nor does it throw an exception, if the listener specified by the argument
727
         * was not previously added to this component. If listener <code>l</code> is
728
         * <code>null</code>, no exception is thrown and no action is performed.
729
         * 
730
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
731
         * 
732
         * @param l
733
         *            the after saving listener
734
         * @see SaveEvent
735
         * @see AfterSavingListener
736
         * @see #addListener(AfterSavingListener)
737
         * @see #getAfterSavingListeners()
738
         */
739
        public synchronized void removeListener(AfterSavingListener l) {
740
                if (l == null) {
741
                        return;
742
                }
743

    
744
                this.afterSavingListeners.remove(l);
745
        }
746

    
747
        /**
748
         * Reports a before saving file event.
749
         * 
750
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
751
         * 
752
         * @param evt
753
         *            the before saving file event
754
         */
755
        protected void fireBeforeSavingFileEvent(SaveEvent evt) {
756
                if ((evt.getID() != SaveEvent.BEFORE_SAVING) || (evt.getFile() == null)) {
757
                        return;
758
                }
759

    
760
                Iterator<BeforeSavingListener> iter = this.beforeSavingListeners
761
                                .iterator();
762

    
763
                while (iter.hasNext()) {
764
                        iter.next().beforeSaving(evt);
765
                }
766
        }
767

    
768
        /**
769
         * Reports a after saving file event.
770
         * 
771
         * @author Pablo Piqueras Bartolom? <pablo.piqueras@iver.es>
772
         * 
773
         * @param evt
774
         *            the after saving file event
775
         */
776
        protected void fireAfterSavingFileEvent(SaveEvent evt) {
777
                if ((evt.getID() != SaveEvent.AFTER_SAVING) || (evt.getFile() == null)) {
778
                        return;
779
                }
780
                Iterator<AfterSavingListener> iter = this.afterSavingListeners
781
                                .iterator();
782

    
783
                while (iter.hasNext()) {
784
                        iter.next().afterSaving(evt);
785
                }
786

    
787
        }
788
}