Skip to content

Latest commit

 

History

History
179 lines (142 loc) · 5.27 KB

style.md

File metadata and controls

179 lines (142 loc) · 5.27 KB

Style

Most of this section is incomplete and shall have more content in future.

  • [Using ol.style.Style on ol.Feature](#Using ol.style.Style on ol.Feature)
  • Arrows
  • Arcs

Using ol.style.Style on ol.Feature

To style a single Feature, you shall call the .setStyle() method with a StyleLike. There are certain exceptions: when hiding or highlighting features. It is required to use the layers FeatureVisibility or the LayerCollections .globalHider to hide and highlight features. This ensures the features style remains correct, even though the feature is rendered differently. The reason this works, is because he @vcmap/core patches ol.Feature.prototype.getStyleFunction to ensure hidden features are hidden and highlighted features highlighted without changing the style on the feature.

import { LayerCollection, VectorLayer } from '@vcmap/core';
import { Feature } from 'ol';
import { LineString } from 'ol/geom';
import { Style, Stroke } from 'ol/style';

const collection = new LayerCollection();
const layer = new VectorLayer({});
collection.add(layer);

const features = [
  new Feature({
    geometry: new LineString([
      [0, 0],
      [1, 0],
    ]),
  }),
  new Feature({
    geometry: new LineString([
      [0, 0],
      [0, 1],
    ]),
  }),
];

const featureStyle = new Style({
  stroke: new Stroke({ color: '#000000', widht: 1 }),
});
features.forEach((f) => {
  f.setStyle(featureStyle);
});

const [id1, id2] = layer.addFeatures(features);
// the first feature is red
layer.featureVisibility.highlight({
  [id1]: new Style({ stroke: new Storke({ color: '#FF0000', width: 4 }) }),
});

// the second feature is hidden
collection.globalHider.hideObjects([id2]);

features.forEach((f) => {
  assert(f.getStyle() === featureStyle);
  assert(!f.getStyleFunction()().includes(featureStyle));
});

Arrows

You can create an ArrowStyle, which is a specialized ol.style.Style. It will render an arrow head at the end of a ol.geom.LineString. It will not render any other geometry. You can have arrow heads at the start, end or at both ends of your line by setting the end configuration using the ArrowEnd enum.

import { ArrowStyle, ArrowEnd, VectorLayer } from '@vcmap/core';

const style = new ArrowStyle({
  color: '#FF0000', // sets the color of the arrow head & the line
  end: ArrowEnd.BOTH, // have an arrow at both ends of the line
});

const layer = new VectorLayer({});
layer.setStyle(style);

To define the shape of the arrow head, you can provide your own definition of the Primitive to be rendered in 3D. The ol.style.Icon used in 2D can be deduced for primitives of type: SPHERE, BOX & CYLINDER. By default, the arrow head is a CYLINDER with a top radius of 0, resulting in a triangle representation in 2D. You could use a cube as follows:

import { ArrowStyle, PrimitiveOptionsType } from '@vcmap/core';

const style = new ArrowStyle({
  color: '#FF0000', // sets the color of the arrow head & the line
  primitiveOptions: {
    // sets a box, which will result in a square 2D representation
    type: PrimitiveOptionsType.BOX,
    geometryOptions: {
      minimum: [0, 0, 0],
      maximum: [6, 6, 9],
    },
    offset: [-3, -3, 0],
  },
});

You can also provide a custom 2D icon.

import { ArrowStyle } from '@vcmap/core';

// create a custom white svg icon
const radius = 10;
const icon = `<svg height="${radius * 2}" width="${
  radius * 2
}" xmlns="http://www.w3.org/2000/svg">
  <circle cx="${radius}" cy="${radius}" r="${radius}" style="fill:white;" />
</svg>`;

const style = new ArrowStyle({
  color: '#FF0000', // sets the color of the line
  arrowIcon: {
    src: `data:image/svg+xml,${encodeURIComponent(icon)}`,
    color: '#00FF00', // arrow head is now green
  },
});

Arcs

The ArcStyle is a special kind of ArrowStyle. It will render an arc from the first point to the last point of LineString geometries. If the geometries have 3D coordinates, the arcs will be 3D as well (otherwise they are drapped onto the terrain). Usage is the same as an arrow style:

import { ArcStyle, ArrowEnd, VectorLayer } from '@vcmap/core';

const style = new ArcStyle({
  color: '#FF0000', // sets the color of the arrow head & the line
  end: ArrowEnd.BOTH, // have an arrow at both ends of the line
});

const layer = new VectorLayer({});
layer.setStyle(style);

You can draw arcs without arrows too:

import { ArcStyle, ArrowEnd } from '@vcmap/core';

const style = new ArcStyle({
  end: ArrowEnd.NONE, // no arrow heads drawn
});

You can define the arcFactor, which states how extreme the arc is. An arcFactor of 0.5 will lead to the arc following a circle path with the center at the mid point of start and end.

import { ArcStyle } from '@vcmap/core';

const style = new ArcStyle({ arcFactor: 0.2 });
style.arcFactor = 0.5; // you can change the arc factor. You must redraw yourself

The arc is rendered in segments. By default, this is 64. You can set the number of segments to either get smoother arcs or better performance.

import { ArcStyle } from '@vcmap/core';

const style = new ArcStyle({ numberOfSegments: 128 });
style.numberOfSegments = 16; // you can change the number of segments. You must redraw yourself