---
id: "packages/active-geo/examples"
title: "Examples"
description: "Every working example of active-geo on one page. Each one shows the file that renders it."
url: "/packages/active-geo/examples"
locale: "en"
revision: "b191128df6cc0a3b"
---

# Examples

Both examples are **Client** examples. They load the world collection, which ships with the
package; the values and sites are invented.

**Example: Countries coloured by a measure**

Client: Runs entirely in your browser. Source: `examples/geo/world-map.tsx`.

```tsx
// apps/docs/examples/geo/world-map.tsx
'use client';

import {useEffect, useState} from 'react';

import {
  englishGeoTranslator,
  GeoMap,
  type GeoAreaFeature,
} from '@workspace/active-geo';
import {
  loadWorld50m,
  world50m,
} from '@workspace/active-geo/collections/world-50m';

// Invented values per country, joined by the collection's key (ADM0_A3).
const SHARE: Record<string, number> = {
  NLD: 82,
  BEL: 64,
  DEU: 71,
  FRA: 55,
  GBR: 48,
  ESP: 39,
  ITA: 44,
  POL: 31,
  SWE: 77,
  NOR: 69,
  USA: 58,
  CAN: 62,
  BRA: 27,
  IND: 19,
  JPN: 66,
  AUS: 52,
};

/**
 * The optional world collection (Natural Earth, 1:50m), loaded on demand,
 * coloured by a measure with a threshold scale. Hover or focus a country
 * for its value; the menu (right click, Shift+F10) holds the table and export.
 */
export default function WorldMap() {
  const [features, setFeatures] = useState<GeoAreaFeature[] | null>(null);
  useEffect(() => {
    let current = true;
    void loadWorld50m().then((loaded) => {
      if (current) setFeatures([...loaded]);
    });
    return () => {
      current = false;
    };
  }, []);
  if (!features) {
    return <p className="text-muted-foreground text-sm">Loading the map…</p>;
  }
  return (
    // The map takes the width of its container (a ResizeObserver);
    // in a centring layout the host gives it one.
    <div className="w-full">
      <GeoMap
        title="Share of online orders"
        projection="equal-earth"
        locale="en-GB"
        t={englishGeoTranslator}
        attribution={world50m.attribution}
        layers={[
          {
            type: 'area',
            id: 'countries',
            title: 'Countries',
            features,
            measures: [
              {
                id: 'share',
                label: 'Online share',
                semantics: {
                  kind: 'percent',
                  source: 'percentage-points',
                  preset: 'integer',
                },
              },
            ],
            data: Object.entries(SHARE).map(([key, share]) => ({
              key,
              values: {share},
            })),
            fill: {
              measure: 'share',
              scale: {type: 'threshold', thresholds: [30, 50, 70]},
            },
          },
        ]}
      />
    </div>
  );
}
```

**Example: Sites sized by their staff**

Client: Runs entirely in your browser. Source: `examples/geo/points.tsx`.

```tsx
// apps/docs/examples/geo/points.tsx
'use client';

import {useEffect, useState} from 'react';

import {
  englishGeoTranslator,
  GeoMap,
  type GeoAreaFeature,
  type GeoContextGeometry,
} from '@workspace/active-geo';
import {
  loadWorld50m,
  world50m,
} from '@workspace/active-geo/collections/world-50m';

const BENELUX = new Set(['NLD', 'BEL', 'LUX']);

// Invented sites, sized by their staff.
const SITES = [
  {key: 'ams', name: 'Amsterdam', latitude: 52.37, longitude: 4.9, staff: 120},
  {key: 'rtm', name: 'Rotterdam', latitude: 51.92, longitude: 4.48, staff: 64},
  {key: 'utr', name: 'Utrecht', latitude: 52.09, longitude: 5.12, staff: 38},
  {key: 'ein', name: 'Eindhoven', latitude: 51.44, longitude: 5.47, staff: 45},
  {key: 'bru', name: 'Brussels', latitude: 50.85, longitude: 4.35, staff: 72},
  {key: 'ant', name: 'Antwerp', latitude: 51.22, longitude: 4.4, staff: 51},
  {key: 'lux', name: 'Luxembourg', latitude: 49.61, longitude: 6.13, staff: 19},
];

/**
 * Point symbols over context geometry, sized by a count, with a legend, a
 * tooltip and selection (click, or Enter on a focused point).
 */
export default function SitesMap() {
  const [outline, setOutline] = useState<GeoAreaFeature[] | null>(null);
  useEffect(() => {
    let current = true;
    void loadWorld50m().then((loaded) => {
      if (current) setOutline(loaded.filter((f) => BENELUX.has(String(f.key))));
    });
    return () => {
      current = false;
    };
  }, []);
  if (!outline) {
    return <p className="text-muted-foreground text-sm">Loading the map…</p>;
  }
  return (
    // The map takes the width of its container (a ResizeObserver);
    // in a centring layout the host gives it one.
    <div className="w-full">
      <GeoMap
        title="Sites in the Benelux"
        projection="conic-equal-area"
        locale="en-GB"
        t={englishGeoTranslator}
        attribution={world50m.attribution}
        layers={[
          {
            type: 'context',
            id: 'benelux',
            title: 'Benelux',
            // Context, not the frame: the Netherlands of Natural Earth
            // include the Caribbean islands, so the sites frame the map.
            fit: false,
            geometries: outline.flatMap((feature): GeoContextGeometry[] =>
              feature.geometry ? [feature.geometry] : [],
            ),
          },
          {
            type: 'point',
            id: 'sites',
            title: 'Sites',
            measures: [
              {id: 'staff', label: 'Staff', semantics: {kind: 'count'}},
            ],
            marker: {size: {measure: 'staff'}},
            points: SITES.map(({staff, ...site}) => ({
              ...site,
              values: {staff},
            })),
          },
        ]}
      />
    </div>
  );
}
```
