Statistics
| Revision:

gvsig-vectorediting / org.gvsig.vectorediting / trunk / org.gvsig.vectorediting / org.gvsig.vectorediting.swing / org.gvsig.vectorediting.swing.impl / src / main / java / org / gvsig / vectorediting / swing / impl / DefaultEditingContext.java @ 673

History | View | Annotate | Download (36.8 KB)

1 159 llmarques
/**
2
 * gvSIG. Desktop Geographic Information System.
3
 *
4
 * Copyright ? 2007-2014 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 2
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 89 llmarques
 */
24 159 llmarques
25 89 llmarques
package org.gvsig.vectorediting.swing.impl;
26
27
import java.awt.BorderLayout;
28
import java.awt.Component;
29 150 llmarques
import java.lang.ref.WeakReference;
30 366 llmarques
import java.util.ArrayList;
31 226 llmarques
import java.util.Set;
32
import java.util.Stack;
33 366 llmarques
import java.util.prefs.PreferenceChangeEvent;
34
import java.util.prefs.PreferenceChangeListener;
35
import java.util.prefs.Preferences;
36 89 llmarques
37 376 llmarques
import javax.swing.JComponent;
38
39 89 llmarques
import org.gvsig.editing.EditingNotification;
40
import org.gvsig.editing.EditingNotificationManager;
41 226 llmarques
import org.gvsig.fmap.dal.exception.DataException;
42 89 llmarques
import org.gvsig.fmap.dal.feature.FeatureStore;
43 226 llmarques
import org.gvsig.fmap.geom.Geometry;
44
import org.gvsig.fmap.geom.GeometryLocator;
45
import org.gvsig.fmap.geom.GeometryManager;
46
import org.gvsig.fmap.geom.primitive.Point;
47
import org.gvsig.fmap.geom.type.GeometryType;
48 89 llmarques
import org.gvsig.fmap.mapcontext.MapContext;
49
import org.gvsig.fmap.mapcontext.layers.CancelationException;
50
import org.gvsig.fmap.mapcontext.layers.FLayer;
51
import org.gvsig.fmap.mapcontext.layers.FLayers;
52
import org.gvsig.fmap.mapcontext.layers.LayerCollectionEvent;
53
import org.gvsig.fmap.mapcontext.layers.LayerCollectionListener;
54
import org.gvsig.fmap.mapcontext.layers.LayerEvent;
55
import org.gvsig.fmap.mapcontext.layers.LayerListener;
56
import org.gvsig.fmap.mapcontext.layers.LayerPositionEvent;
57
import org.gvsig.fmap.mapcontext.layers.vectorial.FLyrVect;
58
import org.gvsig.fmap.mapcontrol.MapControl;
59
import org.gvsig.fmap.mapcontrol.MapControlLocator;
60
import org.gvsig.fmap.mapcontrol.tools.CompoundBehavior;
61
import org.gvsig.fmap.mapcontrol.tools.Behavior.Behavior;
62 226 llmarques
import org.gvsig.tools.ToolsLocator;
63
import org.gvsig.tools.i18n.I18nManager;
64 303 fdiaz
import org.gvsig.tools.observer.BaseNotification;
65
import org.gvsig.tools.observer.Notification;
66 157 llmarques
import org.gvsig.tools.observer.ObservableHelper;
67
import org.gvsig.tools.observer.Observer;
68 89 llmarques
import org.gvsig.utils.console.JDockPanel;
69
import org.gvsig.utils.console.ResponseListener;
70 226 llmarques
import org.gvsig.vectorediting.lib.api.EditingLocator;
71 89 llmarques
import org.gvsig.vectorediting.lib.api.EditingManager;
72 226 llmarques
import org.gvsig.vectorediting.lib.api.EditingService;
73
import org.gvsig.vectorediting.lib.api.EditingServiceInfo;
74
import org.gvsig.vectorediting.lib.api.EditingServiceParameter;
75
import org.gvsig.vectorediting.lib.api.EditingServiceParameter.TYPE;
76 89 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.CreateEditingBehaviorException;
77
import org.gvsig.vectorediting.lib.api.exceptions.EndEditingException;
78 226 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.InvalidEntryException;
79
import org.gvsig.vectorediting.lib.api.exceptions.ParsePointException;
80
import org.gvsig.vectorediting.lib.api.exceptions.ParseValueException;
81 157 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.ServiceInformationException;
82 89 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.StartEditingException;
83 226 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.StartServiceException;
84
import org.gvsig.vectorediting.lib.api.exceptions.StopServiceException;
85 89 llmarques
import org.gvsig.vectorediting.lib.api.exceptions.VectorEditingException;
86
import org.gvsig.vectorediting.swing.api.EditingContext;
87
import org.gvsig.vectorediting.swing.api.EditingSwingLocator;
88
import org.gvsig.vectorediting.swing.api.EditingSwingManager;
89 376 llmarques
import org.gvsig.vectorediting.swing.api.console.EditingConsole;
90
import org.gvsig.vectorediting.swing.impl.console.DefaultEditingConsole;
91 547 llmarques
import org.slf4j.Logger;
92
import org.slf4j.LoggerFactory;
93 89 llmarques
94
public class DefaultEditingContext implements EditingContext {
95
96 109 llmarques
    private static final Logger logger = LoggerFactory
97
        .getLogger(EditingManager.class);
98 89 llmarques
99 150 llmarques
    private WeakReference<MapControl> mapControlReference;
100 89 llmarques
101 383 llmarques
    private WeakReference<MapContext> mapContextReference;
102 150 llmarques
103 109 llmarques
    private EditingCompoundBehavior editingCompoundBehavior;
104 89 llmarques
105 155 llmarques
    private Behavior[] lastAdditionalBehaviors;
106 150 llmarques
107 157 llmarques
    private ObservableHelper observableHelper;
108
109 376 llmarques
    private EditingConsole console;
110 89 llmarques
111 109 llmarques
    private JDockPanel dockConsole = null;
112 89 llmarques
113 109 llmarques
    private boolean isShowConsole = false;
114 89 llmarques
115 226 llmarques
    private Stack<EditingService> serviceStack;
116
117
    private FLyrVect currentLayer;
118
119
    private EditingServiceParameter currentParam;
120
121 438 fdiaz
    private Behavior[] defaultBehaviors;
122
123 109 llmarques
    private LayerListener layerListener = new LayerListener() {
124 89 llmarques
125 109 llmarques
        public void activationChanged(LayerEvent e) {
126
            FLayer layer = e.getSource();
127 89 llmarques
128 127 llmarques
            FLayer[] activeLayers =
129
                layer.getMapContext().getLayers().getActives();
130 130 llmarques
131 227 llmarques
            if ((activeLayers.length == 1) && (layer instanceof FLyrVect)) {
132 127 llmarques
                if (layer.isActive() && layer.isEditing()) {
133 438 fdiaz
                    getMapControl().setTool("VectorEditing");
134
                    setCurrentLayer((FLyrVect) layer);
135 127 llmarques
                    showConsole();
136
                    return;
137
                }
138
            }
139 109 llmarques
140 127 llmarques
            hideConsole();
141 227 llmarques
            if ((getMapControl().getCurrentTool() != null)
142 205 llmarques
                && getMapControl().getCurrentTool().equals("VectorEditing")) {
143 197 llmarques
                getMapControl().setPrevTool();
144
            }
145 89 llmarques
        }
146 109 llmarques
147
        public void drawValueChanged(LayerEvent e) {
148 89 llmarques
        }
149
150 109 llmarques
        public void editionChanged(LayerEvent e) {
151 438 fdiaz
            FLayer layer = e.getSource();
152
153
            if (layer instanceof FLyrVect) {
154
                if (layer.isEditing()) {
155
                    synchronized (DefaultEditingContext.this) {
156 546 llmarques
                        beginEdition((FLyrVect) layer);
157 438 fdiaz
                        showConsole();
158
                    }
159
                } else {
160
                    hideConsole();
161
                }
162
            }
163
164 109 llmarques
        }
165 89 llmarques
166 109 llmarques
        public void nameChanged(LayerEvent e) {
167
        }
168 89 llmarques
169 109 llmarques
        public void visibilityChanged(LayerEvent e) {
170
        }
171
    };
172 89 llmarques
173 366 llmarques
    private PreferenceChangeListener preferenceChangeListener =
174
        new PreferenceChangeListener() {
175
176
            public void preferenceChange(PreferenceChangeEvent evt) {
177
                String key = evt.getKey();
178
                if (key.equalsIgnoreCase("apply-snappers")) {
179
                    boolean newValue = Boolean.parseBoolean(evt.getNewValue());
180
                    getMapControl().setRefentEnabled(newValue);
181
                }
182
            }
183
        };
184
185 109 llmarques
    public DefaultEditingContext(MapControl mapControl) {
186 226 llmarques
187 150 llmarques
        this.mapControlReference = new WeakReference<MapControl>(mapControl);
188 383 llmarques
        this.mapContextReference =
189
            new WeakReference<MapContext>(mapControl.getMapContext());
190 385 llmarques
        this.observableHelper = new ObservableHelper();
191 205 llmarques
192 226 llmarques
        this.serviceStack = new Stack<EditingService>();
193
194 163 llmarques
        addLayerListeners();
195 366 llmarques
        addPreferenceListener();
196 109 llmarques
    }
197 89 llmarques
198 366 llmarques
    private void addPreferenceListener() {
199
        Preferences prefs = Preferences.userRoot().node("snappers");
200
        prefs.addPreferenceChangeListener(preferenceChangeListener);
201
    }
202
203 109 llmarques
    public void activateService(String name) {
204 226 llmarques
205 227 llmarques
        if ((getMapControl() != null)
206
            && getMapControl().hasTool("VectorEditing")) {
207 226 llmarques
208 109 llmarques
            CompoundBehavior editingCompoundBehavior =
209
                getEditingCompoundBehavior();
210 142 llmarques
            getMapControl().setTool("VectorEditing");
211 109 llmarques
            editingCompoundBehavior.setDrawnBehavior(
212
                EditingCompoundBehavior.EDITING_INDEX, true);
213 226 llmarques
214
            EditingManager manager = EditingLocator.getManager();
215
216
            if (currentLayer != null) {
217
218
                EditingService service =
219 227 llmarques
                    manager.getEditingService(name,
220 383 llmarques
                        currentLayer.getFeatureStore(),
221
                        mapContextReference.get());
222 226 llmarques
223
                if (service != null) {
224
225
                    this.enableSelection(false);
226
227
                    try {
228
                        service.start();
229
                    } catch (StartServiceException e) {
230 252 llmarques
231 226 llmarques
                        logger.info(String.format(
232
                            "Can't start the service %1$s", service.getName()),
233
                            e);
234
                        cleanEditingContext();
235
                        return;
236 252 llmarques
237
                    } catch (InvalidEntryException e) {
238
239
                        I18nManager i18nManager = ToolsLocator.getI18nManager();
240 376 llmarques
                        showConsoleMessage("\n"
241
                            + i18nManager.getTranslation("invalid_option"));
242 226 llmarques
                    }
243
244
                    if (!serviceStack.isEmpty()
245
                        && !getActiveService().next().getTypes()
246 245 llmarques
                            .contains(TYPE.GEOMETRY)) {
247 226 llmarques
                        serviceStack.pop();
248
                    }
249
250
                    setActiveService(service);
251 252 llmarques
252 226 llmarques
                    getNextParameter();
253
                }
254
            }
255 109 llmarques
        }
256
    }
257 89 llmarques
258 227 llmarques
    private void addBehaviors(Behavior[] additionalBehavior)
259
        throws CreateEditingBehaviorException {
260
261
        DefaultEditingBehavior editingBehavior;
262
        EditingCompoundBehavior editingCompoundBehavior;
263
264
        if (!getMapControl().hasTool("VectorEditing")) {
265
266
            editingBehavior = new DefaultEditingBehavior(this);
267
            editingCompoundBehavior =
268
                new EditingCompoundBehavior(editingBehavior);
269
            setCompoundBehavior(editingCompoundBehavior);
270
271
            if (additionalBehavior != null) {
272
273
                Behavior[] behaviors =
274
                    new Behavior[additionalBehavior.length + 1];
275
                behaviors[0] = editingCompoundBehavior;
276
277
                for (int i = 0; i < additionalBehavior.length; i++) {
278
                    behaviors[i + 1] = additionalBehavior[i];
279
                }
280
281
                getMapControl().addBehavior("VectorEditing", behaviors);
282
283
                lastAdditionalBehaviors = additionalBehavior;
284
285
            } else {
286
                getMapControl().addBehavior("VectorEditing",
287
                    editingCompoundBehavior);
288
            }
289
290
        } else {
291
            editingCompoundBehavior = getEditingCompoundBehavior();
292
            editingBehavior =
293
                (DefaultEditingBehavior) editingCompoundBehavior
294 245 llmarques
                    .getBehavior(EditingCompoundBehavior.EDITING_INDEX);
295 227 llmarques
            setCompoundBehavior(editingCompoundBehavior);
296
            cleanEditingContext();
297
        }
298
299
    }
300
301
    private void addLayerListeners() {
302
303 383 llmarques
        FLayers layers = mapContextReference.get().getLayers();
304 227 llmarques
305
        layers.addLayerListener(layerListener);
306
307
        layers.addLayerCollectionListener(new LayerCollectionListener() {
308
309 546 llmarques
            public void addLayer(FLayer layer) {
310
                if (layer instanceof FLayers) {
311
                    FLayers layers = (FLayers) layer;
312
                    for (int i = 0; i < layers.getLayersCount(); i++) {
313
                        addLayer(layers.getLayer(i));
314 227 llmarques
                    }
315 546 llmarques
                } else if (layer instanceof FLyrVect) {
316
                    ((FLyrVect) layer).addLayerListener(layerListener);
317 227 llmarques
                }
318
            }
319 546 llmarques
320
            public void layerAdded(LayerCollectionEvent e) {
321
                addLayer(e.getLayers());
322
            }
323 227 llmarques
324
            public void layerAdding(LayerCollectionEvent e)
325
                throws CancelationException {
326
            }
327
328
            public void layerMoved(LayerPositionEvent e) {
329
            }
330
331
            public void layerMoving(LayerPositionEvent e)
332
                throws CancelationException {
333
            }
334 547 llmarques
335
            public void removeLayer(FLayer layer) {
336
                if (layer instanceof FLayers) {
337
                    FLayers layers = (FLayers) layer;
338
                    for (int i = 0; i < layers.getLayersCount(); i++) {
339
                        addLayer(layers.getLayer(i));
340 227 llmarques
                    }
341 547 llmarques
                } else if (layer instanceof FLyrVect) {
342
                    ((FLyrVect) layer).removeLayerListener(layerListener);
343 227 llmarques
                }
344
            }
345
346 547 llmarques
            public void layerRemoved(LayerCollectionEvent e) {
347
                removeLayer(e.getLayers());
348
            }
349
350 227 llmarques
            public void layerRemoving(LayerCollectionEvent e)
351
                throws CancelationException {
352
            }
353
354
            public void visibilityChanged(LayerCollectionEvent e)
355
                throws CancelationException {
356
            }
357
        });
358
    }
359
360
    public void addObserver(Observer o) {
361
        this.observableHelper.addObserver(o);
362
    }
363
364
    private void askQuestion(EditingServiceParameter param) {
365 245 llmarques
        I18nManager i18nManager = ToolsLocator.getI18nManager();
366
        String translation = i18nManager.getTranslation(param.getDescription());
367
        String activeServiceName =
368
            i18nManager.getTranslation(getActiveService().getName());
369 365 llmarques
370 377 fdiaz
        Object defaultValue = param.getDefaultValue();
371
        String strDefaultValue;
372
373
        if (defaultValue != null) {
374 383 llmarques
            if (defaultValue instanceof String) {
375
                strDefaultValue = (String) defaultValue;
376
                strDefaultValue =
377
                    i18nManager.getTranslation((String) defaultValue);
378 377 fdiaz
            } else {
379
                strDefaultValue = defaultValue.toString();
380
            }
381 383 llmarques
            showConsoleMessage("\n" + activeServiceName + "# " + translation
382
                + "<" + strDefaultValue + "> : ");
383 365 llmarques
        } else {
384
            showConsoleMessage("\n" + activeServiceName + "# " + translation
385
                + " : ");
386
        }
387 227 llmarques
    }
388 546 llmarques
389 438 fdiaz
    public synchronized void beginEdition(FLyrVect layer,
390
        Behavior[] additionalBehaviors) {
391 546 llmarques
392
        try{
393
            throw new Exception("Deprecated method");
394
        } catch (Exception e){
395
            logger.info("Deprecated method", e);
396
        }
397
398
        beginEdition(layer);
399
        try {
400
            addBehaviors(additionalBehaviors);
401
        } catch (CreateEditingBehaviorException e1) {
402
            logger.info("Problems adding behaviors to editing context", e1);
403
            getMapControl().setTool("pan");
404
            return;
405
        }
406
    }
407
408
    public synchronized void beginEdition(FLyrVect layer) {
409
410 109 llmarques
        EditingNotificationManager editingNotificationManager =
411
            MapControlLocator.getEditingNotificationManager();
412 89 llmarques
413 109 llmarques
        EditingNotification notification =
414
            editingNotificationManager.notifyObservers(this,
415
                EditingNotification.BEFORE_ENTER_EDITING_STORE, null, layer);
416 89 llmarques
417 109 llmarques
        if (notification.isCanceled()) {
418 130 llmarques
            String msg =
419
                String.format("Edit layer %1$s canceled by somme observer.",
420
                    layer.getName());
421
            logger.info(msg, new StartEditingException(msg, null));
422
            return;
423 109 llmarques
        }
424 546 llmarques
425 226 llmarques
        setCurrentLayer(layer);
426 127 llmarques
427 438 fdiaz
        FeatureStore featureStore = layer.getFeatureStore();
428
        if (!featureStore.isEditing()) {
429
            try {
430
                featureStore.edit();
431
            } catch (Exception e) {
432
                String msg =
433
                    String.format("Can't set %1$s in edit mode",
434
                        featureStore.getName());
435
                logger.info(msg, new VectorEditingException(e));
436
                cleanEditingContext();
437
                return;
438
            }
439 109 llmarques
        }
440 89 llmarques
441 438 fdiaz
        featureStore.addObserver(getMapControl());
442 89 llmarques
443 109 llmarques
        editingNotificationManager.notifyObservers(this,
444
            EditingNotification.AFTER_ENTER_EDITING_STORE, null, layer);
445 150 llmarques
446 366 llmarques
        enableSnapping();
447 89 llmarques
    }
448
449 366 llmarques
    @SuppressWarnings({ "rawtypes", "unchecked" })
450
    private void enableSnapping() {
451
        Preferences prefs = Preferences.userRoot().node("snappers");
452
        if ((prefs.getBoolean("apply-snappers", false) && currentLayer != null)) {
453
            ArrayList layersToSnap =
454
                getMapControl().getMapContext().getLayersToSnap();
455
            if (!layersToSnap.contains(currentLayer)) {
456
                layersToSnap.add(currentLayer);
457
            }
458
        }
459
    }
460
461
    @SuppressWarnings("rawtypes")
462
    private void disableSnapping() {
463
        ArrayList layersToSnap =
464
            getMapControl().getMapContext().getLayersToSnap();
465
        if (layersToSnap.contains(currentLayer)) {
466
            layersToSnap.remove(currentLayer);
467
        }
468
    }
469
470 245 llmarques
    private void changeSelectedTool(String name) {
471 316 llmarques
        if (name.equalsIgnoreCase(DEFAULT_TOOL)) {
472 303 fdiaz
            name = "selection-simple-select-view";
473
            this.getMapControl().setTool("pointSelection");
474
        }
475 365 llmarques
        Notification notification =
476
            new BaseNotification(
477
                EditingContext.CHANGE_SELECTED_TOOL_NOTIFICATION,
478
                new Object[] { name });
479 303 fdiaz
        this.observableHelper.notifyObservers(this, notification);
480 245 llmarques
    }
481
482 227 llmarques
    private void cleanEditingContext() {
483
        serviceStack.clear();
484
        currentParam = null;
485
        this.enableSelection(false);
486
        refreshMenusAndToolBars();
487 89 llmarques
488 227 llmarques
        I18nManager i18nManager = ToolsLocator.getI18nManager();
489
        showConsoleMessage("\n" + i18nManager.getTranslation("select_new_tool")
490
            + "\n");
491
    }
492 127 llmarques
493 227 llmarques
    public void deleteObserver(Observer o) {
494
        this.observableHelper.deleteObserver(o);
495 109 llmarques
    }
496 89 llmarques
497 227 llmarques
    public void deleteObservers() {
498
        this.observableHelper.deleteObservers();
499 142 llmarques
    }
500
501 109 llmarques
    private void discardChanges(FLyrVect layer) throws EndEditingException {
502
        FeatureStore featureStore = layer.getFeatureStore();
503
        try {
504
            featureStore.cancelEditing();
505
        } catch (Exception e) {
506
            throw new EndEditingException(e);
507 89 llmarques
        }
508
    }
509
510 109 llmarques
    private void doAction(FLyrVect layer, int option) {
511
        switch (option) {
512
        case SAVE_CHANGES:
513
            try {
514
                saveChanges(layer);
515
            } catch (VectorEditingException e) {
516 130 llmarques
                String msg =
517
                    String.format("Changes can not be saved in %1$s",
518
                        layer.getName());
519
                logger.info(msg, e);
520 161 llmarques
                return;
521 109 llmarques
            }
522
            break;
523 130 llmarques
524 109 llmarques
        case DISCARD_CHANGES:
525
            try {
526
                discardChanges(layer);
527
            } catch (VectorEditingException e) {
528 130 llmarques
                String msg =
529
                    String.format("Changes can not be discared in %1$s",
530
                        layer.getName());
531
                logger.info(msg, e);
532 161 llmarques
                return;
533 109 llmarques
            }
534
            break;
535 130 llmarques
536 109 llmarques
        case EXPORT_LAYER:
537
            try {
538
                exportLayer(layer);
539
            } catch (VectorEditingException e) {
540 130 llmarques
                String msg =
541
                    String.format("Changes of %1$s can not be exported",
542
                        layer.getName());
543
                logger.info(msg, e);
544 161 llmarques
                return;
545 109 llmarques
            }
546
            break;
547 130 llmarques
548 109 llmarques
        case CANCEL:
549 126 llmarques
            return;
550 109 llmarques
        }
551 127 llmarques
552 226 llmarques
        cleanEditingContext();
553 126 llmarques
        hideConsole();
554 366 llmarques
        disableSnapping();
555 302 fdiaz
        changeSelectedTool(DEFAULT_TOOL);
556 127 llmarques
557 126 llmarques
        FeatureStore featureStore = layer.getFeatureStore();
558 142 llmarques
        featureStore.deleteObserver(getMapControl());
559 89 llmarques
560 109 llmarques
    }
561 89 llmarques
562 226 llmarques
    private void enableSelection(boolean enableSelection) {
563 109 llmarques
        this.editingCompoundBehavior.setDrawnBehavior(
564
            EditingCompoundBehavior.SELECTION_INDEX, enableSelection);
565 89 llmarques
    }
566
567 109 llmarques
    public void endEdition(FLyrVect layer) {
568
        if (layer.isEditing()) {
569
            EditingNotificationManager editingNotificationManager =
570
                MapControlLocator.getEditingNotificationManager();
571 89 llmarques
572 109 llmarques
            EditingNotification notification =
573
                editingNotificationManager.notifyObservers(this,
574
                    EditingNotification.BEFORE_EXIT_EDITING_STORE, null, layer);
575 89 llmarques
576 109 llmarques
            if (notification.isCanceled()) {
577 130 llmarques
                String msg =
578
                    String.format(
579
                        "Stop edit layer %1$s canceled by somme observer.",
580
                        layer.getName());
581
                logger.info(msg, new EndEditingException(msg, null));
582 89 llmarques
583 109 llmarques
            }
584 130 llmarques
585 142 llmarques
            getMapControl().getCanceldraw().setCanceled(true);
586 109 llmarques
            int option;
587
            EditingSwingManager swingManager =
588
                EditingSwingLocator.getSwingManager();
589 130 llmarques
590 672 jjdelcerro
591
            if (layer.isWritable() && getMapControl().getProjection().equals(layer.getProjection()) ) {
592 109 llmarques
                option =
593 142 llmarques
                    swingManager.showPanelSaveOrDiscard(getMapControl(),
594 109 llmarques
                        layer.getName());
595
            } else {
596
                option =
597 142 llmarques
                    swingManager.showPanelExportOrDiscard(getMapControl(),
598 109 llmarques
                        layer.getName());
599
            }
600 89 llmarques
601 109 llmarques
            doAction(layer, option);
602 89 llmarques
603 109 llmarques
            editingNotificationManager.notifyObservers(this,
604
                EditingNotification.AFTER_EXIT_EDITING_STORE, null, layer);
605 89 llmarques
606 109 llmarques
        }
607 89 llmarques
608
    }
609
610 109 llmarques
    private void exportLayer(FLyrVect layer) throws EndEditingException {
611 673 jjdelcerro
        Notification notification = new BaseNotification(EditingContext.EXPORT_LAYER_NOTIFICATION,1);
612
        notification.setValue(layer);
613
        this.observableHelper.notifyObservers(this, notification);
614 109 llmarques
    }
615 89 llmarques
616 227 llmarques
    protected void finishService() {
617
        EditingService lastService = serviceStack.pop();
618
        try {
619
620
            if (!serviceStack.isEmpty()
621
                && getActiveService().next().getTypes().contains(TYPE.GEOMETRY)) {
622
                Geometry geometry = lastService.finish();
623
                if (geometry != null) {
624
                    getActiveService().setValue(geometry);
625
                }
626
            } else {
627
                lastService.finishAndStore();
628
                getMapControl().rePaintDirtyLayers();
629 252 llmarques
630
                I18nManager i18nManager = ToolsLocator.getI18nManager();
631
                showConsoleMessage("\n"
632 316 llmarques
                    + i18nManager.getTranslation(lastService.getName()) + "# "
633 252 llmarques
                    + i18nManager.getTranslation("finished") + "\n");
634 484 fdiaz
                lastService.stop();
635 227 llmarques
                setActiveService(lastService);
636 484 fdiaz
                lastService.start();
637 316 llmarques
                changeSelectedTool(getActiveService().getName());
638 227 llmarques
            }
639
640
        } catch (InvalidEntryException ex) {
641
            I18nManager i18nManager = ToolsLocator.getI18nManager();
642 376 llmarques
            showConsoleMessage("\n"
643
                + i18nManager.getTranslation("invalid_option"));
644 316 llmarques
            changeSelectedTool(getActiveService().getName());
645 227 llmarques
        } catch (VectorEditingException ex) {
646
            logger.info("Can't finish " + lastService.getName(), ex);
647
            cleanEditingContext();
648
            return;
649
        }
650
651
        getNextParameter();
652
    }
653
654
    protected EditingService getActiveService() {
655
        if (!serviceStack.isEmpty()) {
656
            return serviceStack.peek();
657
        }
658
        return null;
659
    }
660
661 376 llmarques
    private EditingConsole getConsolePanel() {
662 109 llmarques
        if (console == null) {
663 376 llmarques
            console = new DefaultEditingConsole(new ResponseListener() {
664
665
                public void acceptResponse(String response) {
666
                    textEntered(response);
667
                }
668
            });
669 109 llmarques
        }
670
        return console;
671
    }
672 89 llmarques
673 227 llmarques
    protected FLyrVect getCurrentLayer() {
674
        return this.currentLayer;
675
    }
676
677
    protected EditingServiceParameter getCurrentParam() {
678
        return this.currentParam;
679
    }
680
681 109 llmarques
    private Component getDockConsole() {
682
        if (dockConsole == null) {
683 376 llmarques
            dockConsole = new JDockPanel((JComponent) getConsolePanel());
684 109 llmarques
        }
685
        return dockConsole;
686 89 llmarques
    }
687
688 224 llmarques
    private DefaultEditingBehavior getEditingBehavior() {
689 160 llmarques
        if (editingCompoundBehavior != null) {
690 224 llmarques
            return (DefaultEditingBehavior) editingCompoundBehavior
691 160 llmarques
                .getBehavior(EditingCompoundBehavior.EDITING_INDEX);
692
        }
693
        return null;
694 89 llmarques
    }
695
696 109 llmarques
    private EditingCompoundBehavior getEditingCompoundBehavior() {
697
        if (editingCompoundBehavior != null) {
698
            return editingCompoundBehavior;
699
        } else {
700
            EditingCompoundBehavior editingCompoundBehavior;
701 89 llmarques
702 109 llmarques
            CompoundBehavior compoundBehavior =
703 142 llmarques
                (CompoundBehavior) getMapControl().getMapTool("VectorEditing");
704 127 llmarques
705 109 llmarques
            if (compoundBehavior instanceof EditingCompoundBehavior) {
706
                editingCompoundBehavior =
707
                    (EditingCompoundBehavior) compoundBehavior;
708
            } else {
709
                editingCompoundBehavior =
710
                    (EditingCompoundBehavior) compoundBehavior.getBehavior(0);
711
            }
712 127 llmarques
713 109 llmarques
            setCompoundBehavior(editingCompoundBehavior);
714
            return editingCompoundBehavior;
715
        }
716 89 llmarques
    }
717
718 227 llmarques
    public MapControl getMapControl() {
719 323 llmarques
        return mapControlReference.get();
720 227 llmarques
    }
721
722 226 llmarques
    protected void getNextParameter() {
723
724
        currentParam = getActiveService().next();
725
726
        if (currentParam == null) {
727
            finishService();
728
        } else {
729
            askQuestion(currentParam);
730
            if (currentParam.getTypes().contains(TYPE.SELECTION)) {
731
                enableSelection(true);
732
            } else if (currentParam.getTypes().contains(TYPE.GEOMETRY)) {
733
                refreshMenusAndToolBars();
734
            }
735
        }
736
    }
737
738 227 llmarques
    protected Stack<EditingService> getServiceStack() {
739
        return this.serviceStack;
740
    }
741
742 109 llmarques
    private void hideConsole() {
743
        isShowConsole = false;
744
        getDockConsole().setVisible(false);
745
    }
746 89 llmarques
747 157 llmarques
    public boolean isServiceCompatible(String name) {
748 224 llmarques
        DefaultEditingBehavior editingBehavior = getEditingBehavior();
749 157 llmarques
750
        if (editingBehavior != null) {
751
752
            try {
753 226 llmarques
                EditingManager manager = EditingLocator.getManager();
754
                EditingServiceInfo serviceInfo = manager.getServiceInfo(name);
755
                GeometryType geoType = null;
756
757
                for (EditingService editingService : getServiceStack()) {
758 316 llmarques
                    EditingServiceParameter parameter = editingService.next();
759
                    if (parameter != null
760
                        && parameter.getTypes().contains(TYPE.GEOMETRY)) {
761 226 llmarques
762 316 llmarques
                        int geometryType = parameter.getGeometryType();
763 226 llmarques
                        int subType = -1;
764 316 llmarques
765 226 llmarques
                        try {
766
                            subType =
767
                                getCurrentLayer().getFeatureStore()
768 245 llmarques
                                    .getDefaultFeatureType()
769
                                    .getDefaultGeometryAttribute()
770
                                    .getGeomType().getSubType();
771 226 llmarques
772
                            geoType =
773
                                GeometryLocator.getGeometryManager()
774 245 llmarques
                                    .getGeometryType(geometryType, subType);
775 226 llmarques
                        } catch (Exception e) {
776
777
                            String msg =
778 316 llmarques
                                String.format(
779
                                    "Problems getting default feature"
780
                                        + " type of %1$s or getting geometry"
781
                                        + " type of %2$s %3$s",
782
                                    getCurrentLayer().getName(), geometryType,
783
                                    subType);
784 226 llmarques
785
                            throw new ServiceInformationException(msg, e);
786
                        }
787
788
                        return serviceInfo.isCompatibleWith(geoType)
789
                            && serviceInfo.createsNewGeometries();
790
                    }
791
                }
792
793
                if (getCurrentLayer() != null) {
794
                    try {
795
                        geoType =
796
                            getCurrentLayer().getFeatureStore()
797 245 llmarques
                                .getDefaultFeatureType()
798
                                .getDefaultGeometryAttribute().getGeomType();
799 226 llmarques
                    } catch (DataException e) {
800
                        String msg =
801
                            String.format("Problems getting default "
802
                                + "feature type of %1$s", getCurrentLayer()
803
                                .getName());
804
                        throw new ServiceInformationException(msg, e);
805
                    }
806
807
                    return serviceInfo.isCompatibleWith(geoType);
808
                }
809
810
                return false;
811 157 llmarques
            } catch (ServiceInformationException e) {
812 365 llmarques
                logger.warn(
813
                    "Problems getting if editing context is compatible with "
814
                        + name, e);
815 157 llmarques
            }
816
        }
817
        return false;
818
    }
819
820 227 llmarques
    private Point parsePoint(String response) throws ParsePointException {
821
        String[] numbers = new String[1];
822
        numbers[0] = response;
823
        numbers = response.split(",");
824
        if (numbers.length == 2) {
825 157 llmarques
826 227 llmarques
            if (numbers[0].startsWith("(") && numbers[1].endsWith(")\n")) { // CCS
827
                numbers[0] = numbers[0].replace("(", "");
828
                numbers[1] = numbers[1].replace(")\n", "");
829
            }
830 157 llmarques
831 227 llmarques
            double[] values;
832
            try {
833
                values =
834
                    new double[] { Double.parseDouble(numbers[0]),
835 245 llmarques
                        Double.parseDouble(numbers[1]) };
836 227 llmarques
            } catch (Exception e) {
837
                throw new ParsePointException(e);
838
            }
839 157 llmarques
840 227 llmarques
            Point point;
841
            try {
842
                GeometryManager geomManager =
843
                    GeometryLocator.getGeometryManager();
844
                int subType =
845
                    getCurrentLayer().getFeatureStore().getDefaultFeatureType()
846 245 llmarques
                        .getDefaultGeometryAttribute().getGeomType()
847
                        .getSubType();
848 227 llmarques
                point = geomManager.createPoint(values[0], values[1], subType);
849 226 llmarques
850 227 llmarques
            } catch (Exception e) {
851
                throw new ParsePointException(e);
852
            }
853
854
            return point;
855
        } else {
856
            throw new ParsePointException(null);
857 226 llmarques
        }
858
    }
859
860 227 llmarques
    private Double parseValue(String response) throws ParseValueException {
861
        try {
862
            return Double.valueOf(response);
863
        } catch (Exception e) {
864
            throw new ParseValueException(e);
865
        }
866 226 llmarques
867
    }
868
869 227 llmarques
    protected void refreshMenusAndToolBars() {
870 365 llmarques
        Notification notification =
871
            new BaseNotification(EditingContext.REFRESH_TOOLS_NOTIFICATION,
872
                null);
873 303 fdiaz
        this.observableHelper.notifyObservers(this, notification);
874 226 llmarques
    }
875
876 227 llmarques
    private void saveChanges(FLyrVect layer) throws EndEditingException {
877
        FeatureStore featureStore = layer.getFeatureStore();
878 226 llmarques
        try {
879 227 llmarques
            featureStore.finishEditing();
880
        } catch (Exception e) {
881
            throw new EndEditingException(e);
882 226 llmarques
        }
883 227 llmarques
    }
884 226 llmarques
885 227 llmarques
    private void setActiveService(EditingService service) {
886
        serviceStack.add(service);
887 226 llmarques
    }
888
889 227 llmarques
    private void setCompoundBehavior(EditingCompoundBehavior compoundBehavior) {
890
        this.editingCompoundBehavior = compoundBehavior;
891
    }
892
893 226 llmarques
    private void setCurrentLayer(FLyrVect layer) {
894
895
        if (this.currentLayer != layer) {
896 438 fdiaz
            this.currentLayer = layer;
897 226 llmarques
            cleanEditingContext();
898
        }
899
900
    }
901
902 227 llmarques
    public void setMapControl(MapControl mapControl) {
903 226 llmarques
904 227 llmarques
        this.mapControlReference = new WeakReference<MapControl>(mapControl);
905 383 llmarques
        this.mapContextReference =
906
            new WeakReference<MapContext>(mapControl.getMapContext());
907 227 llmarques
908
        // When mapControl is updated we have to add older additional behaviors
909
        // to new mapControl
910
        if (lastAdditionalBehaviors != null) {
911
            try {
912
                addBehaviors(lastAdditionalBehaviors);
913
            } catch (CreateEditingBehaviorException e1) {
914
                logger.info("Problems adding behaviors to editing context", e1);
915
                getMapControl().setTool("pan");
916
                return;
917
            }
918
        }
919 226 llmarques
    }
920
921 227 llmarques
    private void showConsole() {
922
        if (isShowConsole) {
923
            return;
924
        }
925
        isShowConsole = true;
926
        getMapControl().remove(getDockConsole());
927
        getMapControl().setLayout(new BorderLayout());
928
        getMapControl().add(getDockConsole(), BorderLayout.SOUTH);
929
        getDockConsole().setVisible(true);
930 226 llmarques
    }
931
932 227 llmarques
    protected void showConsoleMessage(String text) {
933 376 llmarques
        getConsolePanel().addText(text);
934 227 llmarques
    }
935
936 226 llmarques
    protected void textEntered(String response) {
937 472 fdiaz
        FeatureStore featureStore = getCurrentLayer().getFeatureStore();
938 226 llmarques
        if (response == null) {
939
            if (getActiveService() != null) {
940
                try {
941
                    getActiveService().stop();
942 302 fdiaz
                    serviceStack.pop();
943 316 llmarques
                    if (serviceStack.isEmpty()) {
944 472 fdiaz
                        featureStore
945 302 fdiaz
                            .getFeatureSelection().deselectAll();
946
                        changeSelectedTool(DEFAULT_TOOL);
947
                    } else {
948
                        changeSelectedTool(getActiveService().getName());
949
                    }
950 226 llmarques
951 245 llmarques
                    refreshMenusAndToolBars();
952
953 316 llmarques
                    if (getActiveService() != null) {
954 302 fdiaz
                        getNextParameter();
955
                    } else {
956
                        cleanEditingContext();
957
                    }
958 245 llmarques
959 226 llmarques
                } catch (StopServiceException e) {
960
                    logger
961 245 llmarques
                        .info("Can't stop " + getActiveService().getName(), e);
962 226 llmarques
                    return;
963 245 llmarques
                } catch (DataException e) {
964
                    logger.info("Can't get selection of "
965 472 fdiaz
                        + featureStore.getFullName(), e);
966 245 llmarques
                    return;
967 226 llmarques
                }
968
            }
969
        } else {
970
971
            if (getCurrentParam() != null) {
972
                Set<TYPE> types = getCurrentParam().getTypes();
973
                Point point = null;
974
                Double value = null;
975
976
                boolean insertedValue = false;
977 227 llmarques
                if ((!insertedValue && types.contains(TYPE.POSITION))
978 226 llmarques
                    || types.contains(TYPE.LIST_POSITIONS)) {
979
980
                    try {
981
982
                        point = parsePoint(response);
983
                        if (point != null) {
984
                            getActiveService().setValue(point);
985
                            insertedValue = true;
986
                        }
987
988
                    } catch (VectorEditingException e) {
989
                        // Do nothing to try other types
990
                    }
991
                }
992
                if (!insertedValue && types.contains(TYPE.VALUE)) {
993
994
                    try {
995
996
                        value = parseValue(response);
997
                        if (value != null) {
998
                            getActiveService().setValue(value);
999
                            insertedValue = true;
1000
                        }
1001
1002
                    } catch (VectorEditingException e) {
1003
                        // Do nothing to try other types
1004
                    }
1005
1006
                }
1007
                if (!insertedValue && types.contains(TYPE.OPTION)) {
1008
1009
                    try {
1010
1011
                        response = response.replace("\n", "");
1012
                        if (response != null) {
1013
                            getActiveService().setValue(response);
1014
                            insertedValue = true;
1015
                        }
1016
1017
                    } catch (VectorEditingException e) {
1018
                        // Do nothing to try other types
1019
                    }
1020
                }
1021
                if (!insertedValue && types.contains(TYPE.SELECTION)) {
1022
                    if (response.equalsIgnoreCase("\n")) {
1023
                        enableSelection(false);
1024
                        insertedValue = true;
1025
1026
                        try {
1027
1028
                            getActiveService().setValue(
1029 472 fdiaz
                                featureStore
1030 245 llmarques
                                    .getFeatureSelection().clone());
1031 226 llmarques
1032
                        } catch (InvalidEntryException e) {
1033
                            I18nManager i18nManager =
1034
                                ToolsLocator.getI18nManager();
1035 376 llmarques
                            showConsoleMessage("\n"
1036
                                + i18nManager.getTranslation("invalid_option"));
1037 226 llmarques
                        } catch (Exception e) {
1038 472 fdiaz
                            logger.info("Can't access to selection.", e);
1039 226 llmarques
                            cleanEditingContext();
1040
                            return;
1041
                        }
1042
                    }
1043
                }
1044
                if (!insertedValue) {
1045
                    I18nManager i18nManager = ToolsLocator.getI18nManager();
1046 376 llmarques
                    showConsoleMessage("\n"
1047
                        + i18nManager.getTranslation("invalid_option"));
1048 226 llmarques
                }
1049
                getNextParameter();
1050
            }
1051
        }
1052
    }
1053 438 fdiaz
1054
    public void setDefaultBehaviors(Behavior[] defaultBehaviors) {
1055
        this.defaultBehaviors = defaultBehaviors;
1056 546 llmarques
        try {
1057
            addBehaviors(defaultBehaviors);
1058
        } catch (CreateEditingBehaviorException e1) {
1059
            logger.info("Problems adding behaviors to editing context", e1);
1060
            getMapControl().setTool("pan");
1061
            return;
1062
        }
1063 438 fdiaz
    }
1064
1065
    public Behavior[] getDefaultBehaviors() {
1066
        return this.defaultBehaviors;
1067
    }
1068 89 llmarques
}