mirror of
https://github.com/FoggedLens/iD.git
synced 2026-02-13 01:02:58 +00:00
Fix issue where valid merge operations could be blocked
Disable merge when it'd create a redundant multipolygon or add a redundant membership
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
import { geoPolygonContainsPolygon } from '../geo';
|
||||
import { osmJoinWays, osmRelation } from '../osm';
|
||||
import { utilArrayGroupBy, utilObjectOmit } from '../util';
|
||||
import { utilArrayGroupBy, utilArrayIntersection, utilObjectOmit } from '../util';
|
||||
|
||||
|
||||
export function actionMergePolygon(ids, newRelationId) {
|
||||
@@ -114,10 +114,35 @@ export function actionMergePolygon(ids, newRelationId) {
|
||||
action.disabled = function(graph) {
|
||||
var entities = groupEntities(graph);
|
||||
if (entities.other.length > 0 ||
|
||||
entities.closedWay.length + entities.multipolygon.length < 2)
|
||||
entities.closedWay.length + entities.multipolygon.length < 2) {
|
||||
return 'not_eligible';
|
||||
if (!entities.multipolygon.every(function(r) { return r.isComplete(graph); }))
|
||||
}
|
||||
if (!entities.multipolygon.every(function(r) { return r.isComplete(graph); })) {
|
||||
return 'incomplete_relation';
|
||||
}
|
||||
|
||||
if (!entities.multipolygon.length) {
|
||||
var sharedMultipolygons = [];
|
||||
entities.closedWay.forEach(function(way, i) {
|
||||
if (i === 0) {
|
||||
sharedMultipolygons = graph.parentMultipolygons(way);
|
||||
} else {
|
||||
sharedMultipolygons = utilArrayIntersection(sharedMultipolygons, graph.parentMultipolygons(way));
|
||||
}
|
||||
});
|
||||
sharedMultipolygons = sharedMultipolygons.filter(function(relation) {
|
||||
return relation.members.length === entities.closedWay.length;
|
||||
});
|
||||
if (sharedMultipolygons.length) {
|
||||
// don't create a new multipolygon if it'd be redundant
|
||||
return 'not_eligible';
|
||||
}
|
||||
} else if (entities.closedWay.some(function(way) {
|
||||
return utilArrayIntersection(graph.parentMultipolygons(way), entities.multipolygon).length;
|
||||
})) {
|
||||
// don't add a way to a multipolygon again if it's already a member
|
||||
return 'not_eligible';
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -14,19 +14,24 @@ export function operationMerge(context, selectedIDs) {
|
||||
var _action = getAction();
|
||||
|
||||
function getAction() {
|
||||
// prefer a non-disabled action first
|
||||
var join = actionJoin(selectedIDs);
|
||||
if (join.disabled(context.graph()) !== 'not_eligible') {
|
||||
return join;
|
||||
}
|
||||
if (!join.disabled(context.graph())) return join;
|
||||
|
||||
var merge = actionMerge(selectedIDs);
|
||||
if (merge.disabled(context.graph()) !== 'not_eligible') {
|
||||
return merge;
|
||||
}
|
||||
if (!merge.disabled(context.graph())) return merge;
|
||||
|
||||
var mergePolygon = actionMergePolygon(selectedIDs);
|
||||
if (mergePolygon.disabled(context.graph()) !== 'not_eligible') {
|
||||
return mergePolygon;
|
||||
}
|
||||
if (!mergePolygon.disabled(context.graph())) return mergePolygon;
|
||||
|
||||
var mergeNodes = actionMergeNodes(selectedIDs);
|
||||
if (!mergeNodes.disabled(context.graph())) return mergeNodes;
|
||||
|
||||
// otherwise prefer an action with an interesting disabled reason
|
||||
if (join.disabled(context.graph()) !== 'not_eligible') return join;
|
||||
if (merge.disabled(context.graph()) !== 'not_eligible') return merge;
|
||||
if (mergePolygon.disabled(context.graph()) !== 'not_eligible') return mergePolygon;
|
||||
|
||||
return mergeNodes;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user