source: josm/trunk/src/org/openstreetmap/josm/actions/SaveActionBase.java@ 327

Last change on this file since 327 was 327, checked in by framm, 17 years ago
File size: 5.5 KB
Line 
1//License: GPL. Copyright 2007 by Immanuel Scholz and others
2package org.openstreetmap.josm.actions;
3
4import static org.openstreetmap.josm.tools.I18n.tr;
5
6import java.awt.event.ActionEvent;
7import java.io.File;
8import java.io.FileOutputStream;
9import java.io.FileInputStream;
10import java.io.FileNotFoundException;
11import java.io.IOException;
12
13import javax.swing.JFileChooser;
14import javax.swing.JOptionPane;
15import javax.swing.filechooser.FileFilter;
16
17import org.openstreetmap.josm.Main;
18import org.openstreetmap.josm.data.osm.OsmPrimitive;
19import org.openstreetmap.josm.gui.layer.OsmDataLayer;
20import org.openstreetmap.josm.io.OsmWriter;
21
22public abstract class SaveActionBase extends DiskAccessAction {
23
24 private OsmDataLayer layer;
25
26 public SaveActionBase(String name, String iconName, String tooltip, int shortCut, int modifiers, OsmDataLayer layer) {
27 super(name, iconName, tooltip, shortCut, modifiers);
28 this.layer = layer;
29 }
30
31 public void actionPerformed(ActionEvent e) {
32 OsmDataLayer layer = this.layer;
33 if (layer == null && Main.map != null && Main.map.mapView.getActiveLayer() instanceof OsmDataLayer)
34 layer = (OsmDataLayer)Main.map.mapView.getActiveLayer();
35 if (layer == null)
36 layer = Main.main.editLayer();
37
38 if (!checkSaveConditions(layer))
39 return;
40
41
42 File file = getFile(layer);
43 if (file == null)
44 return;
45
46 save(file, layer);
47
48 layer.name = file.getName();
49 layer.associatedFile = file;
50 Main.parent.repaint();
51 }
52
53 protected abstract File getFile(OsmDataLayer layer);
54
55 /**
56 * Checks whether it is ok to launch a save (whether we have data,
57 * there is no conflict etc...)
58 * @return <code>true</code>, if it is save to save.
59 */
60 public boolean checkSaveConditions(OsmDataLayer layer) {
61 if (Main.map == null) {
62 JOptionPane.showMessageDialog(Main.parent, tr("No document open so nothing to save."));
63 return false;
64 }
65 if (isDataSetEmpty(layer) && JOptionPane.NO_OPTION == JOptionPane.showConfirmDialog(Main.parent,tr("The document contains no data. Save anyway?"), tr("Empty document"), JOptionPane.YES_NO_OPTION))
66 return false;
67 if (!Main.map.conflictDialog.conflicts.isEmpty()) {
68 int answer = JOptionPane.showConfirmDialog(Main.parent,
69 tr("There are unresolved conflicts. Conflicts will not be saved and handled as if you rejected all. Continue?"),tr("Conflicts"), JOptionPane.YES_NO_OPTION);
70 if (answer != JOptionPane.YES_OPTION)
71 return false;
72 }
73 return true;
74 }
75
76 public static File openFileDialog() {
77 JFileChooser fc = createAndOpenFileChooser(false, false);
78 if (fc == null)
79 return null;
80
81 File file = fc.getSelectedFile();
82
83 String fn = file.getPath();
84 if (fn.indexOf('.') == -1) {
85 FileFilter ff = fc.getFileFilter();
86 if (ff instanceof ExtensionFileFilter)
87 fn = "." + ((ExtensionFileFilter)ff).defaultExtension;
88 else
89 fn += ".osm";
90 file = new File(fn);
91 }
92 return file;
93 }
94
95 private static void copy(File src, File dst) throws IOException {
96 FileInputStream srcStream;
97 FileOutputStream dstStream;
98 try {
99 srcStream = new FileInputStream(src);
100 dstStream = new FileOutputStream(dst);
101 } catch (FileNotFoundException e) {
102 JOptionPane.showMessageDialog(Main.parent, tr("Could not back up file.")+"\n"+e.getMessage());
103 return;
104 }
105 byte buf[] = new byte[1<<16];
106 int len;
107 while ((len = srcStream.read(buf)) != -1) {
108 dstStream.write(buf, 0, len);
109 }
110 srcStream.close();
111 dstStream.close();
112 }
113
114 public static void save(File file, OsmDataLayer layer) {
115 File tmpFile = null;
116 try {
117 if (ExtensionFileFilter.filters[ExtensionFileFilter.GPX].acceptName(file.getPath())) {
118 GpxExportAction.exportGpx(file, layer);
119 } else if (ExtensionFileFilter.filters[ExtensionFileFilter.OSM].acceptName(file.getPath())) {
120 // use a tmp file because if something errors out in the
121 // process of writing the file, we might just end up with
122 // a truncated file. That can destroy lots of work.
123 if (file.exists()) {
124 tmpFile = new File(file.getPath() + "~");
125 copy(file, tmpFile);
126 }
127 OsmWriter.output(new FileOutputStream(file), new OsmWriter.All(layer.data, false));
128 if (tmpFile != null && !Main.pref.getBoolean("save.keepbackup"))
129 tmpFile.delete();
130 } else if (ExtensionFileFilter.filters[ExtensionFileFilter.CSV].acceptName(file.getPath())) {
131 JOptionPane.showMessageDialog(Main.parent, tr("CSV output not supported yet."));
132 return;
133 } else {
134 JOptionPane.showMessageDialog(Main.parent, tr("Unknown file extension."));
135 return;
136 }
137 layer.cleanData(null, false);
138 } catch (IOException e) {
139 e.printStackTrace();
140 JOptionPane.showMessageDialog(Main.parent, tr("An error occurred while saving.")+"\n"+e.getMessage());
141 }
142 try {
143 // if the file save failed, then the tempfile will not
144 // be deleted. So, restore the backup if we made one.
145 if (tmpFile != null && tmpFile.exists()) {
146 copy(tmpFile, file);
147 }
148 } catch (IOException e) {
149 e.printStackTrace();
150 JOptionPane.showMessageDialog(Main.parent, tr("An error occurred while restoring backup file.")+"\n"+e.getMessage());
151 }
152 }
153
154 /**
155 * Check the data set if it would be empty on save. It is empty, if it contains
156 * no objects (after all objects that are created and deleted without beeing
157 * transfered to the server have been removed).
158 *
159 * @return <code>true</code>, if a save result in an empty data set.
160 */
161 private boolean isDataSetEmpty(OsmDataLayer layer) {
162 for (OsmPrimitive osm : layer.data.allNonDeletedPrimitives())
163 if (!osm.deleted || osm.id > 0)
164 return false;
165 return true;
166 }
167}
Note: See TracBrowser for help on using the repository browser.