By definition, a WMS server returns static maps, rendered as images. Depending on the capabilities of the WMS server, a WMS client can customize the styling of the rendered maps.

Using named styles

The WMS specification defines the concept of named styles: a WMS server can define one or more styling options for a WMS layer. The WMS capabilities metadata identifies those styling options with a name, and a client can refer to them in requests.

Discovering the named styles

You can find the available named styles for a WMS layer in the WMS capabilities of the server. When you have discovered the available WMS layers, you can discover the named styles for a WMS layer as follows:

ALcdWMSNamedLayer layer = ...
System.out.println("Available WMS named styles for layer " + layer.getNamedLayerName());
for(int i = 0; i < layer.getNamedLayerStyleCount(); i++) {
  System.out.println(layer.getNamedLayerStyle(i).getStyleName());
}

Using a named style

To use a named style for a WMS layer, you can specify it on TLcdWMSDataSource:

String serverURL = "https://sampleservices.luciad.com/wms";
String wmsLayerName = "rivers";
String wmsLayerStyle = "default";
TLcdWMSDataSource dataSource = TLcdWMSDataSource.newBuilder()
                                                .uri(serverURL)
                                                .addLayer(wmsLayerName, wmsLayerStyle)
                                                .build();

Visualize WMS data on a GXY map and Visualize WMS data on a Lightspeed map explain how to visualize this data source on a map.

Using custom styles defined on the client

The idea of named styles allows WMS clients to choose the styling for a WMS layer, but they can’t customize the styling. To meet this need, the OGC defines the Styled Layer Descriptor (SLD) Profile of the WMS. It adds the possibility to include fine-grained styling options in requests, through an SLD. The SLD specifies the desired WMS layers and their styling, such as the icons, line styles, polygon fills and raster rendering settings. For more information about the styling options, see Styling data with OGC SLD.

Defining an SLD

To define the SLD, you can:

<?xml version='1.0' encoding='UTF-8'?>
<sld:StyledLayerDescriptor xmlns:sld="http://www.opengis.net/sld"
                           xmlns:se="http://www.opengis.net/se"
                           xmlns:ogc="http://www.opengis.net/ogc"
                           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                           xsi:schemaLocation="http://www.opengis.net/se http://schemas.opengis.net/se/1.1.0/FeatureStyle.xsd   http://www.opengis.net/ogc http://schemas.opengis.net/filter/1.1.0/filter.xsd http://www.opengis.net/sld http://schemas.opengis.net/sld/1.1.0/StyledLayerDescriptor.xsd"
                           version="1.1.0">
  <sld:NamedLayer>
    <se:Name>cities</se:Name>
    <sld:UserStyle>
      <se:Name>squares</se:Name>
      <se:FeatureTypeStyle version="1.1.0">
        <se:Rule>
          <se:MinScaleDenominator>0.0</se:MinScaleDenominator>
          <se:MaxScaleDenominator>INF</se:MaxScaleDenominator>
          <se:PointSymbolizer>
            <se:Graphic>
              <se:Mark>
                <se:WellKnownName>square</se:WellKnownName>
                <se:Fill>
                  <se:SvgParameter name="fill">#00FF00</se:SvgParameter>
                  <se:SvgParameter name="fill-opacity">
                    <ogc:Literal>1.0</ogc:Literal>
                  </se:SvgParameter>
                </se:Fill>
                <se:Stroke>
                  <se:SvgParameter name="stroke-width">
                    <ogc:Literal>1.0</ogc:Literal>
                  </se:SvgParameter>
                  <se:SvgParameter name="stroke">
                    <ogc:Literal>#FF0000</ogc:Literal>
                  </se:SvgParameter>
                  <se:SvgParameter name="stroke-opacity">
                    <ogc:Literal>1.0</ogc:Literal>
                  </se:SvgParameter>
                </se:Stroke>
              </se:Mark>
              <se:Size>8</se:Size>
            </se:Graphic>
          </se:PointSymbolizer>
        </se:Rule>
      </se:FeatureTypeStyle>
    </sld:UserStyle>
  </sld:NamedLayer>
</sld:StyledLayerDescriptor>

Including an SLD in WMS requests

When you have your SLD, you can use it in the WMS client in several ways.

Configuring the SLD on the WMS data source

You can specify an SLD on the WMS data source like you specify a named style. Note that with this approach, you must make the SLD content available as a String.

String serverURL = "https://sampleservices.luciad.com/wms";
String wmsLayerName = "rivers";
String wmsLayerStyle = "default";
TLcdWMSDataSource dataSource = TLcdWMSDataSource.newBuilder()
                                                .uri(serverURL)
                                                .styledLayerDescriptor("mySLdEncodedAsAString")
                                                .build();

You also have the option to include layer names and styles on TLcdWMSDataSource, next to an SLD. In that case, you are using the SLD as a style library: only the specified layer names and styles are used.

Configuring the SLD on the WMS proxy

An alternative is to first decode a WMS model for the WMS layers you want, and then set the SLD on the ALcdWMSProxy element inside the model. With this approach, you can set the SLD as an instance of the domain object TLcdSLDStyledLayerDescriptor:

TLcdSLDStyledLayerDescriptor styledLayerDescriptor = ...;
ALcdWMSProxy proxy = (ALcdWMSProxy) model.elements().nextElement();
proxy.setStyledLayerDescriptor(styledLayerDescriptor);

You can also set it as a URL pointing to the SLD:

URL styledLayerDescriptorUrl = ...;
ALcdWMSProxy proxy = (ALcdWMSProxy) model.elements().nextElement();
proxy.setStyledLayerDescriptorURL(styledLayerDescriptorUrl);

If you use a URL, make sure that the WMS server can also access it.