add WMS 1.3 GetCapabilities parser, r=ahocevar (closes #2294)

git-svn-id: http://svn.openlayers.org/trunk/openlayers@9894 dc9f47b5-9b13-0410-9fdd-eb0c1a62fdaf
This commit is contained in:
bartvde
2009-12-16 10:24:12 +00:00
parent e9264d89eb
commit 31189f1e45
7 changed files with 1145 additions and 379 deletions

View File

@@ -257,9 +257,12 @@
"OpenLayers/Format/WMC/v1_0_0.js",
"OpenLayers/Format/WMC/v1_1_0.js",
"OpenLayers/Format/WMSCapabilities.js",
"OpenLayers/Format/WMSCapabilities/v1.js",
"OpenLayers/Format/WMSCapabilities/v1_1.js",
"OpenLayers/Format/WMSCapabilities/v1_1_0.js",
"OpenLayers/Format/WMSCapabilities/v1_1_1.js",
"OpenLayers/Format/WMSCapabilities/v1_3.js",
"OpenLayers/Format/WMSCapabilities/v1_3_0.js",
"OpenLayers/Format/WMSGetFeatureInfo.js",
"OpenLayers/Layer/WFS.js",
"OpenLayers/Control/GetFeature.js",

View File

@@ -0,0 +1,406 @@
/**
* @requires OpenLayers/Format/XML.js
*/
/**
* Class: OpenLayers.Format.WMSCapabilities.v1
* Abstract class not to be instantiated directly. Creates
* the common parts for both WMS 1.1.X and WMS 1.3.X.
*
* Inherits from:
* - <OpenLayers.Format.XML>
*/
OpenLayers.Format.WMSCapabilities.v1 = OpenLayers.Class(
OpenLayers.Format.XML, {
/**
* Property: namespaces
* {Object} Mapping of namespace aliases to namespace URIs.
*/
namespaces: {
wms: "http://www.opengis.net/wms",
xlink: "http://www.w3.org/1999/xlink",
xsi: "http://www.w3.org/2001/XMLSchema-instance"
},
/**
* Property: defaultPrefix
*/
defaultPrefix: "wms",
/**
* Constructor: OpenLayers.Format.WMSCapabilities.v1
* Create an instance of one of the subclasses.
*
* Parameters:
* options - {Object} An optional object whose properties will be set on
* this instance.
*/
initialize: function(options) {
OpenLayers.Format.XML.prototype.initialize.apply(this, [options]);
},
/**
* APIMethod: read
* Read capabilities data from a string, and return a list of layers.
*
* Parameters:
* data - {String} or {DOMElement} data to read/parse.
*
* Returns:
* {Array} List of named layers.
*/
read: function(data) {
if(typeof data == "string") {
data = OpenLayers.Format.XML.prototype.read.apply(this, [data]);
}
if(data && data.nodeType == 9) {
data = data.documentElement;
}
var capabilities = {};
this.readNode(data, capabilities);
// postprocess the layer list
this.postProcessLayers(capabilities);
return capabilities;
},
/**
* Method: postProcessLayers
* Post process the layers, so that the nested layer structure is converted
* to a flat layer list with only named layers.
*
* Parameters:
* capabilities - {Object} The object (structure) returned by the parser with
* all the info from the GetCapabilities response.
*/
postProcessLayers: function(capabilities) {
if (capabilities.capability) {
capabilities.capability.layers = [];
var layers = capabilities.capability.nestedLayers;
for (var i=0, len = layers.length; i<len; ++i) {
var layer = layers[i];
this.processLayer(capabilities.capability, layer);
}
}
},
/**
* Method: processLayer
* Recursive submethod of postProcessLayers. This function will among
* others deal with property inheritance.
*
* Parameters:
* capability - {Object} The capability part of the capabilities object
* layer - {Object} The layer that needs processing
* parentLayer - {Object} The parent layer of the respective layer
*/
processLayer: function(capability, layer, parentLayer) {
if (layer.formats === undefined) {
layer.formats = capability.request.getmap.formats;
}
// deal with property inheritance
if(parentLayer) {
// add style
layer.styles = layer.styles.concat(parentLayer.styles);
var attributes = ["queryable",
"cascaded",
"fixedWidth",
"fixedHeight",
"opaque",
"noSubsets",
"llbbox",
"minScale",
"maxScale",
"attribution"];
var complexAttr = ["srs",
"bbox",
"dimensions",
"authorityURLs"];
var key;
for (var j=0; j<attributes.length; j++) {
key = attributes[j];
if (key in parentLayer) {
// only take parent value if not present (null or undefined)
if (layer[key] == null) {
layer[key] = parentLayer[key];
}
// if attribute isn't present, and we haven't
// inherited anything from a parent layer
// set to default value
if (layer[key] == null) {
var intAttr = ["cascaded", "fixedWidth", "fixedHeight"];
var boolAttr = ["queryable", "opaque", "noSubsets"];
if (OpenLayers.Util.indexOf(intAttr, key) != -1) {
layer[key] = 0;
}
if (OpenLayers.Util.indexOf(boolAttr, key) != -1) {
layer[key] = false;
}
}
}
}
for (var j=0; j<complexAttr.length; j++) {
key = complexAttr[j];
layer[key] = OpenLayers.Util.extend(
layer[key], parentLayer[key]);
}
}
// process sublayers
for (var i=0, len=layer.nestedLayers.length; i<len; i++) {
var childLayer = layer.nestedLayers[i];
this.processLayer(capability, childLayer, layer);
}
if (layer.name) {
capability.layers.push(layer);
}
},
/**
* Property: readers
* Contains public functions, grouped by namespace prefix, that will
* be applied when a namespaced node is found matching the function
* name. The function will be applied in the scope of this parser
* with two arguments: the node being read and a context object passed
* from the parent.
*/
readers: {
"wms": {
"Service": function(node, obj) {
obj.service = {};
this.readChildNodes(node, obj.service);
},
"Name": function(node, obj) {
obj.name = this.getChildValue(node);
},
"Title": function(node, obj) {
obj.title = this.getChildValue(node);
},
"Abstract": function(node, obj) {
obj.abstract = this.getChildValue(node);
},
"BoundingBox": function(node, obj) {
var bbox = {};
bbox.bbox = [
parseFloat(node.getAttribute("minx")),
parseFloat(node.getAttribute("miny")),
parseFloat(node.getAttribute("maxx")),
parseFloat(node.getAttribute("maxy"))
];
var res = {
x: parseFloat(node.getAttribute("resx")),
y: parseFloat(node.getAttribute("resy"))
};
if (! (isNaN(res.x) && isNaN(res.y))) {
bbox.res = res;
}
// return the bbox so that descendant classes can set the
// CRS and SRS and add it to the obj
return bbox;
},
"OnlineResource": function(node, obj) {
obj.href = this.getAttributeNS(node, this.namespaces.xlink,
"href");
},
"ContactInformation": function(node, obj) {
obj.contactInformation = {};
this.readChildNodes(node, obj.contactInformation);
},
"ContactPersonPrimary": function(node, obj) {
obj.personPrimary = {};
this.readChildNodes(node, obj.personPrimary);
},
"ContactPerson": function(node, obj) {
obj.person = this.getChildValue(node);
},
"ContactOrganization": function(node, obj) {
obj.organization = this.getChildValue(node);
},
"ContactPosition": function(node, obj) {
obj.position = this.getChildValue(node);
},
"ContactAddress": function(node, obj) {
obj.contactAddress = {};
this.readChildNodes(node, obj.contactAddress);
},
"AddressType": function(node, obj) {
obj.type = this.getChildValue(node);
},
"Address": function(node, obj) {
obj.address = this.getChildValue(node);
},
"City": function(node, obj) {
obj.city = this.getChildValue(node);
},
"StateOrProvince": function(node, obj) {
obj.stateOrProvince = this.getChildValue(node);
},
"PostCode": function(node, obj) {
obj.postcode = this.getChildValue(node);
},
"Country": function(node, obj) {
obj.country = this.getChildValue(node);
},
"ContactVoiceTelephone": function(node, obj) {
obj.phone = this.getChildValue(node);
},
"ContactFacsimileTelephone": function(node, obj) {
obj.fax = this.getChildValue(node);
},
"ContactElectronicMailAddress": function(node, obj) {
obj.email = this.getChildValue(node);
},
"Fees": function(node, obj) {
var fees = this.getChildValue(node);
if (fees && fees.toLowerCase() != "none") {
obj.fees = fees;
}
},
"AccessConstraints": function(node, obj) {
var constraints = this.getChildValue(node);
if (constraints && constraints.toLowerCase() != "none") {
obj.accessConstraints = constraints;
}
},
"Capability": function(node, obj) {
obj.capability = {nestedLayers: []};
this.readChildNodes(node, obj.capability);
},
"Request": function(node, obj) {
obj.request = {};
this.readChildNodes(node, obj.request);
},
"GetCapabilities": function(node, obj) {
obj.getcapabilities = {formats: []};
this.readChildNodes(node, obj.getcapabilities);
},
"Format": function(node, obj) {
if (obj.formats instanceof Array) {
obj.formats.push(this.getChildValue(node));
} else {
obj.format = this.getChildValue(node);
}
},
"DCPType": function(node, obj) {
this.readChildNodes(node, obj);
},
"HTTP": function(node, obj) {
this.readChildNodes(node, obj);
},
"Get": function(node, obj) {
this.readChildNodes(node, obj);
},
"Post": function(node, obj) {
this.readChildNodes(node, obj);
},
"GetMap": function(node, obj) {
obj.getmap = {formats: []};
this.readChildNodes(node, obj.getmap);
},
"GetFeatureInfo": function(node, obj) {
obj.getfeatureinfo = {formats: []};
this.readChildNodes(node, obj.getfeatureinfo);
},
"Exception": function(node, obj) {
obj.exception = {formats: []};
this.readChildNodes(node, obj.exception);
},
"Layer": function(node, obj) {
var attrNode = node.getAttributeNode("queryable");
var queryable = (attrNode && attrNode.specified) ?
node.getAttribute("queryable") : null;
attrNode = node.getAttributeNode("cascaded");
var cascaded = (attrNode && attrNode.specified) ?
node.getAttribute("cascaded") : null;
attrNode = node.getAttributeNode("opaque");
var opaque = (attrNode && attrNode.specified) ?
node.getAttribute('opaque') : null;
var noSubsets = node.getAttribute('noSubsets');
var fixedWidth = node.getAttribute('fixedWidth');
var fixedHeight = node.getAttribute('fixedHeight');
var layer = {nestedLayers: [], styles: [], srs: {},
metadataURLs: [], bbox: {}, dimensions: {},
authorityURLs: {}, identifiers: {}, keywords: [],
queryable: (queryable && queryable !== "") ?
( queryable === "1" || queryable === "true" ) : null,
cascaded: (cascaded !== null) ? parseInt(cascaded) : null,
opaque: opaque ?
(opaque === "1" || opaque === "true" ) : null,
noSubsets: (noSubsets !== null) ?
( noSubsets === "1" || noSubsets === "true" ) : null,
fixedWidth: (fixedWidth != null) ?
parseInt(fixedWidth) : null,
fixedHeight: (fixedHeight != null) ?
parseInt(fixedHeight) : null
};
obj.nestedLayers.push(layer);
this.readChildNodes(node, layer);
},
"Attribution": function(node, obj) {
obj.attribution = {};
this.readChildNodes(node, obj.attribution);
},
"LogoURL": function(node, obj) {
obj.logo = {
width: node.getAttribute("width"),
height: node.getAttribute("height")
};
this.readChildNodes(node, obj.logo);
},
"Style": function(node, obj) {
var style = {};
obj.styles.push(style);
this.readChildNodes(node, style);
},
"LegendURL": function(node, obj) {
var legend = {
width: node.getAttribute("width"),
height: node.getAttribute("height")
};
obj.legend = legend;
this.readChildNodes(node, legend);
},
"MetadataURL": function(node, obj) {
var metadataURL = {type: node.getAttribute("type")};
obj.metadataURLs.push(metadataURL);
this.readChildNodes(node, metadataURL);
},
"DataURL": function(node, obj) {
obj.dataURL = {};
this.readChildNodes(node, obj.dataURL);
},
"FeatureListURL": function(node, obj) {
obj.featureListURL = {};
this.readChildNodes(node, obj.featureListURL);
},
"AuthorityURL": function(node, obj) {
var name = node.getAttribute("name");
var authority = {};
this.readChildNodes(node, authority);
obj.authorityURLs[name] = authority.href;
},
"Identifier": function(node, obj) {
var authority = node.getAttribute("authority");
obj.identifiers[authority] = this.getChildValue(node);
},
"KeywordList": function(node, obj) {
this.readChildNodes(node, obj);
},
"SRS": function(node, obj) {
obj.srs[this.getChildValue(node)] = true;
}
}
},
CLASS_NAME: "OpenLayers.Format.WMSCapabilities.v1"
});

View File

@@ -1,6 +1,5 @@
/**
* @requires OpenLayers/Format/WMSCapabilities.js
* @requires OpenLayers/Format/XML.js
* @requires OpenLayers/Format/WMSCapabilities/v1.js
*/
/**
@@ -8,161 +7,10 @@
* Abstract class not to be instantiated directly.
*
* Inherits from:
* - <OpenLayers.Format.XML>
* - <OpenLayers.Format.WMSCapabilities.v1>
*/
OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
OpenLayers.Format.XML, {
/**
* Property: namespaces
* {Object} Mapping of namespace aliases to namespace URIs.
*/
namespaces: {
wms: "http://www.opengis.net/wms",
xlink: "http://www.w3.org/1999/xlink",
xsi: "http://www.w3.org/2001/XMLSchema-instance"
},
/**
* Property: defaultPrefix
*/
defaultPrefix: "wms",
/**
* Constructor: OpenLayers.Format.WMSCapabilities.v1_1
* Create an instance of one of the subclasses.
*
* Parameters:
* options - {Object} An optional object whose properties will be set on
* this instance.
*/
initialize: function(options) {
OpenLayers.Format.XML.prototype.initialize.apply(this, [options]);
},
/**
* APIMethod: read
* Read capabilities data from a string, and return a list of layers.
*
* Parameters:
* data - {String} or {DOMElement} data to read/parse.
*
* Returns:
* {Array} List of named layers.
*/
read: function(data) {
if(typeof data == "string") {
data = OpenLayers.Format.XML.prototype.read.apply(this, [data]);
}
if(data && data.nodeType == 9) {
data = data.documentElement;
}
var capabilities = {};
this.readNode(data, capabilities);
// postprocess the layer list
this.postProcessLayers(capabilities);
return capabilities;
},
/**
* Method: postProcessLayers
* Post process the layers, so that the nested layer structure is converted
* to a flat layer list with only named layers.
*
* Parameters:
* capabilities - {Object} The object (structure) returned by the parser with
* all the info from the GetCapabilities response.
*/
postProcessLayers: function(capabilities) {
if (capabilities.capability) {
capabilities.capability.layers = [];
var layers = capabilities.capability.nestedLayers;
for (var i=0, len = layers.length; i<len; ++i) {
var layer = layers[i];
this.processLayer(capabilities.capability, layer);
}
}
},
/**
* Method: processLayer
* Recursive submethod of postProcessLayers. This function will among
* others deal with property inheritance.
*
* Parameters:
* capability - {Object} The capability part of the capabilities object
* layer - {Object} The layer that needs processing
* parentLayer - {Object} The parent layer of the respective layer
*/
processLayer: function(capability, layer, parentLayer) {
if (layer.formats === undefined) {
layer.formats = capability.request.getmap.formats;
}
// deal with property inheritance
if(parentLayer) {
// add style
layer.styles = layer.styles.concat(parentLayer.styles);
var attributes = ["queryable",
"cascaded",
"fixedWidth",
"fixedHeight",
"opaque",
"noSubsets",
"llbbox",
"minScale",
"maxScale",
"attribution"];
var complexAttr = ["srs",
"bbox",
"dimensions",
"authorityURLs"];
var key;
for (var j=0; j<attributes.length; j++) {
key = attributes[j];
if (key in parentLayer) {
// only take parent value if not present (null or undefined)
if (layer[key] == null) {
layer[key] = parentLayer[key];
}
// if attribute isn't present, and we haven't
// inherited anything from a parent layer
// set to default value
if (layer[key] == null) {
var intAttr = ["cascaded", "fixedWidth", "fixedHeight"];
var boolAttr = ["queryable", "opaque", "noSubsets"];
if (OpenLayers.Util.indexOf(intAttr, key) != -1) {
layer[key] = 0;
}
if (OpenLayers.Util.indexOf(boolAttr, key) != -1) {
layer[key] = false;
}
}
}
}
for (var j=0; j<complexAttr.length; j++) {
key = complexAttr[j];
layer[key] = OpenLayers.Util.extend(
layer[key], parentLayer[key]);
}
}
// process sublayers
for (var i=0, len=layer.nestedLayers.length; i<len; i++) {
var childLayer = layer.nestedLayers[i];
this.processLayer(capability, childLayer, layer);
}
if (layer.name) {
capability.layers.push(layer);
}
},
OpenLayers.Format.WMSCapabilities.v1, {
/**
* Property: readers
@@ -173,126 +21,15 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
* from the parent.
*/
readers: {
"wms": {
"wms": OpenLayers.Util.applyDefaults({
"WMT_MS_Capabilities": function(node, obj) {
this.readChildNodes(node, obj);
},
"Service": function(node, obj) {
obj.service = {};
this.readChildNodes(node, obj.service);
},
"Name": function(node, obj) {
obj.name = this.getChildValue(node);
},
"Title": function(node, obj) {
obj.title = this.getChildValue(node);
},
"Abstract": function(node, obj) {
obj.abstract = this.getChildValue(node);
},
"OnlineResource": function(node, obj) {
obj.href = this.getAttributeNS(node, this.namespaces.xlink,
"href");
},
"ContactInformation": function(node, obj) {
obj.contactInformation = {};
this.readChildNodes(node, obj.contactInformation);
},
"ContactPersonPrimary": function(node, obj) {
obj.personPrimary = {};
this.readChildNodes(node, obj.personPrimary);
},
"ContactPerson": function(node, obj) {
obj.person = this.getChildValue(node);
},
"ContactOrganization": function(node, obj) {
obj.organization = this.getChildValue(node);
},
"ContactPosition": function(node, obj) {
obj.position = this.getChildValue(node);
},
"ContactAddress": function(node, obj) {
obj.contactAddress = {};
this.readChildNodes(node, obj.contactAddress);
},
"AddressType": function(node, obj) {
obj.type = this.getChildValue(node);
},
"Address": function(node, obj) {
obj.address = this.getChildValue(node);
},
"City": function(node, obj) {
obj.city = this.getChildValue(node);
},
"StateOrProvince": function(node, obj) {
obj.stateOrProvince = this.getChildValue(node);
},
"PostCode": function(node, obj) {
obj.postcode = this.getChildValue(node);
},
"Country": function(node, obj) {
obj.country = this.getChildValue(node);
},
"ContactVoiceTelephone": function(node, obj) {
obj.phone = this.getChildValue(node);
},
"ContactFacsimileTelephone": function(node, obj) {
obj.fax = this.getChildValue(node);
},
"ContactElectronicMailAddress": function(node, obj) {
obj.email = this.getChildValue(node);
},
"Fees": function(node, obj) {
var fees = this.getChildValue(node);
if (fees && fees.toLowerCase() != "none") {
obj.fees = fees;
"Keyword": function(node, obj) {
if (obj.keywords) {
obj.keywords.push(this.getChildValue(node));
}
},
"AccessConstraints": function(node, obj) {
var constraints = this.getChildValue(node);
if (constraints && constraints.toLowerCase() != "none") {
obj.accessConstraints = constraints;
}
},
"Capability": function(node, obj) {
obj.capability = {nestedLayers: []};
this.readChildNodes(node, obj.capability);
},
"Request": function(node, obj) {
obj.request = {};
this.readChildNodes(node, obj.request);
},
"GetCapabilities": function(node, obj) {
obj.getcapabilities = {formats: []};
this.readChildNodes(node, obj.getcapabilities);
},
"Format": function(node, obj) {
if (obj.formats instanceof Array) {
obj.formats.push(this.getChildValue(node));
} else {
obj.format = this.getChildValue(node);
}
},
"DCPType": function(node, obj) {
this.readChildNodes(node, obj);
},
"HTTP": function(node, obj) {
this.readChildNodes(node, obj);
},
"Get": function(node, obj) {
this.readChildNodes(node, obj);
},
"Post": function(node, obj) {
this.readChildNodes(node, obj);
},
"GetMap": function(node, obj) {
obj.getmap = {formats: []};
this.readChildNodes(node, obj.getmap);
},
"GetFeatureInfo": function(node, obj) {
obj.getfeatureinfo = {formats: []};
this.readChildNodes(node, obj.getfeatureinfo);
},
"DescribeLayer": function(node, obj) {
obj.describelayer = {formats: []};
this.readChildNodes(node, obj.describelayer);
@@ -309,10 +46,6 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
obj.putstyles = {formats: []};
this.readChildNodes(node, obj.putstyles);
},
"Exception": function(node, obj) {
obj.exception = {formats: []};
this.readChildNodes(node, obj.exception);
},
"UserDefinedSymbolization": function(node, obj) {
var userSymbols = {
supportSLD: parseInt(node.getAttribute("SupportSLD")) == 1,
@@ -322,37 +55,6 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
};
obj.userSymbols = userSymbols;
},
"Layer": function(node, obj) {
var attrNode = node.getAttributeNode("queryable");
var queryable = (attrNode && attrNode.specified) ?
node.getAttribute("queryable") : null;
attrNode = node.getAttributeNode("cascaded");
var cascaded = (attrNode && attrNode.specified) ?
node.getAttribute("cascaded") : null;
attrNode = node.getAttributeNode("opaque");
var opaque = (attrNode && attrNode.specified) ?
node.getAttribute('opaque') : null;
var noSubsets = node.getAttribute('noSubsets');
var fixedWidth = node.getAttribute('fixedWidth');
var fixedHeight = node.getAttribute('fixedHeight');
var layer = {nestedLayers: [], styles: [], srs: {},
metadataURLs: [], bbox: {}, dimensions: {},
authorityURLs: {}, identifiers: {}, keywords: [],
queryable: (queryable && queryable !== "") ?
( queryable === "1" || queryable === "true" ) : null,
cascaded: (cascaded !== null) ? parseInt(cascaded) : null,
opaque: opaque ?
(opaque === "1" || opaque === "true" ) : null,
noSubsets: (noSubsets !== null) ?
( noSubsets === "1" || noSubsets === "true" ) : null,
fixedWidth: (fixedWidth != null) ?
parseInt(fixedWidth) : null,
fixedHeight: (fixedHeight != null) ?
parseInt(fixedHeight) : null
};
obj.nestedLayers.push(layer);
this.readChildNodes(node, layer);
},
"LatLonBoundingBox": function(node, obj) {
obj.llbbox = [
parseFloat(node.getAttribute("minx")),
@@ -362,51 +64,10 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
];
},
"BoundingBox": function(node, obj) {
var bbox = {};
var bbox = OpenLayers.Format.WMSCapabilities.v1.prototype.readers["wms"].BoundingBox.apply(this, [node, obj]);
bbox.srs = node.getAttribute("SRS");
bbox.bbox = [
parseFloat(node.getAttribute("minx")),
parseFloat(node.getAttribute("miny")),
parseFloat(node.getAttribute("maxx")),
parseFloat(node.getAttribute("maxy"))
];
var res = {
x: parseFloat(node.getAttribute("resx")),
y: parseFloat(node.getAttribute("resy"))
};
if (! (isNaN(res.x) && isNaN(res.y))) {
bbox.res = res;
}
obj.bbox[bbox.srs] = bbox;
},
"Attribution": function(node, obj) {
obj.attribution = {};
this.readChildNodes(node, obj.attribution);
},
"LogoURL": function(node, obj) {
obj.logo = {
width: node.getAttribute("width"),
height: node.getAttribute("height")
};
this.readChildNodes(node, obj.logo);
},
"Style": function(node, obj) {
var style = {};
obj.styles.push(style);
this.readChildNodes(node, style);
},
"LegendURL": function(node, obj) {
var legend = {
width: node.getAttribute("width"),
height: node.getAttribute("height")
};
obj.legend = legend;
this.readChildNodes(node, legend);
},
"SRS": function(node, obj) {
obj.srs[this.getChildValue(node)] = true;
},
"ScaleHint": function(node, obj) {
var min = node.getAttribute("min");
var max = node.getAttribute("max");
@@ -421,11 +82,6 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
OpenLayers.DOTS_PER_INCH).toPrecision(13)
);
},
"MetadataURL": function(node, obj) {
var metadataURL = {type: node.getAttribute("type")};
obj.metadataURLs.push(metadataURL);
this.readChildNodes(node, metadataURL);
},
"Dimension": function(node, obj) {
var name = node.getAttribute("name").toLowerCase();
var dim = {
@@ -448,34 +104,8 @@ OpenLayers.Format.WMSCapabilities.v1_1 = OpenLayers.Class(
var values = this.getChildValue(node);
extent.values = values.split(",");
}
},
"DataURL": function(node, obj) {
obj.dataURL = {};
this.readChildNodes(node, obj.dataURL);
},
"FeatureListURL": function(node, obj) {
obj.featureListURL = {};
this.readChildNodes(node, obj.featureListURL);
},
"AuthorityURL": function(node, obj) {
var name = node.getAttribute("name");
var authority = {};
this.readChildNodes(node, authority);
obj.authorityURLs[name] = authority.href;
},
"Identifier": function(node, obj) {
var authority = node.getAttribute("authority");
obj.identifiers[authority] = this.getChildValue(node);
},
"KeywordList": function(node, obj) {
this.readChildNodes(node, obj);
},
"Keyword": function(node, obj) {
if (obj.keywords) {
obj.keywords.push(this.getChildValue(node));
}
}
}
}, OpenLayers.Format.WMSCapabilities.v1.prototype.readers["wms"])
},
CLASS_NAME: "OpenLayers.Format.WMSCapabilities.v1_1"

View File

@@ -0,0 +1,123 @@
/**
* @requires OpenLayers/Format/WMSCapabilities/v1.js
*/
/**
* Class: OpenLayers.Format.WMSCapabilities/v1_3
* Abstract base class for WMS Capabilities version 1.3.X.
* SLD 1.1.0 adds in the extra operations DescribeLayer and GetLegendGraphic,
* see: http://schemas.opengis.net/sld/1.1.0/sld_capabilities.xsd
*
* Inherits from:
* - <OpenLayers.Format.WMSCapabilities.v1>
*/
OpenLayers.Format.WMSCapabilities.v1_3 = OpenLayers.Class(
OpenLayers.Format.WMSCapabilities.v1, {
/**
* Property: readers
* Contains public functions, grouped by namespace prefix, that will
* be applied when a namespaced node is found matching the function
* name. The function will be applied in the scope of this parser
* with two arguments: the node being read and a context object passed
* from the parent.
*/
readers: {
"wms": OpenLayers.Util.applyDefaults({
"WMS_Capabilities": function(node, obj) {
this.readChildNodes(node, obj);
},
"LayerLimit": function(node, obj) {
obj.layerLimit = parseInt(this.getChildValue(node));
},
"MaxWidth": function(node, obj) {
obj.maxWidth = parseInt(this.getChildValue(node));
},
"MaxHeight": function(node, obj) {
obj.maxHeight = parseInt(this.getChildValue(node));
},
"BoundingBox": function(node, obj) {
var bbox = OpenLayers.Format.WMSCapabilities.v1.prototype.readers["wms"].BoundingBox.apply(this, [node, obj]);
bbox.srs = node.getAttribute("CRS");
obj.bbox[bbox.srs] = bbox;
},
"CRS": function(node, obj) {
// CRS is the synonym of SRS
this.readers.wms.SRS.apply(this, [node, obj]);
},
"EX_GeographicBoundingBox": function(node, obj) {
// replacement of LatLonBoundingBox
obj.llbbox = [];
this.readChildNodes(node, obj.llbbox);
},
"westBoundLongitude": function(node, obj) {
obj[0] = this.getChildValue(node);
},
"eastBoundLongitude": function(node, obj) {
obj[2] = this.getChildValue(node);
},
"southBoundLatitude": function(node, obj) {
obj[1] = this.getChildValue(node);
},
"northBoundLatitude": function(node, obj) {
obj[3] = this.getChildValue(node);
},
"MinScaleDenominator": function(node, obj) {
obj.maxScale = parseFloat(this.getChildValue(node)).toPrecision(16);
},
"MaxScaleDenominator": function(node, obj) {
obj.minScale = parseFloat(this.getChildValue(node)).toPrecision(16);
},
"Dimension": function(node, obj) {
// dimension has extra attributes: default, multipleValues,
// nearestValue, current which used to be part of Extent. It now
// also contains the values.
var name = node.getAttribute("name").toLowerCase();
var dim = {
name: name,
units: node.getAttribute("units"),
unitsymbol: node.getAttribute("unitSymbol"),
nearestVal: node.getAttribute("nearestValue") === "1",
multipleVal: node.getAttribute("multipleValues") === "1",
"default": node.getAttribute("default") || "",
current: node.getAttribute("current") === "1",
values: this.getChildValue(node).split(",")
};
// Theoretically there can be more dimensions with the same
// name, but with a different unit. Until we meet such a case,
// let's just keep the same structure as the WMS 1.1
// GetCapabilities parser uses. We will store the last
// one encountered.
obj.dimensions[dim.name] = dim;
},
"Keyword": function(node, obj) {
// TODO: should we change the structure of keyword in v1.js?
// Make it an object with a value instead of a string?
var keyword = {value: this.getChildValue(node),
vocabulary: node.getAttribute("vocabulary")};
if (obj.keywords) {
obj.keywords.push(keyword);
}
}
}, OpenLayers.Format.WMSCapabilities.v1.prototype.readers["wms"]),
"sld": {
"UserDefinedSymbolization": function(node, obj) {
this.readers.wms.UserDefinedSymbolization.apply(this, [node, obj]);
// add the two extra attributes
obj.userSymbols.inlineFeature = parseInt(node.getAttribute("InlineFeature")) == 1;
obj.userSymbols.remoteWCS = parseInt(node.getAttribute("RemoteWCS")) == 1;
},
"DescribeLayer": function(node, obj) {
this.readers.wms.DescribeLayer.apply(this, [node, obj]);
},
"GetLegendGraphic": function(node, obj) {
this.readers.wms.GetLegendGraphic.apply(this, [node, obj]);
}
}
},
CLASS_NAME: "OpenLayers.Format.WMSCapabilities.v1_3"
});

View File

@@ -0,0 +1,25 @@
/**
* @requires OpenLayers/Format/WMSCapabilities/v1_3.js
*/
/**
* Class: OpenLayers.Format.WMSCapabilities/v1_3_0
* Read WMS Capabilities version 1.3.0.
* SLD 1.1.0 adds in the extra operations DescribeLayer and GetLegendGraphic,
* see: http://schemas.opengis.net/sld/1.1.0/sld_capabilities.xsd
*
* Inherits from:
* - <OpenLayers.Format.WMSCapabilities.v1_3>
*/
OpenLayers.Format.WMSCapabilities.v1_3_0 = OpenLayers.Class(
OpenLayers.Format.WMSCapabilities.v1_3, {
/**
* Property: version
* {String} The specific parser version.
*/
version: "1.3.0",
CLASS_NAME: "OpenLayers.Format.WMSCapabilities.v1_3_0"
});

View File

@@ -0,0 +1,578 @@
<html>
<head>
<script src="../../../lib/OpenLayers.js"></script>
<script type="text/javascript">
function test_layers(t) {
t.plan(22);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var capability = obj.capability;
var layers = {};
for (var i=0, len=capability.layers.length; i<len; i++) {
if ("name" in capability.layers[i]) {
layers[ capability.layers[i].name ] = capability.layers[i];
}
}
var rootlayer = capability.layers[ capability.layers.length - 1];
t.eq(rootlayer.srs,
{"CRS:84": true},
"SRS parsed correctly for root layer");
t.eq(layers["ROADS_RIVERS"].srs,
{"CRS:84": true, "EPSG:26986": true},
"Inheritance of SRS handled correctly when adding SRSes");
t.eq(layers["Temperature"].srs,
{"CRS:84": true},
"Inheritance of SRS handled correctly when redeclaring an inherited SRS");
var bbox = layers["ROADS_RIVERS"].bbox["EPSG:26986"];
t.eq(bbox.bbox,
[189000, 834000, 285000, 962000],
"Correct bbox from BoundingBox");
t.eq(bbox.res, {x: 1, y: 1}, "Correct resolution");
bbox = layers["ROADS_1M"].bbox["EPSG:26986"];
t.eq(bbox.bbox,
[189000, 834000, 285000, 962000],
"Correctly inherited bbox");
t.eq(bbox.res, {x: 1, y: 1}, "Correctly inherited resolution");
var identifiers = layers["ROADS_RIVERS"].identifiers;
var authorities = layers["ROADS_RIVERS"].authorityURLs;
t.ok(identifiers, "got identifiers from layer ROADS_RIVERS");
t.ok("DIF_ID" in identifiers,
"authority attribute from Identifiers parsed correctly");
t.eq(identifiers["DIF_ID"],
"123456",
"Identifier value parsed correctly");
t.ok("DIF_ID" in authorities,
"AuthorityURLs parsed and inherited correctly");
t.eq(authorities["DIF_ID"],
"http://gcmd.gsfc.nasa.gov/difguide/whatisadif.html",
"OnlineResource in AuthorityURLs parsed correctly");
var featurelist = layers["ROADS_RIVERS"].featureListURL;
t.ok(featurelist, "layer has FeatureListURL");
t.eq(featurelist.format,
"XML",
"FeatureListURL format parsed correctly");
t.eq(featurelist.href,
"http://www.university.edu/data/roads_rivers.gml",
"FeatureListURL OnlineResource parsed correctly");
t.eq(layers["Pressure"].queryable,
true,
"queryable property inherited correctly");
t.eq(layers["ozone_image"].queryable,
false,
"queryable property has correct default value");
t.eq(layers["population"].cascaded,
1,
"cascaded property parsed correctly");
t.eq(layers["ozone_image"].fixedWidth,
512,
"fixedWidth property correctly parsed");
t.eq(layers["ozone_image"].fixedHeight,
256,
"fixedHeight property correctly parsed");
t.eq(layers["ozone_image"].opaque,
true,
"opaque property parsed correctly");
t.eq(layers["ozone_image"].noSubsets,
true,
"noSubsets property parsed correctly");
}
function test_dimensions(t) {
t.plan(8);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var capability = obj.capability;
var layers = {};
for (var i=0, len=capability.layers.length; i<len; i++) {
if ("name" in capability.layers[i]) {
layers[ capability.layers[i].name ] = capability.layers[i];
}
}
var time = layers["Clouds"].dimensions.time;
t.eq(time["default"], "2000-08-22", "Default time value parsed correctly");
t.eq(time.values.length, 1, "Currect number of time extent values/periods");
t.eq(time.values[0], "1999-01-01/2000-08-22/P1D", "Time extent values parsed correctly");
var elevation = layers["Pressure"].dimensions.elevation;
t.eq(elevation.units, "CRS:88", "Dimension units parsed correctly");
t.eq(elevation["default"], "0", "Default elevation value parsed correctly");
t.eq(elevation.nearestVal, true, "NearestValue parsed correctly");
t.eq(elevation.multipleVal, false, "Absense of MultipleValues handled correctly");
t.eq(elevation.values,
["0","1000","3000","5000","10000"],
"Parsing of comma-separated values done correctly");
}
function test_contactinfo(t) {
t.plan(14);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var service = obj.service;
var contactinfo = service.contactInformation;
t.ok(contactinfo, "object contains contactInformation property");
var personPrimary = contactinfo.personPrimary;
t.ok(personPrimary, "object contains personPrimary property");
t.eq(personPrimary.person, "Jeff Smith", "ContactPerson parsed correctly");
t.eq(personPrimary.organization, "NASA", "ContactOrganization parsed correctly");
t.eq(contactinfo.position,
"Computer Scientist",
"ContactPosition parsed correctly");
var addr = contactinfo.contactAddress;
t.ok(addr, "object contains contactAddress property");
t.eq(addr.type, "postal", "AddressType parsed correctly");
t.eq(addr.address,
"NASA Goddard Space Flight Center",
"Address parsed correctly");
t.eq(addr.city, "Greenbelt", "City parsed correctly");
t.eq(addr.stateOrProvince, "MD", "StateOrProvince parsed correctly");
t.eq(addr.postcode, "20771", "PostCode parsed correctly");
t.eq(addr.country, "USA", "Country parsed correctly");
t.eq(contactinfo.phone,
"+1 301 555-1212",
"ContactVoiceTelephone parsed correctly");
t.eq(contactinfo.email,
"user@host.com",
"ContactElectronicMailAddress parsed correctly");
}
function test_feesAndConstraints(t) {
t.plan(2);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var service = obj.service;
t.ok(! ("fees" in service), "Fees=none handled correctly");
t.ok(! ("accessConstraints" in service), "AccessConstraints=none handled correctly");
}
function test_requests(t) {
t.plan(6);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var request = obj.capability.request;
t.ok(request, "request property exists");
t.ok("getmap" in request, "got GetMap request");
t.ok("getfeatureinfo" in request, "got GetFeatureInfo request");
t.eq(request.getfeatureinfo.formats,
["text/xml", "text/plain", "text/html"],
"GetFeatureInfo formats correctly parsed");
var exception = obj.capability.exception;
t.ok(exception, "exception property exists");
t.eq(exception.formats,
["XML", "INIMAGE", "BLANK"],
"Exception Format parsed");
}
function test_ogc(t) {
t.plan(14);
/*
* Set up
*/
// needed for the minScale/maxScale test, see below
var dpi = OpenLayers.DOTS_PER_INCH;
OpenLayers.DOTS_PER_INCH = 90.71;
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
var capability = obj.capability;
/*
* Test
*/
var attribution = capability.layers[2].attribution;
t.eq(attribution.title, "State College University", "attribution title parsed correctly.");
t.eq(attribution.href, "http://www.university.edu/", "attribution href parsed correctly.")
t.eq(attribution.logo.href, "http://www.university.edu/icons/logo.gif", "attribution logo url parsed correctly.");
t.eq(attribution.logo.format, "image/gif", "attribution logo format parsed correctly.");
t.eq(attribution.logo.width, "100", "attribution logo width parsed correctly.");
t.eq(attribution.logo.height, "100", "attribution logo height parsed correctly.");
var keywords = capability.layers[0].keywords;
t.eq(keywords.length, 3, "layer has 3 keywords.");
t.eq(keywords[0].value, "road", "1st keyword parsed correctly.");
var metadataURLs = capability.layers[0].metadataURLs;
t.eq(metadataURLs.length, 2, "layer has 2 metadata urls.");
t.eq(metadataURLs[0].type, "FGDC:1998", "type parsed correctly.");
t.eq(metadataURLs[0].format, "text/plain", "format parsed correctly.");
t.eq(metadataURLs[0].href, "http://www.university.edu/metadata/roads.txt", "href parsed correctly.");
/*
Test minScale and maxScale
*/
var minScale = 250000;
var maxScale = 1000;
t.eq(capability.layers[0].minScale, minScale.toPrecision(16), "layer.minScale is correct");
t.eq(capability.layers[0].maxScale, maxScale.toPrecision(16), "layer.maxScale is correct");
/*
* Tear down
*/
OpenLayers.DOTS_PER_INCH = dpi;
}
function test_WMS13specials(t) {
t.plan(3);
var xml = document.getElementById("ogcsample").firstChild.nodeValue;
var doc = new OpenLayers.Format.XML().read(xml);
var obj = new OpenLayers.Format.WMSCapabilities().read(doc);
t.eq(obj.service.layerLimit, 16, "LayerLimit parsed correctly");
t.eq(obj.service.maxHeight, 2048, "MaxHeight parsed correctly");
t.eq(obj.service.maxWidth, 2048, "MaxWidth parsed correctly");
}
</script>
</head>
<body>
<!--
OGC example below taken from
http://schemas.opengis.net/wms/1.3.0/capabilities_1_3_0.xml
Changes:
-removed comments
-corrected typo in FeatureListURL Format XML with double quote
-added MinScaleDenominator and MaxScaleDenominator
-remove whitespace in Dimension tags
-->
<div id="ogcsample"><!--
<?xml version='1.0' encoding="UTF-8"?>
<WMS_Capabilities version="1.3.0" xmlns="http://www.opengis.net/wms"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.opengis.net/wms http://schemas.opengis.net/wms/1.3.0/capabilities_1_3_0.xsd">
<Service>
<Name>WMS</Name>
<Title>Acme Corp. Map Server</Title>
<Abstract>Map Server maintained by Acme Corporation. Contact: webmaster@wmt.acme.com. High-quality maps showing roadrunner nests and possible ambush locations.</Abstract>
<KeywordList>
<Keyword>bird</Keyword>
<Keyword>roadrunner</Keyword>
<Keyword>ambush</Keyword>
</KeywordList>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple"
xlink:href="http://hostname/" />
<ContactInformation>
<ContactPersonPrimary>
<ContactPerson>Jeff Smith</ContactPerson>
<ContactOrganization>NASA</ContactOrganization>
</ContactPersonPrimary>
<ContactPosition>Computer Scientist</ContactPosition>
<ContactAddress>
<AddressType>postal</AddressType>
<Address>NASA Goddard Space Flight Center</Address>
<City>Greenbelt</City>
<StateOrProvince>MD</StateOrProvince>
<PostCode>20771</PostCode>
<Country>USA</Country>
</ContactAddress>
<ContactVoiceTelephone>+1 301 555-1212</ContactVoiceTelephone>
<ContactElectronicMailAddress>user@host.com</ContactElectronicMailAddress>
</ContactInformation>
<Fees>none</Fees>
<AccessConstraints>none</AccessConstraints>
<LayerLimit>16</LayerLimit>
<MaxWidth>2048</MaxWidth>
<MaxHeight>2048</MaxHeight>
</Service>
<Capability>
<Request>
<GetCapabilities>
<Format>text/xml</Format>
<DCPType>
<HTTP>
<Get>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://hostname/path?" />
</Get>
<Post>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://hostname/path?" />
</Post>
</HTTP>
</DCPType>
</GetCapabilities>
<GetMap>
<Format>image/gif</Format>
<Format>image/png</Format>
<Format>image/jpeg</Format>
<DCPType>
<HTTP>
<Get>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://hostname/path?" />
</Get>
</HTTP>
</DCPType>
</GetMap>
<GetFeatureInfo>
<Format>text/xml</Format>
<Format>text/plain</Format>
<Format>text/html</Format>
<DCPType>
<HTTP>
<Get>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://hostname/path?" />
</Get>
</HTTP>
</DCPType>
</GetFeatureInfo>
</Request>
<Exception>
<Format>XML</Format>
<Format>INIMAGE</Format>
<Format>BLANK</Format>
</Exception>
<Layer>
<Title>Acme Corp. Map Server</Title>
<CRS>CRS:84</CRS>
<AuthorityURL name="DIF_ID">
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple"
xlink:href="http://gcmd.gsfc.nasa.gov/difguide/whatisadif.html" />
</AuthorityURL>
<Layer>
<Name>ROADS_RIVERS</Name>
<Title>Roads and Rivers</Title>
<CRS>EPSG:26986</CRS>
<EX_GeographicBoundingBox>
<westBoundLongitude>-71.63</westBoundLongitude>
<eastBoundLongitude>-70.78</eastBoundLongitude>
<southBoundLatitude>41.75</southBoundLatitude>
<northBoundLatitude>42.90</northBoundLatitude>
</EX_GeographicBoundingBox>
<BoundingBox CRS="CRS:84"
minx="-71.63" miny="41.75" maxx="-70.78" maxy="42.90" resx="0.01" resy="0.01"/>
<BoundingBox CRS="EPSG:26986"
minx="189000" miny="834000" maxx="285000" maxy="962000" resx="1" resy="1" />
<Attribution>
<Title>State College University</Title>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple"
xlink:href="http://www.university.edu/" />
<LogoURL width="100" height="100">
<Format>image/gif</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/icons/logo.gif" />
</LogoURL>
</Attribution>
<Identifier authority="DIF_ID">123456</Identifier>
<FeatureListURL>
<Format>XML</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple"
xlink:href="http://www.university.edu/data/roads_rivers.gml" />
</FeatureListURL>
<Style>
<Name>USGS</Name>
<Title>USGS Topo Map Style</Title>
<Abstract>Features are shown in a style like that used in USGS topographic maps.</Abstract>
<LegendURL width="72" height="72">
<Format>image/gif</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/legends/usgs.gif" />
</LegendURL>
<StyleSheetURL>
<Format>text/xsl</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/stylesheets/usgs.xsl" />
</StyleSheetURL>
</Style>
<MinScaleDenominator>1000</MinScaleDenominator>
<MaxScaleDenominator>250000</MaxScaleDenominator>
<Layer queryable="1">
<Name>ROADS_1M</Name>
<Title>Roads at 1:1M scale</Title>
<Abstract>Roads at a scale of 1 to 1 million.</Abstract>
<KeywordList>
<Keyword>road</Keyword>
<Keyword>transportation</Keyword>
<Keyword>atlas</Keyword>
</KeywordList>
<Identifier authority="DIF_ID">123456</Identifier>
<MetadataURL type="FGDC:1998">
<Format>text/plain</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/metadata/roads.txt" />
</MetadataURL>
<MetadataURL type="ISO19115:2003">
<Format>text/xml</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/metadata/roads.xml" />
</MetadataURL>
<Style>
<Name>ATLAS</Name>
<Title>Road atlas style</Title>
<Abstract>Roads are shown in a style like that used in a commercial road atlas.</Abstract>
<LegendURL width="72" height="72">
<Format>image/gif</Format>
<OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink"
xlink:type="simple"
xlink:href="http://www.university.edu/legends/atlas.gif" />
</LegendURL>
</Style>
</Layer>
<Layer queryable="1">
<Name>RIVERS_1M</Name>
<Title>Rivers at 1:1M scale</Title>
<Abstract>Rivers at a scale of 1 to 1 million.</Abstract>
<KeywordList>
<Keyword>river</Keyword>
<Keyword>canal</Keyword>
<Keyword>waterway</Keyword>
</KeywordList>
</Layer>
</Layer>
<Layer queryable="1">
<Title>Weather Forecast Data</Title>
<CRS>CRS:84</CRS>
<EX_GeographicBoundingBox>
<westBoundLongitude>-180</westBoundLongitude>
<eastBoundLongitude>180</eastBoundLongitude>
<southBoundLatitude>-90</southBoundLatitude>
<northBoundLatitude>90</northBoundLatitude>
</EX_GeographicBoundingBox>
<Dimension name="time" units="ISO8601" default="2000-08-22">1999-01-01/2000-08-22/P1D</Dimension>
<Layer>
<Name>Clouds</Name>
<Title>Forecast cloud cover</Title>
</Layer>
<Layer>
<Name>Temperature</Name>
<Title>Forecast temperature</Title>
</Layer>
<Layer>
<Name>Pressure</Name>
<Title>Forecast barometric pressure</Title>
<Dimension name="elevation" units="EPSG:5030" />
<Dimension name="time" units="ISO8601" default="2000-08-22">
1999-01-01/2000-08-22/P1D</Dimension>
<Dimension name="elevation" units="CRS:88" default="0" nearestValue="1">0,1000,3000,5000,10000</Dimension>
</Layer>
</Layer>
<Layer opaque="1" noSubsets="1" fixedWidth="512" fixedHeight="256">
<Name>ozone_image</Name>
<Title>Global ozone distribution (1992)</Title>
<EX_GeographicBoundingBox>
<westBoundLongitude>-180</westBoundLongitude>
<eastBoundLongitude>180</eastBoundLongitude>
<southBoundLatitude>-90</southBoundLatitude>
<northBoundLatitude>90</northBoundLatitude>
</EX_GeographicBoundingBox>
<Dimension name="time" units="ISO8601" default="1992">1992</Dimension>
</Layer>
<Layer cascaded="1">
<Name>population</Name>
<Title>World population, annual</Title>
<EX_GeographicBoundingBox>
<westBoundLongitude>-180</westBoundLongitude>
<eastBoundLongitude>180</eastBoundLongitude>
<southBoundLatitude>-90</southBoundLatitude>
<northBoundLatitude>90</northBoundLatitude>
</EX_GeographicBoundingBox>
<Dimension name="time" units="ISO8601" default="2000">1990/2000/P1Y</Dimension>
</Layer>
</Layer>
</Capability>
</WMS_Capabilities>
--></div>
</body>
</html>

View File

@@ -78,6 +78,7 @@
<li>Format/WMC/v1.html</li>
<li>Format/WMSCapabilities.html</li>
<li>Format/WMSCapabilities/v1_1_1.html</li>
<li>Format/WMSCapabilities/v1_3_0.html</li>
<li>Format/WMSDescribeLayer.html</li>
<li>Format/WMSGetFeatureInfo.html</li>
<li>Format/CSWGetDomain.html</li>