From 2bd6178f07d30cc12cc528b84791efb62ee1ca8c Mon Sep 17 00:00:00 2001 From: John Firebaugh Date: Fri, 29 Mar 2013 14:32:06 -0700 Subject: [PATCH] Split on self-intersections --- js/id/actions/split.js | 16 +++++++++++---- test/spec/actions/split.js | 41 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 53 insertions(+), 4 deletions(-) diff --git a/js/id/actions/split.js b/js/id/actions/split.js index d4c88595a..0f679fc77 100644 --- a/js/id/actions/split.js +++ b/js/id/actions/split.js @@ -15,9 +15,17 @@ iD.actions.Split = function(nodeId, newWayIds) { parents = graph.parentWays(node); return parents.filter(function(parent) { - return parent.isClosed() || - (parent.first() !== nodeId && - parent.last() !== nodeId); + if (parent.isClosed()) { + return true; + } + + for (var i = 1; i < parent.nodes.length - 1; i++) { + if (parent.nodes[i] === nodeId) { + return true; + } + } + + return false; }); } @@ -41,7 +49,7 @@ iD.actions.Split = function(nodeId, newWayIds) { nodesB = nodes.slice(idxB).concat(nodes.slice(0, idxA + 1)); } } else { - var idx = _.indexOf(wayA.nodes, nodeId); + var idx = _.indexOf(wayA.nodes, nodeId, 1); nodesA = wayA.nodes.slice(0, idx + 1); nodesB = wayA.nodes.slice(idx); } diff --git a/test/spec/actions/split.js b/test/spec/actions/split.js index bc7227ba1..ec8042708 100644 --- a/test/spec/actions/split.js +++ b/test/spec/actions/split.js @@ -25,6 +25,18 @@ describe("iD.actions.Split", function () { expect(iD.actions.Split('*').disabled(graph)).not.to.be.ok; }); + it("returns falsy for a self-intersection", function () { + var graph = iD.Graph({ + 'a': iD.Node({id: 'a'}), + 'b': iD.Node({id: 'b'}), + 'c': iD.Node({id: 'c'}), + 'd': iD.Node({id: 'c'}), + '-': iD.Way({id: '-', nodes: ['a', 'b', 'c', 'a', 'd']}) + }); + + expect(iD.actions.Split('a').disabled(graph)).not.to.be.ok; + }); + it("returns 'not_eligible' for the first node of a single way", function () { var graph = iD.Graph({ 'a': iD.Node({id: 'a'}), @@ -148,6 +160,35 @@ describe("iD.actions.Split", function () { expect(graph.entity('¦').nodes).to.eql(['*', 'd']); }); + it("splits self-intersecting ways", function () { + // Situation: + // b + // / | + // / | + // c - a -- d + // + // Split at a. + // + // Expected result: + // b + // / | + // / | + // c - a == d + // + var graph = iD.Graph({ + 'a': iD.Node({id: 'a'}), + 'b': iD.Node({id: 'b'}), + 'c': iD.Node({id: 'c'}), + 'd': iD.Node({id: 'c'}), + '-': iD.Way({id: '-', nodes: ['a', 'b', 'c', 'a', 'd']}) + }); + + graph = iD.actions.Split('a', ['='])(graph); + + expect(graph.entity('-').nodes).to.eql(['a', 'b', 'c', 'a']); + expect(graph.entity('=').nodes).to.eql(['a', 'd']); + }); + it("splits a closed way at the given point and its antipode", function () { // Situation: // a ---- b