Formats now support reprojection using internalProjection and
externalProjection properties. These allow for the reprojection of data -- OpenLayers users with SphericalMercator get this built in for EPSG:900913, and other users can use the external proj4js library available from MapBuilder SVN to add support for any number of projections. This means that featres can be, for example, transformed from a KML doc in 4326 to Spherical Mercator before being added to a layer, making using SphericalMercator slightly more enticing. r=elemoine (Closes #1039) git-svn-id: http://svn.openlayers.org/trunk/openlayers@5516 dc9f47b5-9b13-0410-9fdd-eb0c1a62fdaf
This commit is contained in:
@@ -55,6 +55,32 @@
|
||||
<script src="../lib/OpenLayers.js"></script>
|
||||
<script type="text/javascript">
|
||||
var map, vectors, formats;
|
||||
function updateFormats() {
|
||||
var in_options = {
|
||||
'internalProjection': map.baseLayer.projection,
|
||||
'externalProjection': new OpenLayers.Projection(OpenLayers.Util.getElement("inproj").value)
|
||||
}
|
||||
var out_options = {
|
||||
'internalProjection': map.baseLayer.projection,
|
||||
'externalProjection': new OpenLayers.Projection(OpenLayers.Util.getElement("outproj").value)
|
||||
}
|
||||
formats = {
|
||||
'in': {
|
||||
wkt: new OpenLayers.Format.WKT(in_options),
|
||||
geojson: new OpenLayers.Format.GeoJSON(in_options),
|
||||
georss: new OpenLayers.Format.GeoRSS(in_options),
|
||||
gml: new OpenLayers.Format.GML(in_options),
|
||||
kml: new OpenLayers.Format.KML(in_options)
|
||||
},
|
||||
'out': {
|
||||
wkt: new OpenLayers.Format.WKT(out_options),
|
||||
geojson: new OpenLayers.Format.GeoJSON(out_options),
|
||||
georss: new OpenLayers.Format.GeoRSS(out_options),
|
||||
gml: new OpenLayers.Format.GML(out_options),
|
||||
kml: new OpenLayers.Format.KML(out_options)
|
||||
}
|
||||
};
|
||||
}
|
||||
function init(){
|
||||
map = new OpenLayers.Map('map');
|
||||
var wms = new OpenLayers.Layer.WMS( "OpenLayers WMS",
|
||||
@@ -74,13 +100,7 @@
|
||||
map.addControl(select);
|
||||
select.activate();
|
||||
|
||||
formats = {
|
||||
wkt: new OpenLayers.Format.WKT(),
|
||||
geojson: new OpenLayers.Format.GeoJSON(),
|
||||
georss: new OpenLayers.Format.GeoRSS(),
|
||||
gml: new OpenLayers.Format.GML(),
|
||||
kml: new OpenLayers.Format.KML()
|
||||
};
|
||||
updateFormats();
|
||||
|
||||
map.setCenter(new OpenLayers.LonLat(0, 0), 1);
|
||||
}
|
||||
@@ -89,7 +109,7 @@
|
||||
var type = document.getElementById("formatType").value;
|
||||
// second argument for pretty printing (geojson only)
|
||||
var pretty = document.getElementById("prettyPrint").checked;
|
||||
var str = formats[type].write(feature, pretty);
|
||||
var str = formats['out'][type].write(feature, pretty);
|
||||
// not a good idea in general, just for this demo
|
||||
str = str.replace(/,/g, ', ');
|
||||
document.getElementById('output').value = str;
|
||||
@@ -98,7 +118,7 @@
|
||||
function deserialize() {
|
||||
var element = document.getElementById('text');
|
||||
var type = document.getElementById("formatType").value;
|
||||
var features = formats[type].read(element.value);
|
||||
var features = formats['in'][type].read(element.value);
|
||||
var bounds;
|
||||
if(features) {
|
||||
if(features.constructor != Array) {
|
||||
@@ -164,6 +184,15 @@
|
||||
<input id="prettyPrint" type="checkbox"
|
||||
name="prettyPrint" value="1" />
|
||||
<br />
|
||||
Input Projection: <select id="inproj" onchange='updateFormats()'>
|
||||
<option value="EPSG:4326" selected="selected">EPSG:4326</option>
|
||||
<option value="EPSG:900913">Spherical Mercator</option>
|
||||
</select> <br />
|
||||
Output Projection: <select id="outproj" onchange='updateFormats()'>
|
||||
<option value="EPSG:4326" selected="selected">EPSG:4326</option>
|
||||
<option value="EPSG:900913">Spherical Mercator</option>
|
||||
</select>
|
||||
<br />
|
||||
<textarea id="text">paste text here...</textarea>
|
||||
<br />
|
||||
<input type="button" value="add feature" onclick="deserialize();" />
|
||||
|
||||
@@ -11,6 +11,34 @@
|
||||
*/
|
||||
OpenLayers.Format = OpenLayers.Class({
|
||||
|
||||
/**
|
||||
* APIProperty: externalProjection
|
||||
* {<OpenLayers.Projection>} When passed a externalProjection and
|
||||
* internalProjection, the format will reproject the geometries it
|
||||
* reads or writes. The externalProjection is the projection used by
|
||||
* the content which is passed into read or which comes out of write.
|
||||
* In order to reproject, a projection transformation function for the
|
||||
* specified projections must be available. This support may be
|
||||
* provided via proj4js or via a custom transformation function. See
|
||||
* {<OpenLayers.Projection.addTransform>} for more information on
|
||||
* custom transformations.
|
||||
*/
|
||||
externalProjection: null,
|
||||
|
||||
/**
|
||||
* APIProperty: internalProjection
|
||||
* {<OpenLayers.Projection>} When passed a externalProjection and
|
||||
* internalProjection, the format will reproject the geometries it
|
||||
* reads or writes. The internalProjection is the projection used by
|
||||
* the geometries which are returned by read or which are passed into
|
||||
* write. In order to reproject, a projection transformation function
|
||||
* for the specified projections must be available. This support may be
|
||||
* provided via proj4js or via a custom transformation function. See
|
||||
* {<OpenLayers.Projection.addTransform>} for more information on
|
||||
* custom transformations.
|
||||
*/
|
||||
internalProjection: null,
|
||||
|
||||
/**
|
||||
* Constructor: OpenLayers.Format
|
||||
* Instances of this class are not useful. See one of the subclasses.
|
||||
|
||||
@@ -147,6 +147,10 @@ OpenLayers.Format.GML = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
var parser = this.parseGeometry[type.toLowerCase()];
|
||||
if(parser) {
|
||||
geometry = parser.apply(this, [nodeList[0]]);
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
} else {
|
||||
OpenLayers.Console.error("Unsupported geometry type: " +
|
||||
type);
|
||||
@@ -619,6 +623,11 @@ OpenLayers.Format.GML = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
* APIMethod: buildGeometryNode
|
||||
*/
|
||||
buildGeometryNode: function(geometry) {
|
||||
if (this.externalProjection && this.internalProjection) {
|
||||
geometry = geometry.clone();
|
||||
geometry.transform(this.internalProjection,
|
||||
this.externalProjection);
|
||||
}
|
||||
var className = geometry.CLASS_NAME;
|
||||
var type = className.substring(className.lastIndexOf(".") + 1);
|
||||
var builder = this.buildGeometry[type.toLowerCase()];
|
||||
|
||||
@@ -231,6 +231,10 @@ OpenLayers.Format.GeoJSON = OpenLayers.Class(OpenLayers.Format.JSON, {
|
||||
throw err;
|
||||
}
|
||||
}
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
return geometry;
|
||||
},
|
||||
|
||||
@@ -526,6 +530,11 @@ OpenLayers.Format.GeoJSON = OpenLayers.Class(OpenLayers.Format.JSON, {
|
||||
* {Object} An object representing the geometry.
|
||||
*/
|
||||
'geometry': function(geometry) {
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry = geometry.clone();
|
||||
geometry.transform(this.internalProjection,
|
||||
this.externalProjection);
|
||||
}
|
||||
var geometryType = geometry.CLASS_NAME.split('.')[2];
|
||||
var data = this.extract[geometryType.toLowerCase()].apply(this, [geometry]);
|
||||
var json;
|
||||
|
||||
@@ -152,6 +152,12 @@ OpenLayers.Format.GeoRSS = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
var feature = this.gmlParser.parseFeature(where[0]);
|
||||
geometry = feature.geometry;
|
||||
}
|
||||
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
|
||||
return geometry;
|
||||
},
|
||||
|
||||
@@ -324,6 +330,11 @@ OpenLayers.Format.GeoRSS = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
* {DOMElement} A gml node.
|
||||
*/
|
||||
buildGeometryNode: function(geometry) {
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry = geometry.clone();
|
||||
geometry.transform(this.internalProjection,
|
||||
this.externalProjection);
|
||||
}
|
||||
var node;
|
||||
// match Polygon
|
||||
if (geometry.CLASS_NAME == "OpenLayers.Geometry.Polygon") {
|
||||
|
||||
@@ -132,6 +132,10 @@ OpenLayers.Format.KML = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
var parser = this.parseGeometry[type.toLowerCase()];
|
||||
if(parser) {
|
||||
geometry = parser.apply(this, [nodeList[0]]);
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
} else {
|
||||
OpenLayers.Console.error("Unsupported geometry type: " +
|
||||
type);
|
||||
@@ -450,6 +454,11 @@ OpenLayers.Format.KML = OpenLayers.Class(OpenLayers.Format.XML, {
|
||||
* {DOMElement}
|
||||
*/
|
||||
buildGeometryNode: function(geometry) {
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry = geometry.clone();
|
||||
geometry.transform(this.internalProjection,
|
||||
this.externalProjection);
|
||||
}
|
||||
var className = geometry.CLASS_NAME;
|
||||
var type = className.substring(className.lastIndexOf(".") + 1);
|
||||
var builder = this.buildGeometry[type.toLowerCase()];
|
||||
|
||||
@@ -94,6 +94,10 @@ OpenLayers.Format.Text = OpenLayers.Class(OpenLayers.Format, {
|
||||
}
|
||||
}
|
||||
if (set) {
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
var feature = new OpenLayers.Feature.Vector(geometry, attributes, style);
|
||||
features.push(feature);
|
||||
}
|
||||
|
||||
@@ -60,6 +60,19 @@ OpenLayers.Format.WKT = OpenLayers.Class(OpenLayers.Format, {
|
||||
if(this.parse[type]) {
|
||||
features = this.parse[type].apply(this, [str]);
|
||||
}
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
if (features &&
|
||||
features.CLASS_NAME == "OpenLayers.Feature.Vector") {
|
||||
features.geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
} else if (features && typeof features == "object") {
|
||||
for (var i = 0; i < features.length; i++) {
|
||||
var component = features[i];
|
||||
component.geometry.transform(this.externalProjection,
|
||||
this.internalProjection);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return features;
|
||||
},
|
||||
@@ -97,6 +110,11 @@ OpenLayers.Format.WKT = OpenLayers.Class(OpenLayers.Format, {
|
||||
if(!this.extract[type]) {
|
||||
return null;
|
||||
}
|
||||
if (this.internalProjection && this.externalProjection) {
|
||||
geometry = geometry.clone();
|
||||
geometry.transform(this.internalProjection,
|
||||
this.externalProjection);
|
||||
}
|
||||
data = this.extract[type].apply(this, [geometry]);
|
||||
pieces.push(type.toUpperCase() + '(' + data + ')');
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user