Merge pull request #1793 from bartvde/gml-write

Add write support for ol.format.GML (r=@ahocevar)
This commit is contained in:
Bart van den Eijnden
2014-03-05 16:55:28 +01:00
4 changed files with 892 additions and 157 deletions

View File

@@ -308,6 +308,21 @@
* @typedef {Object} olx.format.GMLOptions
* @property {string} featureNS Feature namespace.
* @property {string} featureType Feature type to parse.
* @property {string} srsName srsName to use when writing geometries.
* @property {boolean|undefined} surface Write gml:Surface instead of
* gml:Polygon elements. This also affects the elements in multi-part
* geometries. Default is `false´.
* @property {boolean|undefined} curve Write gml:Curve instead of
* gml:LineString elements. This also affects the elements in multi-part
* geometries. Default is `false´.
* @property {boolean|undefined} multiCurve Write gml:MultiCurve instead of
* gml:MultiLineString. Since the latter is deprecated in GML 3, the
* default is `true´.
* @property {boolean|undefined} multiSurface Write gml:multiSurface instead
* of gml:MultiPolygon. Since the latter is deprecated in GML 3, the
* default is `true´.
* @property {string|undefined} schemaLocation Optional schemaLocation to use
* when writing out the GML, this will override the default provided.
*/
/**

View File

@@ -9,7 +9,10 @@ goog.require('goog.string');
goog.require('ol.Feature');
goog.require('ol.extent');
goog.require('ol.format.XMLFeature');
goog.require('ol.format.XSD');
goog.require('ol.geom.Geometry');
goog.require('ol.geom.LineString');
goog.require('ol.geom.LinearRing');
goog.require('ol.geom.MultiLineString');
goog.require('ol.geom.MultiPoint');
goog.require('ol.geom.MultiPolygon');
@@ -43,11 +46,62 @@ ol.format.GML = function(opt_options) {
*/
this.featureNS_ = options.featureNS;
/**
* @private
* @type {string}
*/
this.srsName_ = options.srsName;
/**
* @private
* @type {boolean}
*/
this.surface_ = goog.isDef(options.surface) ?
options.surface : false;
/**
* @private
* @type {boolean}
*/
this.curve_ = goog.isDef(options.curve) ?
options.curve : false;
/**
* @private
* @type {boolean}
*/
this.multiCurve_ = goog.isDef(options.multiCurve) ?
options.multiCurve : true;
/**
* @private
* @type {boolean}
*/
this.multiSurface_ = goog.isDef(options.multiSurface) ?
options.multiSurface : true;
/**
* @private
* @type {string}
*/
this.schemaLocation_ = goog.isDef(options.schemaLocation) ?
options.schemaLocation : ol.format.GML.schemaLocation_;
goog.base(this);
};
goog.inherits(ol.format.GML, ol.format.XMLFeature);
/**
* @const
* @type {string}
* @private
*/
ol.format.GML.schemaLocation_ = 'http://www.opengis.net/gml ' +
'http://schemas.opengis.net/gml/3.1.1/profiles/gmlsfProfile/' +
'1.0.0/gmlsf.xsd';
/**
* @param {Node} node Node.
* @param {Array.<*>} objectStack Object stack.
@@ -488,7 +542,7 @@ ol.format.GML.readFlatLinearRing_ = function(node, objectStack) {
* @param {Node} node Node.
* @param {Array.<*>} objectStack Object stack.
* @private
* @return {ol.geom.Polygon|undefined} Polygon.
* @return {ol.geom.LinearRing|undefined} LinearRing.
*/
ol.format.GML.readLinearRing_ = function(node, objectStack) {
goog.asserts.assert(node.nodeType == goog.dom.NodeType.ELEMENT);
@@ -496,10 +550,9 @@ ol.format.GML.readLinearRing_ = function(node, objectStack) {
var flatCoordinates =
ol.format.GML.readFlatCoordinatesFromNode_(node, objectStack);
if (goog.isDef(flatCoordinates)) {
var polygon = new ol.geom.Polygon(null);
polygon.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates,
[flatCoordinates.length]);
return polygon;
var ring = new ol.geom.LinearRing(null);
ring.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates);
return ring;
} else {
return undefined;
}
@@ -672,17 +725,23 @@ ol.format.GML.readFlatPosList_ = function(node, objectStack) {
}
var coords = s.split(/\s+/);
// The "dimension" attribute is from the GML 3.0.1 spec.
var dim = parseInt(node.getAttribute('srsDimension') ||
node.getAttribute('dimension'), 10) ||
(!goog.isNull(containerDimension)) ?
parseInt(containerDimension, 10) : 2;
var dim = 2;
if (!goog.isNull(node.getAttribute('srsDimension'))) {
dim = ol.format.XSD.readNonNegativeIntegerString(
node.getAttribute('srsDimension'));
} else if (!goog.isNull(node.getAttribute('dimension'))) {
dim = ol.format.XSD.readNonNegativeIntegerString(
node.getAttribute('dimension'));
} else if (!goog.isNull(containerDimension)) {
dim = ol.format.XSD.readNonNegativeIntegerString(containerDimension);
}
var x, y, z;
var flatCoordinates = [];
for (var i = 0, ii = coords.length; i < ii; i += dim) {
x = parseFloat(coords[i]);
y = parseFloat(coords[i + 1]);
z = (dim === 3) ? parseFloat(coords[i + 2]) : 0;
if (axisOrientation === 'enu') {
if (axisOrientation.substr(0, 2) === 'en') {
flatCoordinates.push(x, y, z);
} else {
flatCoordinates.push(y, x, z);
@@ -973,3 +1032,601 @@ ol.format.GML.prototype.readFeaturesFromNode = function(node) {
}];
return ol.format.GML.readFeatures_(node, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.Point} value Point geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writePos_ = function(node, value, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
var axisOrientation = 'enu';
if (goog.isDefAndNotNull(srsName)) {
axisOrientation = ol.proj.get(srsName).getAxisOrientation();
}
var point = value.getCoordinates();
var coords;
// only 2d for simple features profile
if (axisOrientation.substr(0, 2) === 'en') {
coords = (point[0] + ' ' + point[1]);
} else {
coords = (point[1] + ' ' + point[0]);
}
ol.format.XSD.writeStringTextNode(node, coords);
};
/**
* @param {Array.<number>} point Point geometry.
* @param {string=} opt_srsName Optional srsName
* @return {string}
* @private
*/
ol.format.GML.getCoords_ = function(point, opt_srsName) {
var axisOrientation = 'enu';
if (goog.isDefAndNotNull(opt_srsName)) {
axisOrientation = ol.proj.get(opt_srsName).getAxisOrientation();
}
return ((axisOrientation.substr(0, 2) === 'en') ?
point[0] + ' ' + point[1] :
point[1] + ' ' + point[0]);
};
/**
* @param {Node} node Node.
* @param {ol.geom.LineString|ol.geom.LinearRing} value Geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writePosList_ = function(node, value, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
// only 2d for simple features profile
var points = value.getCoordinates();
var len = points.length;
var parts = new Array(len);
var point;
for (var i = 0; i < len; ++i) {
point = points[i];
parts[i] = ol.format.GML.getCoords_(point, srsName);
}
ol.format.XSD.writeStringTextNode(node, parts.join(' '));
};
/**
* @param {Node} node Node.
* @param {ol.geom.Point} geometry Point geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writePoint_ = function(node, geometry, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
if (goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
var pos = ol.xml.createElementNS(node.namespaceURI, 'pos');
node.appendChild(pos);
ol.format.GML.writePos_(pos, geometry, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.LinearRing} geometry LinearRing geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeLinearRing_ = function(node, geometry, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
if (goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
var posList = ol.xml.createElementNS(node.namespaceURI, 'posList');
node.appendChild(posList);
ol.format.GML.writePosList_(posList, geometry, objectStack);
};
/**
* @param {*} value Value.
* @param {Array.<*>} objectStack Object stack.
* @param {string=} opt_nodeName Node name.
* @return {Node} Node.
* @private
*/
ol.format.GML.RING_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) {
var context = objectStack[objectStack.length - 1];
var parentNode = context.node;
goog.asserts.assert(goog.isObject(context));
var exteriorWritten = goog.object.get(context, 'exteriorWritten');
if (!goog.isDef(exteriorWritten)) {
goog.object.set(context, 'exteriorWritten', true);
}
return ol.xml.createElementNS(parentNode.namespaceURI,
goog.isDef(exteriorWritten) ? 'interior' : 'exterior');
};
/**
* @param {Node} node Node.
* @param {ol.geom.Polygon} geometry Polygon geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeSurfaceOrPolygon_ = function(node, geometry, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
if (node.nodeName !== 'PolygonPatch' && goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
if (node.nodeName === 'Polygon' || node.nodeName === 'PolygonPatch') {
var rings = geometry.getLinearRings();
ol.xml.pushSerializeAndPop(
{node: node, srsName: srsName},
ol.format.GML.RING_SERIALIZERS_, ol.format.GML.RING_NODE_FACTORY_,
rings, objectStack);
} else if (node.nodeName === 'Surface') {
var patches = ol.xml.createElementNS(node.namespaceURI, 'patches');
node.appendChild(patches);
ol.format.GML.writeSurfacePatches_(patches, geometry, objectStack);
}
};
/**
* @param {Node} node Node.
* @param {ol.geom.LineString} geometry LineString geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeCurveOrLineString_ = function(node, geometry, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
if (node.nodeName !== 'LineStringSegment' && goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
if (node.nodeName === 'LineString' || node.nodeName === 'LineStringSegment') {
var posList = ol.xml.createElementNS(node.namespaceURI, 'posList');
node.appendChild(posList);
ol.format.GML.writePosList_(posList, geometry, objectStack);
} else if (node.nodeName === 'Curve') {
var segments = ol.xml.createElementNS(node.namespaceURI, 'segments');
node.appendChild(segments);
ol.format.GML.writeCurveSegments_(segments, geometry, objectStack);
}
};
/**
* @param {Node} node Node.
* @param {ol.geom.MultiPolygon} geometry MultiPolygon geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeMultiSurfaceOrPolygon_ = function(node, geometry,
objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
var surface = goog.object.get(context, 'surface');
if (goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
var polygons = geometry.getPolygons();
ol.xml.pushSerializeAndPop({node: node, srsName: srsName, surface: surface},
ol.format.GML.SURFACEORPOLYGONMEMBER_SERIALIZERS_,
ol.format.GML.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, polygons,
objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.MultiPoint} geometry MultiPoint geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeMultiPoint_ = function(node, geometry,
objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
if (goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
var points = geometry.getPoints();
ol.xml.pushSerializeAndPop({node: node, srsName: srsName},
ol.format.GML.POINTMEMBER_SERIALIZERS_,
ol.xml.makeSimpleNodeFactory('pointMember'), points,
objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.MultiLineString} geometry MultiLineString geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeMultiCurveOrLineString_ = function(node, geometry,
objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var srsName = goog.object.get(context, 'srsName');
var curve = goog.object.get(context, 'curve');
if (goog.isDefAndNotNull(srsName)) {
node.setAttribute('srsName', srsName);
}
var lines = geometry.getLineStrings();
ol.xml.pushSerializeAndPop({node: node, srsName: srsName, curve: curve},
ol.format.GML.LINESTRINGORCURVEMEMBER_SERIALIZERS_,
ol.format.GML.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, lines,
objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.LinearRing} ring LinearRing geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeRing_ = function(node, ring, objectStack) {
var linearRing = ol.xml.createElementNS(node.namespaceURI, 'LinearRing');
node.appendChild(linearRing);
ol.format.GML.writeLinearRing_(linearRing, ring, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.Polygon} polygon Polygon geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeSurfaceOrPolygonMember_ = function(node, polygon,
objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var child = ol.format.GML.GEOMETRY_NODE_FACTORY_(polygon, objectStack);
if (goog.isDef(child)) {
node.appendChild(child);
ol.format.GML.writeSurfaceOrPolygon_(child, polygon, objectStack);
}
};
/**
* @param {Node} node Node.
* @param {ol.geom.Point} point Point geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writePointMember_ = function(node, point, objectStack) {
var child = ol.xml.createElementNS(node.namespaceURI, 'Point');
node.appendChild(child);
ol.format.GML.writePoint_(child, point, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.LineString} line LineString geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeLineStringOrCurveMember_ = function(node, line,
objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var child = ol.format.GML.GEOMETRY_NODE_FACTORY_(line, objectStack);
if (goog.isDef(child)) {
node.appendChild(child);
ol.format.GML.writeCurveOrLineString_(child, line, objectStack);
}
};
/**
* @param {Node} node Node.
* @param {ol.geom.Polygon} polygon Polygon geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeSurfacePatches_ = function(node, polygon, objectStack) {
var child = ol.xml.createElementNS(node.namespaceURI, 'PolygonPatch');
node.appendChild(child);
ol.format.GML.writeSurfaceOrPolygon_(child, polygon, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.LineString} line LineString geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeCurveSegments_ = function(node, line, objectStack) {
var child = ol.xml.createElementNS(node.namespaceURI, 'LineStringSegment');
node.appendChild(child);
ol.format.GML.writeCurveOrLineString_(child, line, objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.geom.Geometry} geometry Geometry.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeGeometry_ = function(node, geometry, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var item = goog.object.clone(context);
item.node = node;
ol.xml.pushSerializeAndPop(/** @type {ol.xml.NodeStackItem} */
(item), ol.format.GML.GEOMETRY_SERIALIZERS_,
ol.format.GML.GEOMETRY_NODE_FACTORY_, [geometry], objectStack);
};
/**
* @param {Node} node Node.
* @param {ol.Feature} feature Feature.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeFeature_ = function(node, feature, objectStack) {
var fid = feature.getId();
if (goog.isDef(fid)) {
node.setAttribute('fid', fid);
}
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var featureNS = goog.object.get(context, 'featureNS');
var geometryName = feature.getGeometryName();
if (!goog.isDef(context.serializers)) {
context.serializers = {};
context.serializers[featureNS] = {};
}
var properties = feature.getProperties();
var keys = [], values = [];
for (var key in properties) {
keys.push(key);
values.push(properties[key]);
if (key == geometryName) {
if (!(key in context.serializers[featureNS])) {
context.serializers[featureNS][key] = ol.xml.makeChildAppender(
ol.format.GML.writeGeometry_);
}
} else {
if (!(key in context.serializers[featureNS])) {
context.serializers[featureNS][key] = ol.xml.makeChildAppender(
ol.format.XSD.writeStringTextNode);
}
}
}
var item = goog.object.clone(context);
item.node = node;
ol.xml.pushSerializeAndPop(/** @type {ol.xml.NodeStackItem} */
(item), context.serializers,
ol.xml.OBJECT_PROPERTY_NODE_FACTORY,
values,
objectStack, keys);
};
/**
* @param {Node} node Node.
* @param {Array.<ol.Feature>} features Features.
* @param {Array.<*>} objectStack Node stack.
* @private
*/
ol.format.GML.writeFeatureMembers_ = function(node, features, objectStack) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var featureType = goog.object.get(context, 'featureType');
var featureNS = goog.object.get(context, 'featureNS');
var serializers = {};
serializers[featureNS] = {};
serializers[featureNS][featureType] = ol.xml.makeChildAppender(
ol.format.GML.writeFeature_);
var item = goog.object.clone(context);
item.node = node;
ol.xml.pushSerializeAndPop(/** @type {ol.xml.NodeStackItem} */
(item),
serializers,
ol.xml.makeSimpleNodeFactory(featureType, featureNS), features,
objectStack);
};
/**
* @type {Object.<string, Object.<string, ol.xml.Serializer>>}
* @private
*/
ol.format.GML.SURFACEORPOLYGONMEMBER_SERIALIZERS_ = {
'http://www.opengis.net/gml': {
'surfaceMember': ol.xml.makeChildAppender(
ol.format.GML.writeSurfaceOrPolygonMember_),
'polygonMember': ol.xml.makeChildAppender(
ol.format.GML.writeSurfaceOrPolygonMember_)
}
};
/**
* @type {Object.<string, Object.<string, ol.xml.Serializer>>}
* @private
*/
ol.format.GML.POINTMEMBER_SERIALIZERS_ = {
'http://www.opengis.net/gml': {
'pointMember': ol.xml.makeChildAppender(ol.format.GML.writePointMember_)
}
};
/**
* @type {Object.<string, Object.<string, ol.xml.Serializer>>}
* @private
*/
ol.format.GML.LINESTRINGORCURVEMEMBER_SERIALIZERS_ = {
'http://www.opengis.net/gml': {
'lineStringMember': ol.xml.makeChildAppender(
ol.format.GML.writeLineStringOrCurveMember_),
'curveMember': ol.xml.makeChildAppender(
ol.format.GML.writeLineStringOrCurveMember_)
}
};
/**
* @type {Object.<string, Object.<string, ol.xml.Serializer>>}
* @private
*/
ol.format.GML.RING_SERIALIZERS_ = {
'http://www.opengis.net/gml': {
'exterior': ol.xml.makeChildAppender(ol.format.GML.writeRing_),
'interior': ol.xml.makeChildAppender(ol.format.GML.writeRing_)
}
};
/**
* @type {Object.<string, Object.<string, ol.xml.Serializer>>}
* @private
*/
ol.format.GML.GEOMETRY_SERIALIZERS_ = {
'http://www.opengis.net/gml': {
'Curve': ol.xml.makeChildAppender(ol.format.GML.writeCurveOrLineString_),
'MultiCurve': ol.xml.makeChildAppender(
ol.format.GML.writeMultiCurveOrLineString_),
'Point': ol.xml.makeChildAppender(ol.format.GML.writePoint_),
'MultiPoint': ol.xml.makeChildAppender(ol.format.GML.writeMultiPoint_),
'LineString': ol.xml.makeChildAppender(
ol.format.GML.writeCurveOrLineString_),
'MultiLineString': ol.xml.makeChildAppender(
ol.format.GML.writeMultiCurveOrLineString_),
'LinearRing': ol.xml.makeChildAppender(ol.format.GML.writeLinearRing_),
'Polygon': ol.xml.makeChildAppender(ol.format.GML.writeSurfaceOrPolygon_),
'MultiPolygon': ol.xml.makeChildAppender(
ol.format.GML.writeMultiSurfaceOrPolygon_),
'Surface': ol.xml.makeChildAppender(ol.format.GML.writeSurfaceOrPolygon_),
'MultiSurface': ol.xml.makeChildAppender(
ol.format.GML.writeMultiSurfaceOrPolygon_)
}
};
/**
* @const
* @type {Object.<string, string>}
* @private
*/
ol.format.GML.MULTIGEOMETRY_TO_MEMBER_NODENAME_ = {
'MultiLineString': 'lineStringMember',
'MultiCurve': 'curveMember',
'MultiPolygon': 'polygonMember',
'MultiSurface': 'surfaceMember'
};
/**
* @const
* @param {*} value Value.
* @param {Array.<*>} objectStack Object stack.
* @param {string=} opt_nodeName Node name.
* @return {Node|undefined} Node.
* @private
*/
ol.format.GML.MULTIGEOMETRY_MEMBER_NODE_FACTORY_ = function(value,
objectStack, opt_nodeName) {
var parentNode = objectStack[objectStack.length - 1].node;
goog.asserts.assert(ol.xml.isNode(parentNode));
return ol.xml.createElementNS('http://www.opengis.net/gml',
ol.format.GML.MULTIGEOMETRY_TO_MEMBER_NODENAME_[parentNode.nodeName]);
};
/**
* @const
* @param {*} value Value.
* @param {Array.<*>} objectStack Object stack.
* @param {string=} opt_nodeName Node name.
* @return {Node|undefined} Node.
* @private
*/
ol.format.GML.GEOMETRY_NODE_FACTORY_ = function(value, objectStack,
opt_nodeName) {
var context = objectStack[objectStack.length - 1];
goog.asserts.assert(goog.isObject(context));
var multiSurface = goog.object.get(context, 'multiSurface');
var surface = goog.object.get(context, 'surface');
var curve = goog.object.get(context, 'curve');
var multiCurve = goog.object.get(context, 'multiCurve');
goog.asserts.assertInstanceof(value, ol.geom.Geometry);
var parentNode = objectStack[objectStack.length - 1].node;
goog.asserts.assert(ol.xml.isNode(parentNode));
var nodeName = value.getType();
if (nodeName === 'MultiPolygon' && multiSurface === true) {
nodeName = 'MultiSurface';
} else if (nodeName === 'Polygon' && surface === true) {
nodeName = 'Surface';
} else if (nodeName === 'LineString' && curve === true) {
nodeName = 'Curve';
} else if (nodeName === 'MultiLineString' && multiCurve === true) {
nodeName = 'MultiCurve';
}
return ol.xml.createElementNS('http://www.opengis.net/gml',
nodeName);
};
/**
* @inheritDoc
*/
ol.format.GML.prototype.writeGeometryNode = function(geometry) {
var geom = ol.xml.createElementNS('http://www.opengis.net/gml', 'geom');
var context = {node: geom, srsName: this.srsName_,
curve: this.curve_, surface: this.surface_,
multiSurface: this.multiSurface_, multiCurve: this.multiCurve_};
ol.xml.pushSerializeAndPop(/** @type {ol.xml.NodeStackItem} */
(context), ol.format.GML.GEOMETRY_SERIALIZERS_,
ol.format.GML.GEOMETRY_NODE_FACTORY_, [geometry], []);
return geom;
};
/**
* @inheritDoc
*/
ol.format.GML.prototype.writeFeaturesNode = function(features) {
var node = ol.xml.createElementNS('http://www.opengis.net/gml',
'featureMembers');
ol.xml.setAttributeNS(node, 'http://www.w3.org/2001/XMLSchema-instance',
'xsi:schemaLocation', this.schemaLocation_);
var context = {
srsName: this.srsName_,
curve: this.curve_,
surface: this.surface_,
multiSurface: this.multiSurface_,
multiCurve: this.multiCurve_,
featureNS: this.featureNS_,
featureType: this.featureType_
};
ol.format.GML.writeFeatureMembers_(node, features, [context]);
return node;
};

View File

@@ -7,9 +7,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>37.5101 -88.0711 37.5831 -88.1341 37.6281 -88.1571
37.6601 -88.1591 37.7001 -88.1331 37.7351 -88.0721 37.8051
-88.0351 37.8171 -88.0861 37.8311 -88.0891 37.8271 -88.0421
@@ -138,9 +138,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.9661 -77.0081 38.9931 -77.0421 38.9321 -77.1221
38.9151 -77.0781 38.8861 -77.0671 38.8621 -77.0391 38.8381
-77.0401 38.8291 -77.0451 38.8131 -77.0351 38.7881 -77.0451
@@ -179,9 +179,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.5571 -75.7071 38.4631 -75.6991 38.4551 -75.3501
38.4501 -75.0931 38.4491 -75.0681 38.4491 -75.0451 38.7991
-75.0831 38.8081 -75.1901 38.9451 -75.3071 39.0121 -75.3241
@@ -227,9 +227,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.4801 -79.2311 38.6581 -79.1271 38.6631 -79.1211
38.6591 -79.0881 38.7071 -79.0871 38.7611 -79.0561 38.7901
-79.0551 38.7991 -79.0331 38.8461 -78.9871 38.7631 -78.8661
@@ -378,9 +378,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.6491 -75.7111 38.8301 -75.7241 39.1411 -75.7521
39.2471 -75.7611 39.2951 -75.7641 39.3831 -75.7721 39.7231
-75.7911 39.7221 -76.1391 39.7211 -76.2331 39.7201 -76.5701
@@ -456,9 +456,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.9071 -76.2931 38.9491 -76.2731 38.9231 -76.2461
38.9781 -76.2481 39.0401 -76.2991 38.9581 -76.3561 38.8541
-76.3751 38.8751 -76.3291 38.9241 -76.3421 38.9121 -76.3221
@@ -469,9 +469,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.4491 -75.0681 38.3221 -75.0871 38.4491 -75.0451
38.4491 -75.0681</gml:posList>
</gml:LinearRing>
@@ -479,9 +479,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.0271 -75.2701 38.0281 -75.2421 38.1241 -75.1731
38.3201 -75.0941 38.2041 -75.1641 38.0941 -75.2091 38.0371
-75.2441 38.0271 -75.2701</gml:posList>
@@ -519,9 +519,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>37.6411 -102.0431 37.7341 -102.0431 38.2531 -102.0451
38.2631 -102.0451 38.6151 -102.0471 38.6921 -102.0471 39.0361
-102.0481 39.1261 -102.0471 39.5621 -102.0481 39.5681 -102.0481
@@ -573,9 +573,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>36.6551 -86.5101 36.6501 -86.4151 36.6431 -86.1991
36.6331 -85.9801 36.6261 -85.7851 36.6181 -85.4371 36.6261
-85.3001 36.6251 -85.2721 36.6201 -84.9981 36.6051 -84.7911
@@ -681,9 +681,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>36.4981 -89.5331 36.4981 -89.4751 36.5041 -89.4811
36.5251 -89.4711 36.5471 -89.4811 36.5591 -89.4931 36.5641
-89.5301 36.5571 -89.5561 36.5411 -89.5681 36.5181 -89.5661
@@ -722,9 +722,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>37.0011 -95.0711 37.0001 -95.0321 36.9961 -94.6201
37.0601 -94.6201 37.3271 -94.6181 37.3601 -94.6181 37.6501
-94.6181 37.6791 -94.6191 38.0301 -94.6161 38.0551 -94.6171
@@ -795,9 +795,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>36.5461 -79.1441 36.5431 -78.7961 36.5461 -78.7371
36.5411 -78.4581 36.5451 -78.3211 36.5521 -78.0511 36.5521
-77.8981 36.5531 -77.7631 36.5531 -77.3201 36.5561 -77.1771
@@ -907,9 +907,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>38.0271 -75.2701 37.9181 -75.3461 37.9001 -75.3781
37.9011 -75.3441 37.8751 -75.3861 37.8881 -75.3391 37.9621
-75.2981 38.0281 -75.2421 38.0271 -75.2701</gml:posList>
@@ -918,9 +918,9 @@
</gml:Polygon>
</gml:surfaceMember>
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>37.5521 -75.8671 37.5561 -75.9301 37.5211 -75.9541
37.4791 -75.9651 37.4841 -75.9341 37.3081 -76.0181 37.1261
-75.9701 37.1421 -75.9311 37.3671 -75.8971 37.4181 -75.8261
@@ -965,9 +965,9 @@
<feature:the_geom>
<gml:MultiSurface srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:surfaceMember>
<gml:Polygon>
<gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:exterior>
<gml:LinearRing>
<gml:LinearRing srsName="urn:x-ogc:def:crs:EPSG:4326">
<gml:posList>36.9531 -89.1041 36.9771 -89.1071 36.9881 -89.1291
36.9861 -89.1931 37.0281 -89.2101 37.0411 -89.2371 37.0871
-89.2641 37.0911 -89.2841 37.0851 -89.3031 37.0601 -89.3091

View File

@@ -10,16 +10,17 @@ var readGeometry = function(format, text) {
describe('ol.format.GML', function() {
var format;
var format, formatWGS84;
beforeEach(function() {
format = new ol.format.GML();
format = new ol.format.GML({srsName: 'CRS:84'});
formatWGS84 = new ol.format.GML({srsName: 'urn:x-ogc:def:crs:EPSG:4326'});
});
describe('#readGeometry', function() {
describe('point', function() {
it('can read a point geometry', function() {
it('can read and write a point geometry', function() {
var text =
'<gml:Point xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
@@ -28,13 +29,15 @@ describe('ol.format.GML', function() {
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.Point);
expect(g.getCoordinates()).to.eql([1, 2, 0]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('linestring', function() {
it('can read a linestring geometry', function() {
it('can read and write a linestring geometry', function() {
var text =
'<gml:LineString xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
@@ -43,56 +46,71 @@ describe('ol.format.GML', function() {
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.LineString);
expect(g.getCoordinates()).to.eql([[1, 2, 0], [3, 4, 0]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('axis order', function() {
it('can read a linestring geometry with correct axis order', function() {
var text =
'<gml:LineString xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:posList>-90 -180 90 180</gml:posList>' +
'</gml:LineString>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.LineString);
expect(g.getCoordinates()).to.eql([[-180, -90, 0], [180, 90, 0]]);
});
it('can read and write a linestring geometry with ' +
'correct axis order', function() {
var text =
'<gml:LineString xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:posList>-90 -180 90 180</gml:posList>' +
'</gml:LineString>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.LineString);
expect(g.getCoordinates()).to.eql([[-180, -90, 0], [180, 90, 0]]);
var serialized = formatWGS84.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a point geometry with correct axis order', function() {
var text =
'<gml:Point xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:pos>-90 -180</gml:pos>' +
'</gml:Point>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.Point);
expect(g.getCoordinates()).to.eql([-180, -90, 0]);
});
it('can read and write a point geometry with correct axis order',
function() {
var text =
'<gml:Point xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:pos>-90 -180</gml:pos>' +
'</gml:Point>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.Point);
expect(g.getCoordinates()).to.eql([-180, -90, 0]);
var serialized = formatWGS84.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read multi surface geometry with right axis order', function() {
var text =
'<gml:MultiSurface xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:surfaceMember>' +
' <gml:Polygon>' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:posList>38.9661 -77.0081 38.9931 -77.0421 ' +
' 38.9321 -77.1221 38.9151 -77.0781 38.8861 -77.0671 ' +
' 38.8621 -77.0391 38.8381 -77.0401 38.8291 -77.0451 ' +
' 38.8131 -77.0351 38.7881 -77.0451' +
' 38.8891 -76.9111 38.9661 -77.0081</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' </gml:Polygon>' +
' </gml:surfaceMember>' +
'</gml:MultiSurface>';
var g = readGeometry(format, text);
expect(g.getCoordinates()[0][0][0][0]).to.equal(-77.0081);
expect(g.getCoordinates()[0][0][0][1]).to.equal(38.9661);
});
it('can read and write a surface geometry with right axis order',
function() {
var text =
'<gml:MultiSurface xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:surfaceMember>' +
' <gml:Polygon srsName="urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:exterior>' +
' <gml:LinearRing srsName=' +
' "urn:x-ogc:def:crs:EPSG:4326">' +
' <gml:posList>38.9661 -77.0081 38.9931 -77.0421 ' +
' 38.9321 -77.1221 38.9151 -77.0781 38.8861 ' +
' -77.0671 38.8621 -77.0391 38.8381 -77.0401 ' +
' 38.8291 -77.0451 38.8131 -77.0351 38.7881 ' +
' -77.0451 38.8891 -76.9111 38.9661 -77.0081' +
' </gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' </gml:Polygon>' +
' </gml:surfaceMember>' +
'</gml:MultiSurface>';
var g = readGeometry(format, text);
expect(g.getCoordinates()[0][0][0][0]).to.equal(-77.0081);
expect(g.getCoordinates()[0][0][0][1]).to.equal(38.9661);
format = new ol.format.GML({srsName: 'urn:x-ogc:def:crs:EPSG:4326',
surface: false});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
@@ -113,38 +131,40 @@ describe('ol.format.GML', function() {
describe('linearring', function() {
it('can read a linearring geometry', function() {
it('can read and write a linearring geometry', function() {
var text =
'<gml:LinearRing xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:posList>1 2 3 4 5 6 1 2</gml:posList>' +
'</gml:LinearRing>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.Polygon);
expect(g).to.be.an(ol.geom.LinearRing);
expect(g.getCoordinates()).to.eql(
[[[1, 2, 0], [3, 4, 0], [5, 6, 0], [1, 2, 0]]]);
[[1, 2, 0], [3, 4, 0], [5, 6, 0], [1, 2, 0]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('polygon', function() {
it('can read a polygon geometry', function() {
it('can read and write a polygon geometry', function() {
var text =
'<gml:Polygon xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>2 3 2 5 4 5 2 3</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>3 4 3 6 5 6 3 4</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
@@ -154,30 +174,32 @@ describe('ol.format.GML', function() {
expect(g.getCoordinates()).to.eql([[[1, 2, 0], [3, 2, 0], [3, 4, 0],
[1, 2, 0]], [[2, 3, 0], [2, 5, 0], [4, 5, 0], [2, 3, 0]],
[[3, 4, 0], [3, 6, 0], [5, 6, 0], [3, 4, 0]]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('surface', function() {
it('can read a surface geometry', function() {
it('can read and write a surface geometry', function() {
var text =
'<gml:Surface xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:patches>' +
' <gml:PolygonPatch interpolation="planar">' +
' <gml:PolygonPatch>' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>2 3 2 5 4 5 2 3</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>3 4 3 6 5 6 3 4</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
@@ -189,13 +211,16 @@ describe('ol.format.GML', function() {
expect(g.getCoordinates()).to.eql([[[1, 2, 0], [3, 2, 0], [3, 4, 0],
[1, 2, 0]], [[2, 3, 0], [2, 5, 0], [4, 5, 0], [2, 3, 0]],
[[3, 4, 0], [3, 6, 0], [5, 6, 0], [3, 4, 0]]]);
format = new ol.format.GML({srsName: 'CRS:84', surface: true});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('curve', function() {
it('can read a curve geometry', function() {
it('can read and write a curve geometry', function() {
var text =
'<gml:Curve xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
@@ -208,6 +233,9 @@ describe('ol.format.GML', function() {
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.LineString);
expect(g.getCoordinates()).to.eql([[1, 2, 0], [3, 4, 0]]);
format = new ol.format.GML({srsName: 'CRS:84', curve: true});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
@@ -229,22 +257,22 @@ describe('ol.format.GML', function() {
describe('multipoint', function() {
it('can read a singular multipoint geometry', function() {
it('can read and write a singular multipoint geometry', function() {
var text =
'<gml:MultiPoint xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:pointMember>' +
' <gml:Point>' +
' <gml:Point srsName="CRS:84">' +
' <gml:pos>1 2</gml:pos>' +
' </gml:Point>' +
' </gml:pointMember>' +
' <gml:pointMember>' +
' <gml:Point>' +
' <gml:Point srsName="CRS:84">' +
' <gml:pos>2 3</gml:pos>' +
' </gml:Point>' +
' </gml:pointMember>' +
' <gml:pointMember>' +
' <gml:Point>' +
' <gml:Point srsName="CRS:84">' +
' <gml:pos>3 4</gml:pos>' +
' </gml:Point>' +
' </gml:pointMember>' +
@@ -252,6 +280,8 @@ describe('ol.format.GML', function() {
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.MultiPoint);
expect(g.getCoordinates()).to.eql([[1, 2, 0], [2, 3, 0], [3, 4, 0]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a plural multipoint geometry', function() {
@@ -279,17 +309,17 @@ describe('ol.format.GML', function() {
describe('multilinestring', function() {
it('can read a singular multilinestring geometry', function() {
it('can read and write a singular multilinestring geometry', function() {
var text =
'<gml:MultiLineString xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:lineStringMember>' +
' <gml:LineString>' +
' <gml:LineString srsName="CRS:84">' +
' <gml:posList>1 2 2 3</gml:posList>' +
' </gml:LineString>' +
' </gml:lineStringMember>' +
' <gml:lineStringMember>' +
' <gml:LineString>' +
' <gml:LineString srsName="CRS:84">' +
' <gml:posList>3 4 4 5</gml:posList>' +
' </gml:LineString>' +
' </gml:lineStringMember>' +
@@ -298,6 +328,9 @@ describe('ol.format.GML', function() {
expect(g).to.be.an(ol.geom.MultiLineString);
expect(g.getCoordinates()).to.eql(
[[[1, 2, 0], [2, 3, 0]], [[3, 4, 0], [4, 5, 0]]]);
format = new ol.format.GML({srsName: 'CRS:84', multiCurve: false});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a plural multilinestring geometry', function() {
@@ -323,33 +356,33 @@ describe('ol.format.GML', function() {
describe('multipolygon', function() {
it('can read a singular multipolygon geometry', function() {
it('can read and write a singular multipolygon geometry', function() {
var text =
'<gml:MultiPolygon xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:polygonMember>' +
' <gml:Polygon>' +
' <gml:Polygon srsName="CRS:84">' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>2 3 2 5 4 5 2 3</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>3 4 3 6 5 6 3 4</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' </gml:Polygon>' +
' </gml:polygonMember>' +
' <gml:polygonMember>' +
' <gml:Polygon>' +
' <gml:Polygon srsName="CRS:84">' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
@@ -363,6 +396,9 @@ describe('ol.format.GML', function() {
[1, 2, 0]], [[2, 3, 0], [2, 5, 0], [4, 5, 0], [2, 3, 0]],
[[3, 4, 0], [3, 6, 0], [5, 6, 0], [3, 4, 0]]],
[[[1, 2, 0], [3, 2, 0], [3, 4, 0], [1, 2, 0]]]]);
format = new ol.format.GML({srsName: 'CRS:84', multiSurface: false});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a plural multipolygon geometry', function() {
@@ -409,33 +445,36 @@ describe('ol.format.GML', function() {
describe('multicurve', function() {
it('can read a singular multicurve-linestring geometry', function() {
var text =
'<gml:MultiCurve xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:curveMember>' +
' <gml:LineString>' +
' <gml:posList>1 2 2 3</gml:posList>' +
' </gml:LineString>' +
' </gml:curveMember>' +
' <gml:curveMember>' +
' <gml:LineString>' +
' <gml:posList>3 4 4 5</gml:posList>' +
' </gml:LineString>' +
' </gml:curveMember>' +
'</gml:MultiCurve>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.MultiLineString);
expect(g.getCoordinates()).to.eql(
[[[1, 2, 0], [2, 3, 0]], [[3, 4, 0], [4, 5, 0]]]);
});
it('can read and write a singular multicurve-linestring geometry',
function() {
var text =
'<gml:MultiCurve xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:curveMember>' +
' <gml:LineString srsName="CRS:84">' +
' <gml:posList>1 2 2 3</gml:posList>' +
' </gml:LineString>' +
' </gml:curveMember>' +
' <gml:curveMember>' +
' <gml:LineString srsName="CRS:84">' +
' <gml:posList>3 4 4 5</gml:posList>' +
' </gml:LineString>' +
' </gml:curveMember>' +
'</gml:MultiCurve>';
var g = readGeometry(format, text);
expect(g).to.be.an(ol.geom.MultiLineString);
expect(g.getCoordinates()).to.eql(
[[[1, 2, 0], [2, 3, 0]], [[3, 4, 0], [4, 5, 0]]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a singular multicurve-curve geometry', function() {
it('can read and write a singular multicurve-curve geometry', function() {
var text =
'<gml:MultiCurve xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:curveMember>' +
' <gml:Curve>' +
' <gml:Curve srsName="CRS:84">' +
' <gml:segments>' +
' <gml:LineStringSegment>' +
' <gml:posList>1 2 2 3</gml:posList>' +
@@ -444,7 +483,7 @@ describe('ol.format.GML', function() {
' </gml:Curve>' +
' </gml:curveMember>' +
' <gml:curveMember>' +
' <gml:Curve>' +
' <gml:Curve srsName="CRS:84">' +
' <gml:segments>' +
' <gml:LineStringSegment>' +
' <gml:posList>3 4 4 5</gml:posList>' +
@@ -457,39 +496,42 @@ describe('ol.format.GML', function() {
expect(g).to.be.an(ol.geom.MultiLineString);
expect(g.getCoordinates()).to.eql(
[[[1, 2, 0], [2, 3, 0]], [[3, 4, 0], [4, 5, 0]]]);
format = new ol.format.GML({srsName: 'CRS:84', curve: true});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
describe('multisurface', function() {
it('can read a singular multisurface geometry', function() {
it('can read and write a singular multisurface geometry', function() {
var text =
'<gml:MultiSurface xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:surfaceMember>' +
' <gml:Polygon>' +
' <gml:Polygon srsName="CRS:84">' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>2 3 2 5 4 5 2 3</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>3 4 3 6 5 6 3 4</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' </gml:Polygon>' +
' </gml:surfaceMember>' +
' <gml:surfaceMember>' +
' <gml:Polygon>' +
' <gml:Polygon srsName="CRS:84">' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
@@ -503,6 +545,8 @@ describe('ol.format.GML', function() {
[1, 2, 0]], [[2, 3, 0], [2, 5, 0], [4, 5, 0], [2, 3, 0]],
[[3, 4, 0], [3, 6, 0], [5, 6, 0], [3, 4, 0]]],
[[[1, 2, 0], [3, 2, 0], [3, 4, 0], [1, 2, 0]]]]);
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
it('can read a plural multisurface geometry', function() {
@@ -547,26 +591,26 @@ describe('ol.format.GML', function() {
[[[1, 2, 0], [3, 2, 0], [3, 4, 0], [1, 2, 0]]]]);
});
it('can read a multisurface-surface geometry', function() {
it('can read and write a multisurface-surface geometry', function() {
var text =
'<gml:MultiSurface xmlns:gml="http://www.opengis.net/gml" ' +
' srsName="CRS:84">' +
' <gml:surfaceMember>' +
' <gml:Surface>' +
' <gml:Surface srsName="CRS:84">' +
' <gml:patches>' +
' <gml:PolygonPatch interpolation="planar">' +
' <gml:PolygonPatch>' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>2 3 2 5 4 5 2 3</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
' <gml:interior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>3 4 3 6 5 6 3 4</gml:posList>' +
' </gml:LinearRing>' +
' </gml:interior>' +
@@ -575,11 +619,11 @@ describe('ol.format.GML', function() {
' </gml:Surface>' +
' </gml:surfaceMember>' +
' <gml:surfaceMember>' +
' <gml:Surface>' +
' <gml:Surface srsName="CRS:84">' +
' <gml:patches>' +
' <gml:PolygonPatch interpolation="planar">' +
' <gml:PolygonPatch>' +
' <gml:exterior>' +
' <gml:LinearRing>' +
' <gml:LinearRing srsName="CRS:84">' +
' <gml:posList>1 2 3 2 3 4 1 2</gml:posList>' +
' </gml:LinearRing>' +
' </gml:exterior>' +
@@ -595,6 +639,9 @@ describe('ol.format.GML', function() {
[1, 2, 0]], [[2, 3, 0], [2, 5, 0], [4, 5, 0], [2, 3, 0]],
[[3, 4, 0], [3, 6, 0], [5, 6, 0], [3, 4, 0]]],
[[[1, 2, 0], [3, 2, 0], [3, 4, 0], [1, 2, 0]]]]);
format = new ol.format.GML({srsName: 'CRS:84', surface: true});
var serialized = format.writeGeometry(g);
expect(serialized.firstElementChild).to.xmleql(ol.xml.load(text));
});
});
@@ -632,15 +679,25 @@ describe('ol.format.GML', function() {
describe('when parsing TOPP states GML', function() {
var features;
var features, text, gmlFormat;
before(function(done) {
afterLoadText('spec/ol/format/gml/topp-states-gml.xml', function(xml) {
try {
var schemaLoc = 'http://www.openplans.org/topp ' +
'http://demo.opengeo.org/geoserver/wfs?service=WFS&version=' +
'1.1.0&request=DescribeFeatureType&typeName=topp:states ' +
'http://www.opengis.net/gml ' +
'http://schemas.opengis.net/gml/3.2.1/gml.xsd';
var config = {
'featureNS': 'http://www.openplans.org/topp',
'featureType': 'states'
'featureType': 'states',
'multiSurface': true,
'srsName': 'urn:x-ogc:def:crs:EPSG:4326',
'schemaLocation': schemaLoc
};
features = new ol.format.GML(config).readFeatures(xml);
text = xml;
gmlFormat = new ol.format.GML(config);
features = gmlFormat.readFeatures(xml);
} catch (e) {
done(e);
}
@@ -656,6 +713,11 @@ describe('ol.format.GML', function() {
expect(features[0].getId()).to.equal('states.1');
});
it('writes back features as GML', function() {
var serialized = gmlFormat.writeFeatures(features);
expect(serialized).to.xmleql(ol.xml.load(text));
});
});
describe('when parsing TOPP states GML from WFS', function() {
@@ -747,6 +809,7 @@ goog.require('goog.dom');
goog.require('goog.dom.TagName');
goog.require('ol.format.GML');
goog.require('ol.geom.LineString');
goog.require('ol.geom.LinearRing');
goog.require('ol.geom.MultiPoint');
goog.require('ol.geom.MultiLineString');
goog.require('ol.geom.MultiPolygon');