Ticket #13095: patch-fix-13095.patch

File patch-fix-13095.patch, 9.2 KB (added by michael2402, 8 years ago)
  • src/org/openstreetmap/josm/Main.java

    diff --git a/src/org/openstreetmap/josm/Main.java b/src/org/openstreetmap/josm/Main.java
    index c0e89c6..09e5a10 100644
    a b public abstract class Main {  
    657657            @Override
    658658            public void initialize() {
    659659                validator = new OsmValidator();
    660                 getLayerManager().addLayerChangeListener(validator);
    661660            }
    662661        });
    663662
  • src/org/openstreetmap/josm/data/validation/OsmValidator.java

    diff --git a/src/org/openstreetmap/josm/data/validation/OsmValidator.java b/src/org/openstreetmap/josm/data/validation/OsmValidator.java
    index 883f5b9..9fdf307 100644
    a b import org.openstreetmap.josm.data.validation.tests.UntaggedNode;  
    5959import org.openstreetmap.josm.data.validation.tests.UntaggedWay;
    6060import org.openstreetmap.josm.data.validation.tests.WayConnectedToArea;
    6161import org.openstreetmap.josm.data.validation.tests.WronglyOrderedWays;
    62 import org.openstreetmap.josm.gui.layer.LayerManager.LayerAddEvent;
    63 import org.openstreetmap.josm.gui.layer.LayerManager.LayerChangeListener;
    64 import org.openstreetmap.josm.gui.layer.LayerManager.LayerOrderChangeEvent;
    65 import org.openstreetmap.josm.gui.layer.LayerManager.LayerRemoveEvent;
    66 import org.openstreetmap.josm.gui.layer.OsmDataLayer;
    6762import org.openstreetmap.josm.gui.layer.ValidatorLayer;
    6863import org.openstreetmap.josm.gui.preferences.projection.ProjectionPreference;
    6964import org.openstreetmap.josm.gui.preferences.validator.ValidatorPreference;
    import org.openstreetmap.josm.tools.Utils;  
    7469 *
    7570 * @author Francisco R. Santos <frsantos@gmail.com>
    7671 */
    77 public class OsmValidator implements LayerChangeListener {
     72public class OsmValidator {
    7873
    7974    public static volatile ValidatorLayer errorLayer;
    8075
    public class OsmValidator implements LayerChangeListener {  
    345340        }
    346341    }
    347342
    348     /* -------------------------------------------------------------------------- */
    349     /* interface LayerChangeListener                                              */
    350     /* -------------------------------------------------------------------------- */
    351     @Override
    352     public void layerAdded(LayerAddEvent e) {
    353         // do nothing
    354     }
    355 
    356     @Override
    357     public void layerOrderChanged(LayerOrderChangeEvent e) {
    358         // do nothing
    359     }
    360 
    361     @Override
    362     public void layerRemoving(LayerRemoveEvent e) {
    363         if (e.getRemovedLayer() == errorLayer) {
    364             errorLayer = null;
    365             return;
    366         }
    367         if (e.getSource().getLayersOfType(OsmDataLayer.class).isEmpty()) {
    368             if (errorLayer != null) {
    369                 Main.getLayerManager().removeLayer(errorLayer);
    370             }
    371         }
    372     }
    373343}
  • src/org/openstreetmap/josm/gui/layer/LayerManager.java

    diff --git a/src/org/openstreetmap/josm/gui/layer/LayerManager.java b/src/org/openstreetmap/josm/gui/layer/LayerManager.java
    index e7ee59e..f235080 100644
    a b  
    22package org.openstreetmap.josm.gui.layer;
    33
    44import java.util.ArrayList;
     5import java.util.Collection;
    56import java.util.Collections;
     7import java.util.IdentityHashMap;
     8import java.util.Iterator;
    69import java.util.List;
     10import java.util.Set;
    711import java.util.concurrent.CopyOnWriteArrayList;
    812
    913import org.openstreetmap.josm.Main;
    public class LayerManager {  
    97101    public static class LayerRemoveEvent extends LayerManagerEvent {
    98102        private final Layer removedLayer;
    99103        private final boolean lastLayer;
     104        private Collection<Layer> scheduleForRemoval = new ArrayList<>();
    100105
    101106        LayerRemoveEvent(LayerManager source, Layer removedLayer) {
    102107            super(source);
    public class LayerManager {  
    121126            return lastLayer;
    122127        }
    123128
     129        /**
     130         * Schedule the removal of other layers after this layer has been deleted.
     131         * <p>
     132         * Dupplicate removal requests are ignored.
     133         * @param layers The layers to remove.
     134         * @since xxx
     135         */
     136        public void scheduleRemoval(Collection<? extends Layer> layers) {
     137            for (Layer layer : layers) {
     138                getSource().checkContainsLayer(layer);
     139            }
     140            scheduleForRemoval.addAll(layers);
     141        }
     142
    124143        @Override
    125144        public String toString() {
    126145            return "LayerRemoveEvent [removedLayer=" + removedLayer + ", lastLayer=" + lastLayer + ']';
    public class LayerManager {  
    197216    }
    198217
    199218    protected synchronized void realRemoveLayer(Layer layer) {
    200         checkContainsLayer(layer);
     219        GuiHelper.assertCallFromEdt();
     220        Set<Layer> toRemove = Collections.newSetFromMap(new IdentityHashMap<Layer, Boolean>());
     221        toRemove.add(layer);
     222
     223        while (!toRemove.isEmpty()) {
     224            Iterator<Layer> iterator = toRemove.iterator();
     225            Layer layerToRemove = iterator.next();
     226            iterator.remove();
     227            checkContainsLayer(layerToRemove);
    201228
    202         fireLayerRemoving(layer);
    203         layers.remove(layer);
     229            Collection<Layer> newToRemove = realRemoveSingleLayer(layerToRemove);
     230            toRemove.addAll(newToRemove);
     231        }
     232    }
     233
     234    protected Collection<Layer> realRemoveSingleLayer(Layer layerToRemove) {
     235        Collection<Layer> newToRemove = fireLayerRemoving(layerToRemove);
     236        layers.remove(layerToRemove);
     237        return newToRemove;
    204238    }
    205239
    206240    /**
    public class LayerManager {  
    333367        removeLayerChangeListener(listener, false);
    334368    }
    335369
    336 
    337370    /**
    338371     * Removes a layer change listener
    339372     *
    340373     * @param listener the listener.
    341      * @param fireRemove if we should fire a remove event for every layer in this manager.
     374     * @param fireRemove if we should fire a remove event for every layer in this manager. The event is fired as if the layer was deleted but
     375     * {@link LayerRemoveEvent#scheduleRemoval(Collection)} is ignored.
    342376     */
    343377    public synchronized void removeLayerChangeListener(LayerChangeListener listener, boolean fireRemove) {
    344378        if (!layerChangeListeners.remove(listener)) {
    public class LayerManager {  
    364398        }
    365399    }
    366400
    367     private void fireLayerRemoving(Layer layer) {
     401    /**
     402     * Fire the layer remove event
     403     * @param layer The layer to remove
     404     * @return A list of layers that should be removed afterwards.
     405     */
     406    private Collection<Layer> fireLayerRemoving(Layer layer) {
    368407        GuiHelper.assertCallFromEdt();
    369408        LayerRemoveEvent e = new LayerRemoveEvent(this, layer);
    370409        for (LayerChangeListener l : layerChangeListeners) {
    371410            try {
    372411                l.layerRemoving(e);
    373412            } catch (RuntimeException t) {
    374                 throw BugReport.intercept(t).put("listener", l).put("event", e);
     413                throw BugReport.intercept(t).put("listener", l).put("event", e).put("layer", layer);
    375414            }
    376415        }
     416        return e.scheduleForRemoval;
    377417    }
    378418
    379419    private void fireLayerOrderChanged() {
  • src/org/openstreetmap/josm/gui/layer/MainLayerManager.java

    diff --git a/src/org/openstreetmap/josm/gui/layer/MainLayerManager.java b/src/org/openstreetmap/josm/gui/layer/MainLayerManager.java
    index bd6a5ee..f5a30a7 100644
    a b  
    22package org.openstreetmap.josm.gui.layer;
    33
    44import java.util.ArrayList;
     5import java.util.Collection;
    56import java.util.List;
    67import java.util.ListIterator;
    78import java.util.concurrent.CopyOnWriteArrayList;
    public class MainLayerManager extends LayerManager {  
    206207    }
    207208
    208209    @Override
    209     protected synchronized void realRemoveLayer(Layer layer) {
     210    protected Collection<Layer> realRemoveSingleLayer(Layer layer) {
    210211        if (layer == activeLayer || layer == editLayer) {
    211212            Layer nextActive = suggestNextActiveLayer(layer);
    212213            setActiveLayer(nextActive, true);
    213214        }
    214215
    215         super.realRemoveLayer(layer);
     216        return super.realRemoveSingleLayer(layer);
    216217    }
    217218
    218219    /**
  • src/org/openstreetmap/josm/gui/layer/ValidatorLayer.java

    diff --git a/src/org/openstreetmap/josm/gui/layer/ValidatorLayer.java b/src/org/openstreetmap/josm/gui/layer/ValidatorLayer.java
    index a72a581..4044d99 100644
    a b package org.openstreetmap.josm.gui.layer;  
    44import static org.openstreetmap.josm.tools.I18n.tr;
    55
    66import java.awt.Graphics2D;
     7import java.util.Collections;
    78import java.util.Enumeration;
    89import java.util.List;
    910
    public class ValidatorLayer extends Layer implements LayerChangeListener {  
    164165    public void layerRemoving(LayerRemoveEvent e) {
    165166        // Removed layer is still in that list.
    166167        if (e.getRemovedLayer() instanceof OsmDataLayer && e.getSource().getLayersOfType(OsmDataLayer.class).size() <= 1) {
    167             Main.getLayerManager().removeLayer(this);
     168            e.scheduleRemoval(Collections.singleton(this));
    168169        } else if (e.getRemovedLayer() == this) {
    169170            Main.getLayerManager().removeLayerChangeListener(this);
    170171            OsmValidator.errorLayer = null;