Ticket #20091: 20091-full.patch

File 20091-full.patch, 6.8 KB (added by GerdP, 5 years ago)
  • src/org/openstreetmap/josm/actions/relation/DownloadMembersAction.java

     
    66
    77import java.awt.event.ActionEvent;
    88import java.util.Collection;
     9import java.util.List;
     10import java.util.stream.Collectors;
    911
    1012import org.openstreetmap.josm.data.osm.IPrimitive;
    11 import org.openstreetmap.josm.data.osm.Relation;
     13import org.openstreetmap.josm.data.osm.PrimitiveId;
    1214import org.openstreetmap.josm.gui.MainApplication;
    13 import org.openstreetmap.josm.gui.dialogs.relation.DownloadRelationTask;
     15import org.openstreetmap.josm.gui.io.DownloadPrimitivesTask;
    1416import org.openstreetmap.josm.tools.ImageProvider;
    15 import org.openstreetmap.josm.tools.SubclassFilteredCollection;
    16 import org.openstreetmap.josm.tools.Utils;
    1717
    1818/**
    1919 * The action for downloading members of relations
     
    3434    @Override
    3535    public void actionPerformed(ActionEvent e) {
    3636        if (!isEnabled() || relations.isEmpty() || !MainApplication.isDisplayingMapView()) return;
    37         MainApplication.worker.submit(new DownloadRelationTask(
    38                 Utils.filteredCollection(relations, Relation.class), MainApplication.getLayerManager().getEditLayer()));
     37        List<PrimitiveId> members = relations.stream()
     38                .flatMap(r -> r.getMemberPrimitivesList().stream().filter(osm -> !osm.isNew()).map(IPrimitive::getOsmPrimitiveId))
     39                .distinct()
     40                .collect(Collectors.toList());
     41
     42        MainApplication.worker.submit(new DownloadPrimitivesTask(MainApplication.getLayerManager().getEditLayer(), members, false));
    3943    }
    4044
    4145    @Override
    4246    public void setPrimitives(Collection<? extends IPrimitive> primitives) {
    43         // selected non-new relations
    44         this.relations = SubclassFilteredCollection.filter(getRelations(primitives), r -> !r.isNew());
     47        this.relations = getRelations(primitives);
    4548        updateEnabledState();
    4649    }
    4750
  • src/org/openstreetmap/josm/data/osm/DataSetMerger.java

     
    99import java.util.HashMap;
    1010import java.util.HashSet;
    1111import java.util.Iterator;
     12import java.util.LinkedHashSet;
    1213import java.util.LinkedList;
    1314import java.util.List;
    1415import java.util.Map;
     
    6364        conflicts = new ConflictCollection();
    6465        mergedMap = new HashMap<>();
    6566        objectsWithChildrenToMerge = new HashSet<>();
    66         objectsToDelete = new HashSet<>();
     67        objectsToDelete = new LinkedHashSet<>();
    6768    }
    6869
    6970    /**
     
    297298        // found a corresponding target, remember it
    298299        mergedMap.put(source.getPrimitiveId(), target.getPrimitiveId());
    299300
     301        boolean mergeFromSource = false;
    300302        if (target.getVersion() > source.getVersion())
    301303            // target.version > source.version => keep target version
    302304            return true;
    303305
    304         if (target.isIncomplete() && !source.isIncomplete()) {
     306        if (!target.isModified() && source.isDeleted()) {
     307            // target not modified. We can assume that source is the most recent version,
     308            // so mark it to be deleted.
     309            //
     310            objectsToDelete.add(target);
     311        } else if (target.isIncomplete() && !source.isIncomplete()) {
    305312            // target is incomplete, source completes it
    306313            // => merge source into target
    307314            //
    308             target.mergeFrom(source);
    309             objectsWithChildrenToMerge.add(source.getPrimitiveId());
     315            mergeFromSource = true;
    310316        } else if (!target.isIncomplete() && source.isIncomplete()) {
    311317            // target is complete and source is incomplete
    312318            // => keep target, it has more information already
     
    323329            // We shouldn't merge that datasets.
    324330            throw new DataIntegrityProblemException(tr("Conflict in ''visible'' attribute for object of type {0} with id {1}",
    325331                    target.getType(), target.getId()));
     332        } else if (target.isDeleted() && source.isDeleted() && target.getVersion() < source.getVersion()) {
     333            // both deleted. Source is newer. Take source. See #19783
     334            mergeFromSource = true;
    326335        } else if (target.isDeleted() && !source.isDeleted() && target.getVersion() == source.getVersion()) {
    327336            // same version, but target is deleted. Assume target takes precedence
    328337            // otherwise too many conflicts when refreshing from the server
     
    339348                    break;
    340349                }
    341350            }
    342         } else if (!target.isModified() && source.isDeleted()) {
    343             // target not modified. We can assume that source is the most recent version,
    344             // so mark it to be deleted.
    345             //
    346             objectsToDelete.add(target);
    347351        } else if (!target.isModified() && source.isModified()) {
    348352            // target not modified. We can assume that source is the most recent version.
    349353            // clone it into target.
    350             target.mergeFrom(source);
    351             objectsWithChildrenToMerge.add(source.getPrimitiveId());
     354            mergeFromSource = true;
    352355        } else if (!target.isModified() && !source.isModified() && target.getVersion() == source.getVersion()) {
    353356            // both not modified. Merge nevertheless.
    354357            // This helps when updating "empty" relations, see #4295
    355             target.mergeFrom(source);
    356             objectsWithChildrenToMerge.add(source.getPrimitiveId());
     358            mergeFromSource = true;
    357359        } else if (!target.isModified() && !source.isModified() && target.getVersion() < source.getVersion()) {
    358360            // my not modified but other is newer. clone other onto mine.
    359361            //
    360             target.mergeFrom(source);
    361             objectsWithChildrenToMerge.add(source.getPrimitiveId());
     362            mergeFromSource = true;
    362363        } else if (target.isModified() && !source.isModified() && target.getVersion() == source.getVersion()) {
    363364            // target is same as source but target is modified
    364365            // => keep target and reset modified flag if target and source are semantically equal
     
    380381            // technical attributes like timestamp or user information. Semantic
    381382            // attributes should already be equal if we get here.
    382383            //
     384            mergeFromSource = true;
     385        }
     386        if (mergeFromSource) {
    383387            target.mergeFrom(source);
    384388            objectsWithChildrenToMerge.add(source.getPrimitiveId());
    385389        }