Ignore:
Timestamp:
2016-08-23T22:07:06+02:00 (8 years ago)
Author:
Don-vip
Message:

fix #13429 - Clean validator tree and use listener to find changes (patch by michael2402) - gsoc-core

Location:
trunk/src/org/openstreetmap/josm/gui
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/org/openstreetmap/josm/gui/dialogs/ValidatorDialog.java

    r10759 r10880  
    151151        buttons.add(fixButton);
    152152
    153         if (Main.pref.getBoolean(ValidatorPreference.PREF_USE_IGNORE, true)) {
     153        if (ValidatorPreference.PREF_USE_IGNORE.get()) {
    154154            ignoreButton = new SideButton(new AbstractAction() {
    155155                {
     
    193193        }
    194194        super.setVisible(v);
    195         Main.map.repaint();
    196195    }
    197196
  • trunk/src/org/openstreetmap/josm/gui/dialogs/validator/ValidatorTreePanel.java

    r10715 r10880  
    1111import java.util.EnumMap;
    1212import java.util.Enumeration;
    13 import java.util.HashMap;
    1413import java.util.HashSet;
    1514import java.util.List;
     
    1817import java.util.Set;
    1918import java.util.function.Predicate;
     19import java.util.stream.Collectors;
    2020
    2121import javax.swing.JTree;
     
    3636import org.openstreetmap.josm.gui.util.GuiHelper;
    3737import org.openstreetmap.josm.tools.Destroyable;
    38 import org.openstreetmap.josm.tools.MultiMap;
     38import org.openstreetmap.josm.tools.ListenerList;
    3939
    4040/**
     
    7373    private transient Set<? extends OsmPrimitive> filter;
    7474
    75     /** a counter to check if tree has been rebuild */
    76     private int updateCount;
     75    private final ListenerList<Runnable> invalidationListeners = ListenerList.create();
    7776
    7877    /**
     
    135134        }
    136135        super.setVisible(v);
     136        invalidationListeners.fireEvent(Runnable::run);
    137137    }
    138138
     
    141141     */
    142142    public void buildTree() {
    143         updateCount++;
    144143        final DefaultMutableTreeNode rootNode = new DefaultMutableTreeNode();
    145144
     
    172171        }
    173172
    174         Map<Severity, MultiMap<String, TestError>> errorTree = new EnumMap<>(Severity.class);
    175         Map<Severity, HashMap<String, MultiMap<String, TestError>>> errorTreeDeep = new EnumMap<>(Severity.class);
    176         for (Severity s : Severity.values()) {
    177             errorTree.put(s, new MultiMap<String, TestError>(20));
    178             errorTreeDeep.put(s, new HashMap<String, MultiMap<String, TestError>>());
    179         }
    180 
    181         final Boolean other = ValidatorPreference.PREF_OTHER.get();
    182         for (TestError e : errors) {
    183             if (e.isIgnored()) {
    184                 continue;
    185             }
    186             Severity s = e.getSeverity();
    187             if (!other && s == Severity.OTHER) {
    188                 continue;
    189             }
    190             String d = e.getDescription();
    191             String m = e.getMessage();
    192             if (filter != null) {
    193                 boolean found = false;
    194                 for (OsmPrimitive p : e.getPrimitives()) {
    195                     if (filter.contains(p)) {
    196                         found = true;
    197                         break;
    198                     }
    199                 }
    200                 if (!found) {
    201                     continue;
    202                 }
    203             }
    204             if (d != null) {
    205                 MultiMap<String, TestError> b = errorTreeDeep.get(s).get(m);
    206                 if (b == null) {
    207                     b = new MultiMap<>(20);
    208                     errorTreeDeep.get(s).put(m, b);
    209                 }
    210                 b.put(d, e);
    211             } else {
    212                 errorTree.get(s).put(m, e);
    213             }
    214         }
     173        Predicate<TestError> filterToUse = e -> !e.isIgnored();
     174        if (!ValidatorPreference.PREF_OTHER.get()) {
     175            filterToUse = filterToUse.and(e -> e.getSeverity() != Severity.OTHER);
     176        }
     177        if (filter != null) {
     178            filterToUse = filterToUse.and(e -> e.getPrimitives().stream().anyMatch(filter::contains));
     179        }
     180        Map<Severity, Map<String, Map<String, List<TestError>>>> errorTreeDeep
     181            = errors.stream().filter(filterToUse).collect(
     182                    Collectors.groupingBy(e -> e.getSeverity(), () -> new EnumMap<>(Severity.class),
     183                            Collectors.groupingBy(e -> e.getDescription() == null ? "" : e.getDescription(),
     184                                    Collectors.groupingBy(e -> e.getMessage()))));
    215185
    216186        List<TreePath> expandedPaths = new ArrayList<>();
    217         for (Severity s : Severity.values()) {
    218             MultiMap<String, TestError> severityErrors = errorTree.get(s);
    219             Map<String, MultiMap<String, TestError>> severityErrorsDeep = errorTreeDeep.get(s);
    220             if (severityErrors.isEmpty() && severityErrorsDeep.isEmpty()) {
    221                 continue;
    222             }
    223 
     187        errorTreeDeep.forEach((s, severityErrorsDeep) -> {
    224188            // Severity node
    225189            DefaultMutableTreeNode severityNode = new GroupTreeNode(s);
     
    230194            }
    231195
    232             for (Entry<String, Set<TestError>> msgErrors : severityErrors.entrySet()) {
    233                 // Message node
    234                 Set<TestError> errs = msgErrors.getValue();
    235                 String msg = tr("{0} ({1})", msgErrors.getKey(), errs.size());
    236                 DefaultMutableTreeNode messageNode = new DefaultMutableTreeNode(msg);
    237                 severityNode.add(messageNode);
    238 
    239                 if (oldSelectedRows.contains(msgErrors.getKey())) {
    240                     expandedPaths.add(new TreePath(new Object[] {rootNode, severityNode, messageNode}));
    241                 }
    242 
    243                 for (TestError error : errs) {
    244                     // Error node
    245                     DefaultMutableTreeNode errorNode = new DefaultMutableTreeNode(error);
    246                     messageNode.add(errorNode);
    247                 }
    248             }
    249             for (Entry<String, MultiMap<String, TestError>> bag : severityErrorsDeep.entrySet()) {
     196            Map<String, List<TestError>> severityErrors = severityErrorsDeep.get("");
     197            if (severityErrors != null) {
     198                for (Entry<String, List<TestError>> msgErrors : severityErrors.entrySet()) {
     199                    // Message node
     200                    List<TestError> errs = msgErrors.getValue();
     201                    String msg = tr("{0} ({1})", msgErrors.getKey(), errs.size());
     202                    DefaultMutableTreeNode messageNode = new DefaultMutableTreeNode(msg);
     203                    severityNode.add(messageNode);
     204
     205                    if (oldSelectedRows.contains(msgErrors.getKey())) {
     206                        expandedPaths.add(new TreePath(new Object[] {rootNode, severityNode, messageNode}));
     207                    }
     208
     209                    errs.stream().map(DefaultMutableTreeNode::new).forEach(messageNode::add);
     210                }
     211            }
     212
     213            severityErrorsDeep.forEach((description, errorlist) -> {
     214                if (description.isEmpty()) {
     215                    return;
     216                }
    250217                // Group node
    251                 MultiMap<String, TestError> errorlist = bag.getValue();
    252                 DefaultMutableTreeNode groupNode = null;
     218                DefaultMutableTreeNode groupNode;
    253219                if (errorlist.size() > 1) {
    254                     groupNode = new GroupTreeNode(bag.getKey());
     220                    groupNode = new GroupTreeNode(description);
    255221                    severityNode.add(groupNode);
    256                     if (oldSelectedRows.contains(bag.getKey())) {
     222                    if (oldSelectedRows.contains(description)) {
    257223                        expandedPaths.add(new TreePath(new Object[] {rootNode, severityNode, groupNode}));
    258224                    }
    259                 }
    260 
    261                 for (Entry<String, Set<TestError>> msgErrors : errorlist.entrySet()) {
     225                } else {
     226                    groupNode = null;
     227                }
     228
     229                errorlist.forEach((message, errs) -> {
    262230                    // Message node
    263                     Set<TestError> errs = msgErrors.getValue();
    264231                    String msg;
    265232                    if (groupNode != null) {
    266                         msg = tr("{0} ({1})", msgErrors.getKey(), errs.size());
     233                        msg = tr("{0} ({1})", message, errs.size());
    267234                    } else {
    268                         msg = tr("{0} - {1} ({2})", msgErrors.getKey(), bag.getKey(), errs.size());
     235                        msg = tr("{0} - {1} ({2})", message, description, errs.size());
    269236                    }
    270237                    DefaultMutableTreeNode messageNode = new DefaultMutableTreeNode(msg);
     
    275242                    }
    276243
    277                     if (oldSelectedRows.contains(msgErrors.getKey())) {
     244                    if (oldSelectedRows.contains(message)) {
    278245                        if (groupNode != null) {
    279246                            expandedPaths.add(new TreePath(new Object[] {rootNode, severityNode, groupNode, messageNode}));
     
    283250                    }
    284251
    285                     for (TestError error : errs) {
    286                         // Error node
    287                         DefaultMutableTreeNode errorNode = new DefaultMutableTreeNode(error);
    288                         messageNode.add(errorNode);
    289                     }
    290                 }
    291             }
    292         }
     252                    errs.stream().map(DefaultMutableTreeNode::new).forEach(messageNode::add);
     253                });
     254            });
     255        });
    293256
    294257        valTreeModel.setRoot(rootNode);
     
    296259            this.expandPath(path);
    297260        }
     261
     262        invalidationListeners.fireEvent(Runnable::run);
     263    }
     264
     265    /**
     266     * Add a new invalidation listener
     267     * @param listener The listener
     268     */
     269    public void addInvalidationListener(Runnable listener) {
     270        invalidationListeners.addListener(listener);
     271    }
     272
     273    /**
     274     * Remove an invalidation listener
     275     * @param listener The listener
     276     * @since 10880
     277     */
     278    public void removeInvalidationListener(Runnable listener) {
     279        invalidationListeners.removeListener(listener);
    298280    }
    299281
     
    426408    }
    427409
    428     /**
    429      * Returns a value to check if tree has been rebuild
    430      * @return the current counter
    431      */
    432     public int getUpdateCount() {
    433         return updateCount;
    434     }
    435 
    436410    private void clearErrors() {
    437411        if (errors != null) {
  • trunk/src/org/openstreetmap/josm/gui/layer/ValidatorLayer.java

    r10507 r10880  
    4141 */
    4242public class ValidatorLayer extends Layer implements LayerChangeListener {
    43 
    44     private int updateCount = -1;
     43    private final Runnable invalidator = this::invalidate;
    4544
    4645    /**
     
    5049        super(tr("Validation errors"));
    5150        Main.getLayerManager().addLayerChangeListener(this);
     51        Main.map.validatorDialog.tree.addInvalidationListener(invalidator);
    5252    }
    5353
     
    6868    @Override
    6969    public void paint(final Graphics2D g, final MapView mv, Bounds bounds) {
    70         updateCount = Main.map.validatorDialog.tree.getUpdateCount();
    7170        DefaultMutableTreeNode root = Main.map.validatorDialog.tree.getRoot();
    7271        if (root == null || root.getChildCount() == 0)
     
    124123
    125124    @Override
    126     public boolean isChanged() {
    127         return updateCount != Main.map.validatorDialog.tree.getUpdateCount();
    128     }
    129 
    130     @Override
    131125    public void visitBoundingBox(BoundingXYVisitor v) {
    132126        // Do nothing
     
    168162            e.scheduleRemoval(Collections.singleton(this));
    169163        } else if (e.getRemovedLayer() == this) {
    170             Main.getLayerManager().removeLayerChangeListener(this);
    171164            OsmValidator.errorLayer = null;
    172165        }
     
    177170        return LayerPositionStrategy.IN_FRONT;
    178171    }
     172
     173    @Override
     174    public void destroy() {
     175        Main.map.validatorDialog.tree.removeInvalidationListener(invalidator);
     176        Main.getLayerManager().removeLayerChangeListener(this);
     177        super.destroy();
     178    }
    179179}
  • trunk/src/org/openstreetmap/josm/gui/preferences/validator/ValidatorPreference.java

    r8378 r10880  
    4040
    4141    /** The preferences key for error layer */
    42     public static final String PREF_LAYER = PREFIX + ".layer";
     42    public static final BooleanProperty PREF_LAYER = new BooleanProperty(PREFIX + ".layer", true);
    4343
    4444    /** The preferences key for enabled tests */
     
    4646
    4747    /** The preferences key for enabled tests */
    48     public static final String PREF_USE_IGNORE = PREFIX + ".ignore";
     48    public static final BooleanProperty PREF_USE_IGNORE = new BooleanProperty(PREFIX + ".ignore", true);
    4949
    5050    /** The preferences key for enabled tests before upload*/
     
    5252
    5353    /** The preferences key for ignored severity other on upload */
    54     public static final String PREF_OTHER_UPLOAD = PREFIX + ".otherUpload";
     54    public static final BooleanProperty PREF_OTHER_UPLOAD = new BooleanProperty(PREFIX + ".otherUpload", false);
    5555
    5656    /** The preferences for ignored severity other */
  • trunk/src/org/openstreetmap/josm/gui/preferences/validator/ValidatorTestsPreference.java

    r10611 r10880  
    5858        testPanel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
    5959
    60         prefUseIgnore = new JCheckBox(tr("Use ignore list."), Main.pref.getBoolean(ValidatorPreference.PREF_USE_IGNORE, true));
     60        prefUseIgnore = new JCheckBox(tr("Use ignore list."), ValidatorPreference.PREF_USE_IGNORE.get());
    6161        prefUseIgnore.setToolTipText(tr("Use the ignore list to suppress warnings."));
    6262        testPanel.add(prefUseIgnore, GBC.eol());
    6363
    64         prefUseLayer = new JCheckBox(tr("Use error layer."), Main.pref.getBoolean(ValidatorPreference.PREF_LAYER, true));
     64        prefUseLayer = new JCheckBox(tr("Use error layer."), ValidatorPreference.PREF_LAYER.get());
    6565        prefUseLayer.setToolTipText(tr("Use the error layer to display problematic elements."));
    6666        testPanel.add(prefUseLayer, GBC.eol());
     
    7171
    7272        prefOtherUpload = new JCheckBox(tr("Show informational level on upload."),
    73                 Main.pref.getBoolean(ValidatorPreference.PREF_OTHER_UPLOAD, false));
     73                ValidatorPreference.PREF_OTHER_UPLOAD.get());
    7474        prefOtherUpload.setToolTipText(tr("Show the informational tests in the upload check windows."));
    7575        testPanel.add(prefOtherUpload, GBC.eol());
     
    117117        Main.pref.putCollection(ValidatorPreference.PREF_SKIP_TESTS, tests);
    118118        Main.pref.putCollection(ValidatorPreference.PREF_SKIP_TESTS_BEFORE_UPLOAD, testsBeforeUpload);
    119         Main.pref.put(ValidatorPreference.PREF_USE_IGNORE, prefUseIgnore.isSelected());
     119        ValidatorPreference.PREF_USE_IGNORE.put(prefUseIgnore.isSelected());
    120120        ValidatorPreference.PREF_OTHER.put(prefOther.isSelected());
    121         Main.pref.put(ValidatorPreference.PREF_OTHER_UPLOAD, prefOtherUpload.isSelected());
    122         Main.pref.put(ValidatorPreference.PREF_LAYER, prefUseLayer.isSelected());
     121        ValidatorPreference.PREF_OTHER_UPLOAD.put(prefOtherUpload.isSelected());
     122        ValidatorPreference.PREF_LAYER.put(prefUseLayer.isSelected());
    123123        return false;
    124124    }
Note: See TracChangeset for help on using the changeset viewer.