diff --git a/js/id/renderer/map.js b/js/id/renderer/map.js index 0d1532948..08c18e915 100644 --- a/js/id/renderer/map.js +++ b/js/id/renderer/map.js @@ -112,7 +112,7 @@ iD.Map = function() { .call(areas, graph, all, filter) .call(multipolygons, graph, all, filter) .call(midpoints, graph, all, filter) - .call(labels, graph, all, filter, dimensions); + .call(labels, graph, all, filter, dimensions, !difference); } dispatch.drawn(map); } diff --git a/js/id/svg/labels.js b/js/id/svg/labels.js index 2fcc2fcc1..3962c4915 100644 --- a/js/id/svg/labels.js +++ b/js/id/svg/labels.js @@ -156,7 +156,7 @@ iD.svg.Labels = function(projection) { for (var i = 0; i < nodes.length - 1; i++) { var current = segmentLength(i); var portion; - if (!start && sofar + current > from) { + if (!start && sofar + current >= from) { portion = (from - sofar) / current; start = [ nodes[i][0] + portion * (nodes[i + 1][0] - nodes[i][0]), @@ -164,7 +164,7 @@ iD.svg.Labels = function(projection) { ]; i0 = i + 1; } - if (!end && sofar + current > to) { + if (!end && sofar + current >= to) { portion = (to - sofar) / current; end = [ nodes[i][0] + portion * (nodes[i + 1][0] - nodes[i][0]), @@ -183,14 +183,26 @@ iD.svg.Labels = function(projection) { } - return function drawLabels(surface, graph, entities, filter, dimensions) { + var rtree = new RTree(), + rectangles = {}; + + return function drawLabels(surface, graph, entities, filter, dimensions, fullRedraw) { + - var rtree = new RTree(); var hidePoints = !d3.select('.node.point').node(); var labelable = [], i, k, entity; for (i = 0; i < label_stack.length; i++) labelable.push([]); + if (fullRedraw) { + rtree = new RTree(); + rectangles = {}; + } else { + for (i = 0; i < entities.length; i++) { + rtree.remove(rectangles[entities[i].id], entities[i].id); + } + } + // Split entities into groups specified by label_stack for (i = 0; i < entities.length; i++) { entity = entities[i]; @@ -252,7 +264,7 @@ iD.svg.Labels = function(projection) { textAnchor: offset[2] }; var rect = new RTree.Rectangle(p.x - m, p.y - m, width + 2*m, height + 2*m); - if (tryInsert(rect)) return p; + if (tryInsert(rect, entity.id)) return p; } @@ -275,7 +287,7 @@ iD.svg.Labels = function(projection) { Math.abs(sub[0][1] - sub[sub.length - 1][1]) + 30 ); if (rev) sub = sub.reverse(); - if (tryInsert(rect)) return { + if (tryInsert(rect, entity.id)) return { 'font-size': height + 2, lineString: lineString(sub), startOffset: offset + '%' @@ -298,16 +310,19 @@ iD.svg.Labels = function(projection) { height: height }; var rect = new RTree.Rectangle(p.x - width/2, p.y, width, height); - if (tryInsert(rect)) return p; + if (tryInsert(rect, entity.id)) return p; } - function tryInsert(rect) { + function tryInsert(rect, id) { // Check that label is visible if (rect.x1 < 0 || rect.y1 < 0 || rect.x2 > dimensions[0] || rect.y2 > dimensions[1]) return false; var v = rtree.search(rect, true).length === 0; - if (v) rtree.insert(rect); + if (v) { + rtree.insert(rect, id); + rectangles[id] = rect; + } return v; }