SLD: Onder de motorkap

SLD: Onder de motorkap

Vooraf

Welkom bij deze korte workshop. De titel is ‘Onder de motorkap’ omdat je tijdens deze workshop zelf SLD-documenten gaat aanpassen in een teksteditor.

Leerdoelen:

  • Oefenen met handmatig aanpassingen maken in een SLD-document.

  • Kennis maken met minder bekende mogelijkheden van SLD in Onemap.

De workshop bestaat uit een verzameling oefeningen die je in een interactieve pagina uitvoert. Bij elke oefening staat aan het begin een korte omschrijving, zodat je zelf de oefeningen kunt kiezen die je interessant lijken. Elke oefening heeft een (deels) voorbereide SLD, zodat je die niet vanaf nul hoeft op te bouwen.

Link naar interactieve workshoppagina: https://beta4.webgispublisher.nl/user/sld-workshop/index.html

Het is aan te raden om, als je die nog niet hebt, een teksteditor te installeren om makkelijker SLD’s in de oefeningen aan te kunnen passen. Bijvoorbeeld Notepad++.

Verder zijn onderstaande links waarschijnlijk handig als naslagwerk om de oefeningen te kunnen maken:

Link naar SLD-documentatie van GeoServer: https://docs.geoserver.org/main/en/user/styling/sld/index.html

Link naar Filter-documentatie van GeoServer: https://docs.geoserver.org/main/en/user/styling/sld/reference/filters.html

Onderstaande link is voor als je in detail wilt opzoeken wat er mogelijk is in SLD. Deze heb je waarschijnlijk niet nodig voor de workshop.

Link naar de OGC Symbology Encoding spec (PDF): https://portal.ogc.org/files/?artifact_id=16700

SLD in Onemap

De viewer van Onemap gebruikt de OpenLayers-library om de kaart weer te geven. Deze library heeft helaas geen ondersteuning voor SLD, dus die moesten we (lees: Nieuwland Geo) zelf maken. Omdat SLD styling in OpenLayers van algemeen nut is, hebben we hier een open source library van gemaakt: SLDReader.

In deze workshop zal vaker worden verwezen naar de documentatie en demopagina’s van deze library. Wat er op de SLDReader pagina staat beschreven werkt ook in Onemap, of anders op z’n laatst na de volgende Onemap release.

Disclaimer: de wat geavanceerdere voorbeelden in deze workshop werken alleen in de Onemap viewer en niet bij afdrukken naar PDF. Dat komt omdat de library die we gebruiken voor het maken van PDF’s voornamelijk compatibel is met SLD’s die in GeoServer werken.

Noot: de SLD-ondersteuning in de Onemap viewer werkt ook in de Onemap app, omdat die dezelfde SLDReader library gebruikt.

Link naar SLDReader README: https://github.com/NieuwlandGeo/SLDReader/blob/master/README.md

Link naar SLDReader demopagina: https://nieuwlandgeo.github.io/SLDReader/

SLD v1.0.0 en v1.1.0

Er zijn twee versies van de SLD-standaard in omloop. Deze workshop gaat van versie 1.0.0 uit, net als de hierboven gelinkte voorbeelden van GeoServer. Onemap leest beide versies en is erg vergevingsgezind. Het is in Onemap mogelijk om SLD-opties die alleen in 1.1.0 zitten ook in de 1.0.0 syntax te gebruiken. Pas hier wel een beetje mee op: dergelijke SLD’s zijn dan alleen in Onemap te gebruiken.

Oefening 1: puntsymbolen opmaken

Het doel van deze oefening is kennis maken met de interactieve SLD-workshoppagina en spelen met de ingebouwde puntsymbolen en de opmaak daarvan.

  • Kies de laag ‘Puntenlaag - Basisstyling’ in de interactieve workshoppagina.

  • Verander het symbool eens in iets anders door de WellKnownName aan te passen.

  • Maak de symbolen groter of kleiner door Size aan te passen.

  • Roteer de symbolen door een Rotation element toe te voegen naast het Size element.

  • Pas de dikte van de outline aan door een stroke-width CssParameter op de juiste plek toe te voegen.

  • Maak de vulling van de symbolen doorzichtig door een fill-opacity parameter op de juiste plek toe te voegen.

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Eenvoudig puntsymbool</Name> <FeatureTypeStyle> <Rule> <PointSymbolizer> <Graphic> <Mark> <WellKnownName>triangle</WellKnownName> <Fill> <CssParameter name="fill">#AAAAFFF</CssParameter> <CssParameter name="fill-opacity">0.5</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#000088</CssParameter> <CssParameter name="stroke-width">2</CssParameter> </Stroke> </Mark> <Size>24</Size> <Rotation>60</Rotation> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>

Oefening 2: expressions en dynamische waardes

In deze oefening leer je wat een expression is in SLD en hoe je deze kunt gebruiken om styling direct te koppelen aan attributen van een feature.

Een expressie is een element dat een waarde vertegenwoordigt. In een SLD heb je drie soorten expressions:

  • Een vaste waarde: <ogc:Literal>42</ogc:Literal>. Op veel plekken kan je ook de waarde zelf neerzetten in plaats van een Literal-element:

    • <!-- dit mag --> <Size><ogc:Literal>24</ogc:Literal></Size> <!-- maar dit is korter --> <Size>24</Size>
  • Een waarde die uit een feature wordt gelezen: <ogc:PropertyName>type</ogc:PropertyName> betekent: lees de waarde van ‘type’ attribuut van de feature uit en gebruik die.

  • Een Function. Dit element heeft een naam en een lijst met parameters. Elke parameter is zelf weer een expressie, dus kan een literal, propertyname of function zijn.

    • <ogc:Function name="strSubstring"> <ogc:PropertyName>datum</ogc:PropertyName> <!-- vaste waardes moeten altijd in een Literal worden verpakt --> <ogc:Literal>5</ogc:Literal> <ogc:Literal>7</ogc:Literal> </ogc:Function>

Klinkt lekker abstract, maar waar het op neerkomt is dat op veel plaatsen in een SLD waar een vaste waarde staat, in plaats daarvan ook een PropertyName of Function element mag staan. Als je bijvoorbeeld een dataset met punten met een windrichting in graden hebt, kan je symbolen mee laten roteren.

  • Kies de laag ‘Puntenlaag - Basisstyling’

  • Verander het Mark symbool in een plaatje waar je de richting goed kunt zien:

    • <ExternalGraphic> <OnlineResource xlink:type="simple" xlink:href="https://beta4.webgispublisher.nl/user/uploads/compass.png"/> <Format>image/png</Format> </ExternalGraphic>
  • Maak Sizegroter → 32.

  • Voeg een Rotation element toe naast Size en bekijk hoe het symbool draait als je de waarde verandert.

  • Gebruik nu de waarde van het attribuut angle als rotatie. Welk SLD-element moet je hiervoor gebruiken?

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Eenvoudig puntsymbool</Name> <FeatureTypeStyle> <Rule> <PointSymbolizer> <Graphic> <ExternalGraphic> <OnlineResource xlink:type="simple" xlink:href="https://beta4.webgispublisher.nl/user/uploads/compass.png"/> <Format>image/png</Format> </ExternalGraphic> <Size>32</Size> <Rotation> <ogc:PropertyName>angle</ogc:PropertyName> </Rotation> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>
  • Herlaad de workshoppagina opnieuw en kies weer voor ‘Puntenlaag - Basisstyling’.

  • Sommige punten hebben een kleurcode in het attribuut kleur staan. Wat je met deze informatie doet laat ik als huiswerk aan de lezer.

Oefening 3: gebruik van Functions in SLD

In dit vervolg op oefening 2 leer je welke speciale Functions beschikbaar zijn binnen een SLD in Onemap en hoe je deze kunt toepassen.

  • Kies de laag ‘Puntenlaag - meerdere types’.

  • Deze SLD bevat een rule die alleen punten met type 1, 2, of 42 toont met een Or-toren. Dit kan compacter door een in-functie te gebruiken.

  • Documentatie filterfuncties in Onemap SLD: https://github.com/nieuwlandgeo/sldreader?tab=readme-ov-file#functions-supported-by-sldreader

  • Nieuw filter:

    • <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="in"> <!-- bekijk de documentatie van de in-functie en vertaal de parameters van de in-functie naar expressies --> </ogc:Function> <ogc:Literal>true</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter>
<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Style</Name> <FeatureTypeStyle> <Rule> <Name>Type 1, 2 of 42</Name> <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="in"> <ogc:PropertyName>type</ogc:PropertyName> <ogc:Literal>1</ogc:Literal> <ogc:Literal>2</ogc:Literal> <ogc:Literal>42</ogc:Literal> </ogc:Function> <ogc:Literal>true</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter> <PointSymbolizer> <Graphic> <Mark> <WellKnownName>circle</WellKnownName> <Fill> <CssParameter name="fill">#FF0000</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#440000</CssParameter> </Stroke> </Mark> <Size>12</Size> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>
<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Styled layer</Name> <UserStyle> <Name>Eenvoudige puntstijl</Name> <FeatureTypeStyle> <Rule> <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="strSubstring"> <ogc:PropertyName>creationda</ogc:PropertyName> <ogc:Literal>5</ogc:Literal> <ogc:Literal>7</ogc:Literal> </ogc:Function> <ogc:Literal>10</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter> <PointSymbolizer> <Graphic> <Mark> <WellKnownName>circle</WellKnownName> <Fill> <CssParameter name="fill">#aaaaff</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#000088</CssParameter> </Stroke> </Mark> <Size>8</Size> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>

Oefening 4: lagen met gemengde geometrieën

In deze oefening leer je wat je moet doen als je kaartlaag een mix van punten, lijnen en vlakken heeft. Het is handig om vooraf oefening 3a of 3b te doen.

  • Kies de laag 'Gemengde geometrieën'

  • De bedoeling is dat punten rood zijn, lijnen groen, en vlakken geel met een bruine rand.

    • De vlakken hebben een groene rand?

    • Midden in de vlakken en lijnen staan ook rode punten?

  • Dit komt doordat de SLD specificatie het volgende voorschrijft:

    • PointSymbolizers worden op alle geometrieën toegepast. Bij lijnen en vlakken wordt een punt in het midden van de geometrie getekend.

    • LineSymbolizers worden ook op de rand van vlakken toegepast.

  • Repareer de SLD zodanig dat de PointSymbolizer alleen op punten wordt toegepast, de LineSymbolizer alleen op lijnen en de PolygonSymbolizer alleen op vlakken.

  • Voeg daarvoor bij elke rule een filter toe dat de dimensionfunction gebruikt zodat elke rule op de juiste geometrie wordt toegepast. Zie hier: https://github.com/NieuwlandGeo/SLDReader?tab=readme-ov-file#functions-supported-by-sldreader

  • Hint: het geometrieveld van deze laag heet geom.

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Gemengde geometrieën</Name> <FeatureTypeStyle> <Rule> <Name>Punten</Name> <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="dimension"> <ogc:PropertyName>geom</ogc:PropertyName> </ogc:Function> <ogc:Literal>0</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter> <PointSymbolizer> <Graphic> <Mark> <WellKnownName>circle</WellKnownName> <Fill> <CssParameter name="fill">#FF0000</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#440000</CssParameter> </Stroke> </Mark> <Size>10</Size> </Graphic> </PointSymbolizer> </Rule> <Rule> <Name>Lijnen</Name> <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="dimension"> <ogc:PropertyName>geom</ogc:PropertyName> </ogc:Function> <ogc:Literal>1</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter> <LineSymbolizer> <Stroke> <CssParameter name="stroke">#00AA00</CssParameter> <CssParameter name="stroke-width">3</CssParameter> </Stroke> </LineSymbolizer> </Rule> <Rule> <Name>Vlakken</Name> <ogc:Filter> <ogc:PropertyIsEqualTo> <ogc:Function name="dimension"> <ogc:PropertyName>geom</ogc:PropertyName> </ogc:Function> <ogc:Literal>2</ogc:Literal> </ogc:PropertyIsEqualTo> </ogc:Filter> <PolygonSymbolizer> <Fill> <CssParameter name="fill">#FFFF00</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#AA8800</CssParameter> <CssParameter name="stroke-width">2</CssParameter> </Stroke> </PolygonSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>

Oefening 5: samengestelde labels

In deze oefening leer je hoe je samengestelde labels kunt maken en hoe je labels over meerdere regels kunt verdelen.

Je ziet in de praktijk meestal alleen maar een <ogc:PropertyName> expressie staan in een label, maar het Label element in een TextSymbolizer staat samengestelde inhoud toe. Je kunt propertyname en literal-expressies door elkaar gebruiken (en Function expressions).

Alle expressies in een label worden los van elkaar getrimd van whitespace en daarna achter elkaar geplakt. Dit strippen van whitespace is noodzakelijk omdat je anders ook de whitespace van een netjes opgemaakte SLD meeneemt.

Voorbeeld:

<!-- een . geeft whitespace aan in dit voorbeeld! --> <TextSymbolizer>. ..<Label>. ....Titel:<ogc:PropertyName>title</ogc:PropertyName>!. ..</Label> </TextSymbolizer>

Bevat de volgende tekstfragmenten (whitespace als '.' weergegeven)

  • ……..Titel:

  • <ogc:PropertyName>title</ogc:PropertyName>

  • !…

Na strippen whitespace:

  • Titel:

  • <ogc:PropertyName>title</ogc:PropertyName>

  • !

Invullen property name (“hoi”) en plakken:

  • Titel:hoi!

  • Kies kaartlaag ‘Huisnummers - Gelabeld’.

  • Als je over de labels heen gaat, kun je zien dat sommige objecten ook een huisletter en een toevoeging hebben.

  • Pas het Label element aan zodat huisnummer en huisletter worden getoond.

    • Opmerking: als huisletter niet is ingevuld, wordt een lege string getoond in de viewer.

  • Breid het label nu uit zodat toevoeging ook wordt getoond, maar van de rest gescheiden met een streepje, bijvoorbeeld 15K-211.

    • Opmerking: zonder streepje wordt een huisnummer (2) met toevoeging (111) zonder huisletter als 2111 getoond. Niet handig.

  • Nu is het label volledig, maar toont altijd een streepje, ook bij huisnummers zonder toevoeging.

  • Los dit op door twee rules te maken.

    • Een rule die de labels met toevoeging toont, maar alleen voor features die een toevoeging hebben.

      • Gebruik hiervoor een <ogc:Filter> met een <ogc:PropertyIsNull> element dat naar het toevoeging-attribuut kijkt.

    • Een rule die alleen huisnummer en huisletter toont.

      • Gebruik hiervoor in plaats van een <ogc:Filter> een <ElseFilter/>element (zonder ogc:-prefix!). Een ElseFilter in een rule betekent dat de rule alleen wordt toegepast op features die door geen enkele andere rule worden gevangen.

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.1.0" xmlns:xlink="http://www.w3.org/1999/xlink" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.1.0/StyledLayerDescriptor.xsd" xmlns:se="http://www.opengis.net/se"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Gelabelde huisnummers</Name> <FeatureTypeStyle> <Rule> <ogc:Filter> <ogc:PropertyIsNull> <ogc:PropertyName>toevoeging</ogc:PropertyName> </ogc:PropertyIsNull> </ogc:Filter> <TextSymbolizer> <Label> <ogc:PropertyName>huisnummer</ogc:PropertyName> <ogc:PropertyName>huisletter</ogc:PropertyName> </Label> <Font> <CssParameter name="font-size">12</CssParameter> </Font> <Halo> <Radius>1.5</Radius> <Fill> <CssParameter name="fill">#FFFFFF</CssParameter> </Fill> </Halo> <Fill> <CssParameter name="fill">#000000</CssParameter> </Fill> </TextSymbolizer> </Rule> <Rule> <ElseFilter/> <TextSymbolizer> <Label> <ogc:PropertyName>huisnummer</ogc:PropertyName> <ogc:PropertyName>huisletter</ogc:PropertyName> - <ogc:PropertyName>toevoeging</ogc:PropertyName> </Label> <Font> <CssParameter name="font-size">12</CssParameter> </Font> <Halo> <Radius>1.5</Radius> <Fill> <CssParameter name="fill">#FFFFFF</CssParameter> </Fill> </Halo> <Fill> <CssParameter name="fill">#000000</CssParameter> </Fill> </TextSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>
  • Kies de kaartlaag ‘Waarnemingen’.

  • Probeer een label toe te voegen waar het veld naam en gedrag onder elkaar staan. Kopiëer de TextSymbolizer van de huisnummerlaag en pas die aan.

  • Waarom lukt dit niet zomaar? Zie de theorie vooraf.

Whitespace rondom fragmenten in een label wordt verwijderd voordat de fragmenten aan elkaar worden geplakt. Line breaks/newlines tellen ook als whitespace!

Het is mogelijk om een letterlijke line break op de nemen in een label die niet wordt opgegeten door de witruimteverwijderaar. Gebruik hiervoor een CDATA fragment in je tekst

<![CDATA[]]>

Alles wat je tussen <![CDATA[ en ]]> zet wordt zonder aanpassingen, dus inclusief whitespace en line breaks, overgenomen. Ook inclusief witruimte die je voor de opmaak hebt gebruikt. Die mag er dus niet zijn, ook al staat dat ‘een beetje slordig’ in het SLD-document.

  • Gebruik de informatie uit de sectie hierboven om een line break toe te voegen in het label.

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Styled layer</Name> <UserStyle> <Name>Eenvoudige puntstijl</Name> <FeatureTypeStyle> <Rule> <PointSymbolizer> <Graphic> <Mark> <WellKnownName>circle</WellKnownName> <Fill> <CssParameter name="fill">#aaaaff</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#000088</CssParameter> </Stroke> </Mark> <Size>8</Size> </Graphic> </PointSymbolizer> <TextSymbolizer> <Label> <ogc:PropertyName>naam</ogc:PropertyName><![CDATA[ ]]><ogc:PropertyName>gedrag</ogc:PropertyName> </Label> <Font> <CssParameter name="font-size">12</CssParameter> </Font> <Halo> <Radius>1.5</Radius> <Fill> <CssParameter name="fill">#FFFFFF</CssParameter> </Fill> </Halo> <Fill> <CssParameter name="fill">#000000</CssParameter> </Fill> </TextSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>

Oefening 6: units of measure

In deze oefening leer je hoe je symbolen kunt laten meeschalen als je inzoomt door meters in plaats van pixels te gebruiken voor afmetingen.

Alle afmetingen die je in een SLD opgeeft zijn standaard in pixels. Icoongrootte, lijnbreedte etc..

Het is ook mogelijk om afmetingen in ‘ground units’ op te geven. Dit doe je per symbolizer door een ‘units of measure (uom)’ attribuut in een Symbolizer toe te voegen. Hiermee kun je kiezen of de afmetingen in een symbolizer in metre, foot, of pixel worden opgegeven, waarbij pixel standaard is.

Gebruik van uom is officiëel alleen mogelijk in SLD v1.1.0, maar Onemap (en Geoserver) pakken het ook op in een SLD v1.0.0-document.

Documentatie Geoserver: https://docs.geoserver.org/main/en/user/styling/sld/extensions/uom.html

Noot: het gebruik van non-pixel uom is slechts een benadering van de echte afstand op de grond. Zie dit meer als hulpmiddel om bijvoorbeeld verkeersbordiconen mee te laten schalen en niet als een manier om de afmeting van putdeksels op straat exact weer te geven.

Noot: het is in Onemap alleen mogelijk om uom te gebruiken voor losse puntsymbolen of lijnbreedtes. Gebruik van uomin een GraphicStroke/GraphicFill is niet mogelijk.

  • Kies de laag ‘Puntenlaag - Basisstyling’.

  • Pas de SLD aan zodat de symboolgrootte in meters wordt uitgedrukt.

  • Zoom in en uit en zie hoe de symbolen nu even groot blijven ten opzichte van de ondergrond.

  • Maak de rand van het symbool breder door een stroke-width toe te voegen.

  • De rand schaalt ook mee. Door px toe te voegen druk je een getal altijd in pixels uit, ongeacht de uom die is ingesteld voor een symbolizer. Probeer dit uit.

    • Noot: px-overrides in SLD werken waarschijnlijk alleen in de Onemap viewer.

<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>Eenvoudig puntsymbool</Name> <FeatureTypeStyle> <Rule> <PointSymbolizer uom="http://www.opengeospatial.org/se/units/metre"> <Graphic> <Mark> <WellKnownName>circle</WellKnownName> <Fill> <CssParameter name="fill">#aaeeaa</CssParameter> </Fill> <Stroke> <CssParameter name="stroke">#006600</CssParameter> <CssParameter name="stroke-width">3px</CssParameter> </Stroke> </Mark> <Size>12</Size> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>

Oefening 7: ‘kapotte’ SVG-symbolen repareren

Het doel van de oefening is te leren hoe je niet werkende afbeeldingen kunt repareren bij het gebruik van een SVG-afbeelding als icoon.

  • Kies de laag ‘Puntenlaag - SVG symbol’.

  • Je ziet niets. Het is de bedoeling dat je gele driehoeken met uitroeptekens als symbool ziet. Wat is hier aan de hand?

  • Open de link in de ExternalGraphic in je browser. Die afbeelding werkt wel. Maar waarom niet in de SLD?

  • Rechtsklik op de afbeelding in de browser en kies ‘Paginabron bekijken’. Of druk op Ctrl+U.

  • Je ziet nu de broncode van de SVG. Het probleem is dat er geen widthen heightattributen in het svg-rootelement staan. Deze zijn nodig, want anders weet de browser niet wat de afmeting van de SVG is. Er staat een viewBox in de SVG, maar een widthen height zijn verplicht om de SVG als symbool te kunnen laden.

  • Bekijk nu eens de inhoud van deze afbeelding waarin wel width en height zijn toegevoegd: https://beta4.webgispublisher.nl/user/uploads/caution-fixed.svg

  • Pas de OnlineResource van de SLD aan naar deze url. Als het goed is verschijnen er nu wel afbeeldingen.

  • Maar wat te doen als je een SVG wilt gebruiken, maar deze niet zelf kunt aanpassen? Dan is het mogelijk om de SVG in z’n geheel als inline content in de SLD te plaatsen.

  • Vervang het OnlineResourceelement in de SLD door een InlineContent element:

    • <InlineContent encoding="xml"> plak svg hier en zorg ervoor dat de svg width en height heeft </InlineContent>
<?xml version="1.0" encoding="UTF-8"?> <StyledLayerDescriptor xmlns="http://www.opengis.net/sld" xmlns:ogc="http://www.opengis.net/ogc" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0.0" xsi:schemaLocation="http://www.opengis.net/sld http://schemas.opengis.net/sld/1.0.0/StyledLayerDescriptor.xsd"> <NamedLayer> <Name>Layer</Name> <UserStyle> <Name>SVG Symbol</Name> <FeatureTypeStyle> <Rule> <PointSymbolizer> <Graphic> <ExternalGraphic> <InlineContent encoding="xml"> <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" stroke="#000" width="100" height="100"> <path d="M8,80s-5,8,5,9l78,0s9,0,5-9l-40-71s-4-6-8,0z" stroke-width="2" fill="#fff" fill-rule="evenodd" /> <path d="M52,10 L10,85 L93,85z" stroke-width="2" stroke-linejoin="round" fill="#fc0" fill-rule="evenodd"/> <path d="M52,32l0,26" stroke-width="9" stroke-linecap="round" fill-rule="evenodd"/> <circle r="6" cx="52" cy="73"/> </svg> </InlineContent> <Format>image/svg+xml</Format> </ExternalGraphic> <Size>24</Size> </Graphic> </PointSymbolizer> </Rule> </FeatureTypeStyle> </UserStyle> </NamedLayer> </StyledLayerDescriptor>