From 5a898884ecc60a91f63f16b144ce33f054d67526 Mon Sep 17 00:00:00 2001 From: Tim Schaub Date: Tue, 12 Nov 2013 11:30:32 -0700 Subject: [PATCH] Use geometry type enum for configuring draw interaction This allows us to cast single-part geometries to multi-part types before adding features to the target layer. This doesn't yet allow for drawing multi-part geometries with multiple parts. That can be handled separately. --- examples/draw-features.html | 2 +- examples/draw-features.js | 10 ++--- src/objectliterals.jsdoc | 4 +- src/ol/interaction/drawinteraction.js | 57 +++++++++++++++++++++++++-- 4 files changed, 61 insertions(+), 12 deletions(-) diff --git a/examples/draw-features.html b/examples/draw-features.html index 2ad504106d..5459365499 100644 --- a/examples/draw-features.html +++ b/examples/draw-features.html @@ -35,7 +35,7 @@

Example of using the Draw interaction.

- diff --git a/examples/draw-features.js b/examples/draw-features.js index e33ff3a3bd..637035f756 100644 --- a/examples/draw-features.js +++ b/examples/draw-features.js @@ -97,24 +97,24 @@ var map = new ol.Map({ }) }); -var modeSelect = document.getElementById('mode'); +var typeSelect = document.getElementById('type'); var draw; // global so we can remove it later function addInteraction() { draw = new ol.interaction.Draw({ layer: vector, - mode: /** @type {ol.interaction.DrawMode} */ - (modeSelect.options[modeSelect.selectedIndex].value) + type: /** @type {ol.geom.GeometryType} */ + (typeSelect.options[typeSelect.selectedIndex].value) }); map.addInteraction(draw); } /** - * Let user change the draw mode. + * Let user change the geometry type. * @param {Event} e Change event. */ -modeSelect.onchange = function(e) { +typeSelect.onchange = function(e) { map.removeInteraction(draw); addInteraction(); }; diff --git a/src/objectliterals.jsdoc b/src/objectliterals.jsdoc index 55dcb25881..e39f3b5156 100644 --- a/src/objectliterals.jsdoc +++ b/src/objectliterals.jsdoc @@ -346,8 +346,8 @@ * @property {ol.layer.Vector} layer Destination layer for the features. * @property {number|undefined} snapTolerance Pixel distance for snapping to the * drawing finish (default is 12). - * @property {ol.interaction.DrawMode} mode Drawing mode ('point', 'linestring', - * or 'polygon'). + * @property {ol.geom.GeometryType} type Drawing type ('point', 'linestring', + * 'polygon', 'multipoint', 'multilinestring', or 'multipolygon'). * @todo stability experimental */ diff --git a/src/ol/interaction/drawinteraction.js b/src/ol/interaction/drawinteraction.js index 03807276a5..f828a06eac 100644 --- a/src/ol/interaction/drawinteraction.js +++ b/src/ol/interaction/drawinteraction.js @@ -1,5 +1,4 @@ goog.provide('ol.interaction.Draw'); -goog.provide('ol.interaction.DrawMode'); goog.require('goog.asserts'); @@ -8,7 +7,11 @@ goog.require('ol.Feature'); goog.require('ol.Map'); goog.require('ol.MapBrowserEvent'); goog.require('ol.MapBrowserEvent.EventType'); +goog.require('ol.geom.GeometryType'); goog.require('ol.geom.LineString'); +goog.require('ol.geom.MultiLineString'); +goog.require('ol.geom.MultiPoint'); +goog.require('ol.geom.MultiPolygon'); goog.require('ol.geom.Point'); goog.require('ol.geom.Polygon'); goog.require('ol.interaction.Interaction'); @@ -50,11 +53,18 @@ ol.interaction.Draw = function(options) { options.snapTolerance : 12; /** - * Draw mode. + * Geometry type. + * @type {ol.geom.GeometryType} + * @private + */ + this.type_ = options.type; + + /** + * Drawing mode (derived from geometry type. * @type {ol.interaction.DrawMode} * @private */ - this.mode_ = options.mode; + this.mode_ = ol.interaction.Draw.getMode_(this.type_); /** * Finish coordinate for the feature (first point for polygons, last point for @@ -322,6 +332,20 @@ ol.interaction.Draw.prototype.finishDrawing_ = function(event) { coordinates.pop(); geometry.setCoordinates(coordinates); } + // cast multi-part geometries + if (this.type_ === ol.geom.GeometryType.MULTIPOINT) { + sketchFeature.setGeometry( + new ol.geom.MultiPoint( + [sketchFeature.getGeometry().getCoordinates()])); + } else if (this.type_ === ol.geom.GeometryType.MULTILINESTRING) { + sketchFeature.setGeometry( + new ol.geom.MultiLineString( + [sketchFeature.getGeometry().getCoordinates()])); + } else if (this.type_ === ol.geom.GeometryType.MULTIPOLYGON) { + sketchFeature.setGeometry( + new ol.geom.MultiPolygon( + [sketchFeature.getGeometry().getCoordinates()])); + } this.layer_.addFeatures([sketchFeature]); }; @@ -348,7 +372,32 @@ ol.interaction.Draw.prototype.abortDrawing_ = function() { /** - * Draw mode. + * Get the drawing mode. The mode for mult-part geometries is the same as for + * their single-part cousins. + * @param {ol.geom.GeometryType} type Geometry type. + * @return {ol.interaction.DrawMode} Drawing mode. + * @private + */ +ol.interaction.Draw.getMode_ = function(type) { + var mode; + if (type === ol.geom.GeometryType.POINT || + type === ol.geom.GeometryType.MULTIPOINT) { + mode = ol.interaction.DrawMode.POINT; + } else if (type === ol.geom.GeometryType.LINESTRING || + type === ol.geom.GeometryType.MULTILINESTRING) { + mode = ol.interaction.DrawMode.LINESTRING; + } else if (type === ol.geom.GeometryType.POLYGON || + type === ol.geom.GeometryType.MULTIPOLYGON) { + mode = ol.interaction.DrawMode.POLYGON; + } + goog.asserts.assert(goog.isDef(mode)); + return mode; +}; + + +/** + * Draw mode. This collapses multi-part geometry types with their single-part + * cousins. * @enum {string} */ ol.interaction.DrawMode = {