WMS GetMap request with SLD
- Want to add a touch of style to your map?
- Why not use SLD for changing the predefined styles of the WMS layers? Then read on
Contents
1. Introduction
The present description on GetMap requests with SLD will only highlight some small selection of possibilities. This should give an opportunity to grasp the idea of using style descriptions to influence the display of the resulting map when requesting it from the WMS server. It is not intended to replace a thorough study of the relevant OGC specifications (as given below). For further options not mentioned here, please work with the OGC documents directly or look at HowToSLD and HowToSE.
2. Relevant OGC Standards
There are several OGC specifications working together when requesting a map from a WMS with a (user)specific style.
Filter Encoding: http://www.opengeospatial.org/standards/filter
(only needed when filtering is necessary for what you want to accomplish)
The relevant versions when using deegree2 are: WMS 1.1.1/1.3.0, SLD 1.0.0, Filter Encoding 1.0.0.
3. HTTP Get Requests (KVP)
In a simplified explanation, a HTTP Get requests are what you type in the browsers address field, using a number of key-value pairs (KVP). An easy example is the WMS GetCapabilities request:
http://localhost:8080/deegree-wms/services?service=WMS&version=1.1.1&request=GetCapabilities
This request contains the service address:
http://localhost:8080/deegree-wms/services?
and 3 key value pairs:
service=WMS version=1.1.1 request=GetCapabilities
There are two different options for defining a WMS GetMap request with SLD. One makes use of the key SLD, the other uses the key SLD_BODY. Both ways are described below.
3.1. HTTP Get with SLD
A WMS GetMap request with the key "SLD" will expect a URL as value. This URL needs to contain a full SLD document. An example:
http://localhost:8080/deegree-wms/services?SERVICE=WMS&VERSION=1.1.1&REQUEST=GetMap&WIDTH=500&HEIGHT=500&TRANSPARENT=TRUE&FORMAT=image/png&BBOX=372233.9342431239,4460438,489069,4552689&SRS=EPSG:26912&SLD=http://localhost:8080/deegree-wms/named_layer_user_style.xml
This mode is very easy to read, as you only need to specify an URL, where your SLD document may be found. It is up to you whether you prefer to provide a web URL or a file URL. You just have to make sure that you can access the SLD under the specified address.
Next thing you need is the SLD document itself, which you will place at the above URL. One possible SLD example is given below:
<sld:StyledLayerDescriptor version="1.0.0" xmlns:sld="http://www.opengis.net/sld" xmlns:app="http://www.deegree.org/app" xmlns:gml="http://www.opengis.net/gml" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <!-- named layer --> <sld:NamedLayer> <!-- known WMS layer name --> <sld:Name>Railroads</sld:Name> <!-- optional section for filtering --> <sld:LayerFeatureConstraints> <sld:FeatureTypeConstraint> <sld:FeatureTypeName>app:Railroads</sld:FeatureTypeName> <!-- for different filter options refer to the filter specification --> <ogc:Filter> <ogc:PropertyIsLessThanOrEqualTo> <ogc:PropertyName>app:objectid</ogc:PropertyName> <ogc:Literal>842</ogc:Literal> </ogc:PropertyIsLessThanOrEqualTo> </ogc:Filter> </sld:FeatureTypeConstraint> </sld:LayerFeatureConstraints> <!-- define a user style for the layer --> <sld:UserStyle> <sld:FeatureTypeStyle> <sld:Rule> <sld:MinScaleDenominator>0</sld:MinScaleDenominator> <sld:MaxScaleDenominator>999999999</sld:MaxScaleDenominator> <sld:LineSymbolizer> <sld:Stroke> <sld:CssParameter name="stroke">#ff00ff</sld:CssParameter> <sld:CssParameter name="stroke-opacity">1.0</sld:CssParameter> <sld:CssParameter name="stroke-width">1.0</sld:CssParameter> <sld:CssParameter name="stroke-dasharray">1</sld:CssParameter> </sld:Stroke> </sld:LineSymbolizer> </sld:Rule> </sld:FeatureTypeStyle> </sld:UserStyle> </sld:NamedLayer> <!-- add more NamedLayer elements or UserLayer elements here, if needed --> </sld:StyledLayerDescriptor>
3.2. HTTP Get with SLD_BODY
If you want to send a GetMap request using the key SLD_BODY then you need an SLD document as the example above. Then you need to URL-encode this SLD (by using on of the many URL Decoder/Encoder in the internet). Then you can add this URL encoded SLD to the GetMap request and get something looking like this:
http://localhost:8080/deegree-wms/services?SERVICE=WMS&VERSION=1.1.1&REQUEST=GetMap&WIDTH=500&HEIGHT=500&TRANSPARENT=TRUE&FORMAT=image/png&BBOX=372233.9342431239,4460438,489069,4552689&SRS=EPSG:26912&SLD_BODY=%3Csld%3AStyledLayerDescriptor%20version%3D%221.0.0%22%20xmlns%3Asld%3D%22http%3A%2F%2Fwww.opengis.net%2Fsld%22%20xmlns%3Aapp%3D%22http%3A%2F%2Fwww.deegree.org%2Fapp%22%20xmlns%3Agml%3D%22http%3A%2F%2Fwww.opengis.net%2Fgml%22%20xmlns%3Aogc%3D%22http%3A%2F%2Fwww.opengis.net%2Fogc%22%20xmlns%3Axsi%3D%22http%3A%2F%2Fwww.w3.org%2F2001%2FXMLSchema-instance%22%20xsi%3AschemaLocation%3D%22http%3A%2F%2Fwww.opengis.net%2Fsld%20http%3A%2F%2Fschemas.opengis.net%2Fsld%2F1.0.0%2FStyledLayerDescriptor.xsd%22%3E%3C!--%20named%20layer%20--%3E%3Csld%3ANamedLayer%3E%3C!--%20known%20WMS%20layer%20name%20--%3E%3Csld%3AName%3ERailroads%3C%2Fsld%3AName%3E%3C!--%20optional%20section%20for%20filtering%20--%3E%3Csld%3ALayerFeatureConstraints%3E%3Csld%3AFeatureTypeConstraint%3E%3Csld%3AFeatureTypeName%3Eapp%3ARailroads%3C%2Fsld%3AFeatureTypeName%3E%3C!--%20for%20different%20filter%20options%20refer%20to%20the%20filter%20specification%20--%3E%3Cogc%3AFilter%3E%3Cogc%3APropertyIsLessThanOrEqualTo%3E%3Cogc%3APropertyName%3Eapp%3Aobjectid%3C%2Fogc%3APropertyName%3E%3Cogc%3ALiteral%3E842%3C%2Fogc%3ALiteral%3E%3C%2Fogc%3APropertyIsLessThanOrEqualTo%3E%3C%2Fogc%3AFilter%3E%3C%2Fsld%3AFeatureTypeConstraint%3E%3C%2Fsld%3ALayerFeatureConstraints%3E%3C!--%20define%20a%20user%20style%20for%20the%20layer%20--%3E%3Csld%3AUserStyle%3E%3Csld%3AFeatureTypeStyle%3E%3Csld%3ARule%3E%3Csld%3AMinScaleDenominator%3E0%3C%2Fsld%3AMinScaleDenominator%3E%3Csld%3AMaxScaleDenominator%3E999999999%3C%2Fsld%3AMaxScaleDenominator%3E%3Csld%3ALineSymbolizer%3E%3Csld%3AStroke%3E%3Csld%3ACssParameter%20name%3D%22stroke%22%3E%23ff00ff%3C%2Fsld%3ACssParameter%3E%3Csld%3ACssParameter%20name%3D%22stroke-opacity%22%3E1.0%3C%2Fsld%3ACssParameter%3E%3Csld%3ACssParameter%20name%3D%22stroke-width%22%3E1.0%3C%2Fsld%3ACssParameter%3E%3Csld%3ACssParameter%20name%3D%22stroke-dasharray%22%3E1%3C%2Fsld%3ACssParameter%3E%3C%2Fsld%3AStroke%3E%3C%2Fsld%3ALineSymbolizer%3E%3C%2Fsld%3ARule%3E%3C%2Fsld%3AFeatureTypeStyle%3E%3C%2Fsld%3AUserStyle%3E%3C%2Fsld%3ANamedLayer%3E%3C!--%20add%20more%20NamedLayer%20elements%20or%20UserLayer%20elements%20here%2C%20if%20needed%20--%3E%3C%2Fsld%3AStyledLayerDescriptor%3E
This is very hard to read, but it is exactly the same SLD as in the first example. The resulting map, of course, is also the same.
3.3. Comparison of SLD and SLD_BODY
One problem with SLD_BODY is that the request is getting very long. Some browsers have difficulties to send HTTP-Get requests that are longer than about 1000 characters. Since the URL encoding transforms each "<" to a "%3C" this is an increase in characters from 1 to 3. Just imagine to add a second or even third layer to the request. You would soon run into the browser-specific constraints on request lengths.
Another problem with SLD_BODY is the reduced readability and the extra step of URL-encoding the SLD. If you want to add or change something in the SLD, you need to first URL-decode the already encoded fragment, then apply your changes, and then again URL-encode the SLD.
Therefore it is recommendable to use the key SLD instead of SLD_BODY.
4. HTTP Post Requests
It is also an option to send HTTP Post requests to a WMS. This can for example be accomplished with the generic client of that is part of every deegree web sercvice installation. Point your browser to:
http://localhost:8080/deegree-wms/client/client.html
and you will be able to send WMS GetMap requests as HTTP Post requests.
5. Examples for HTTP Get with SLD 1.1.0
Here you can find some examples for SLDs in WMS GetMap request based on the utah demo.