diff --git a/data/core.yaml b/data/core.yaml index f1450b43e..bace83675 100644 --- a/data/core.yaml +++ b/data/core.yaml @@ -55,6 +55,7 @@ en: line: Made a line circular. area: Made an area circular. not_closed: This can't be made circular because it's not a loop. + too_large: This can't be made circular because it extends too far beyond the viewable map. orthogonalize: title: Square description: @@ -65,6 +66,7 @@ en: line: Squared the corners of a line. area: Squared the corners of an area. not_squarish: This can't be made square because it is not squarish. + too_large: This can't be made square because it extends too far beyond the viewable map. straighten: title: Straighten description: Straighten this line. diff --git a/dist/locales/en.json b/dist/locales/en.json index 240edfa6e..b5a466c9a 100644 --- a/dist/locales/en.json +++ b/dist/locales/en.json @@ -71,7 +71,8 @@ "line": "Made a line circular.", "area": "Made an area circular." }, - "not_closed": "This can't be made circular because it's not a loop." + "not_closed": "This can't be made circular because it's not a loop.", + "too_large": "This can't be made circular because not enough of it is currently visible." }, "orthogonalize": { "title": "Square", @@ -84,7 +85,8 @@ "line": "Squared the corners of a line.", "area": "Squared the corners of an area." }, - "not_squarish": "This can't be made square because it is not squarish." + "not_squarish": "This can't be made square because it is not squarish.", + "too_large": "This can't be made square because not enough of it is currently visible." }, "straighten": { "title": "Straighten", diff --git a/js/id/geo/extent.js b/js/id/geo/extent.js index 189e03058..2081f82c2 100644 --- a/js/id/geo/extent.js +++ b/js/id/geo/extent.js @@ -22,6 +22,10 @@ _.extend(iD.geo.Extent.prototype, { Math.max(obj[1][1], this[1][1])]); }, + area: function() { + return Math.abs((this[1][0] - this[0][0]) * (this[1][1] - this[0][1])); + }, + center: function() { return [(this[0][0] + this[1][0]) / 2, (this[0][1] + this[1][1]) / 2]; diff --git a/js/id/operations/circularize.js b/js/id/operations/circularize.js index 4ec23d477..2e59b90e7 100644 --- a/js/id/operations/circularize.js +++ b/js/id/operations/circularize.js @@ -14,7 +14,17 @@ iD.operations.Circularize = function(selectedIDs, context) { }; operation.disabled = function() { - return action.disabled(context.graph()); + var way = context.entity(entityId), + wayExtent = way.extent(context.graph()), + mapExtent = context.extent(), + intersection = mapExtent.intersection(wayExtent), + pctVisible = intersection.area() / wayExtent.area(); + + if (pctVisible < 0.8) { + return 'too_large'; + } else { + return action.disabled(context.graph()); + } }; operation.tooltip = function() { diff --git a/js/id/operations/orthogonalize.js b/js/id/operations/orthogonalize.js index 980d4d52d..e99827806 100644 --- a/js/id/operations/orthogonalize.js +++ b/js/id/operations/orthogonalize.js @@ -17,7 +17,17 @@ iD.operations.Orthogonalize = function(selectedIDs, context) { }; operation.disabled = function() { - return action.disabled(context.graph()); + var way = context.entity(entityId), + wayExtent = way.extent(context.graph()), + mapExtent = context.extent(), + intersection = mapExtent.intersection(wayExtent), + pctVisible = intersection.area() / wayExtent.area(); + + if (pctVisible < 0.8) { + return 'too_large'; + } else { + return action.disabled(context.graph()); + } }; operation.tooltip = function() { diff --git a/test/spec/geo/extent.js b/test/spec/geo/extent.js index 66526c1b6..9ca751efc 100644 --- a/test/spec/geo/extent.js +++ b/test/spec/geo/extent.js @@ -51,6 +51,12 @@ describe("iD.geo.Extent", function () { }); }); + describe("#area", function () { + it("returns the area", function () { + expect(iD.geo.Extent([0, 0], [5, 10]).area()).to.eql(50); + }); + }); + describe("#padByMeters", function () { it("does not change centerpoint of an extent", function () { var min = [0, 0], max = [5, 10];