Skip to main content

Add Image Missing Generated

Dynamically generate a missing icon at runtime and add it to the map. Requires Trimble Maps v3.0.0 or later.

<!doctype html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>3D Terrain</title>
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <link rel="stylesheet" href="https://maps-sdk.trimblemaps.com/v4/trimblemaps-4.2.3.css" />
    <script src="https://maps-sdk.trimblemaps.com/v4/trimblemaps-4.2.3.js"></script>
    <style>
      body {
        margin: 0;
        padding: 0;
      }
      html,
      body,
      #map {
        height: 100%;
      }
    </style>
  </head>
  <body>
    <div id="map"></div>
    <script>
      TrimbleMaps.setAPIKey('YOUR_API_KEY_HERE');
      const map = new TrimbleMaps.Map({
        container: 'map',
        zoom: 5,
        style: TrimbleMaps.Common.Style.TRANSPORTATION,
      });

      map.on('styleimagemissing', (e) => {
        const id = e.id; // id of the missing image

        // check if this missing icon is one this function can generate
        const prefix = 'square-rgb-';
        if (id.indexOf(prefix) !== 0) return;

        // extract the color from the id
        const rgb = id.replace(prefix, '').split(',').map(Number);

        const width = 64; // The image will be 64 pixels square
        const bytesPerPixel = 4; // Each pixel is represented by 4 bytes: red, green, blue, and alpha.
        const data = new Uint8Array(width * width * bytesPerPixel);

        for (let x = 0; x < width; x++) {
          for (let y = 0; y < width; y++) {
            const offset = (y * width + x) * bytesPerPixel;
            data[offset + 0] = rgb[0]; // red
            data[offset + 1] = rgb[1]; // green
            data[offset + 2] = rgb[2]; // blue
            data[offset + 3] = 255; // alpha
          }
        }

        map.addImage(id, {width, height: width, data});
      });

      map.on('load', () => {
        map.addSource('points', {
          type: 'geojson',
          data: {
            type: 'FeatureCollection',
            features: [
              {
                type: 'Feature',
                geometry: {
                  type: 'Point',
                  coordinates: [0, 0],
                },
                properties: {
                  color: '255,0,0',
                },
              },
              {
                type: 'Feature',
                geometry: {
                  type: 'Point',
                  coordinates: [50, 0],
                },
                properties: {
                  color: '255,209,28',
                },
              },
              {
                type: 'Feature',
                geometry: {
                  type: 'Point',
                  coordinates: [-50, 0],
                },
                properties: {
                  color: '242,127,32',
                },
              },
            ],
          },
        });

        map.addLayer({
          id: 'points',
          type: 'symbol',
          source: 'points',
          layout: {
            'icon-image': ['concat', 'square-rgb-', ['get', 'color']],
          },
        });
      });
    </script>
  </body>
</html>
Last updated June 26, 2025.