# opengeos/anymap-studio architecture

> Architecture diagram of the GitHub repository opengeos/anymap-studio, generated by GitDiagram from its file tree, README and a sample of source files (last updated 2026-09-29). It is an AI-made overview: check details against the source.

- Interactive diagram: https://gitdiagram.com/opengeos/anymap-studio
- Repository: https://github.com/opengeos/anymap-studio

## Overview

AnyMap Studio is an Electron GIS desktop app for loading geospatial data, managing layers and projects, and viewing them through a selectable map backend. The primary workflow is to choose a backend, add local or URL-based layers, inspect and style them, then save the project or export results. Navigation, drawing, measuring, and coordinate tools complement that workflow. The README documents eight backends and several formats; sampled implementation confirms MapLibre and selected import paths, so other adapters and capabilities are represented at their documented source paths without asserting their readiness. Some UI wiring is unsampled.

Main entry points: [`src/stores/projectStore.ts`](https://github.com/opengeos/anymap-studio/blob/main/src/stores/projectStore.ts) (Project store), [`src/components/map/MapCanvas.tsx`](https://github.com/opengeos/anymap-studio/blob/main/src/components/map/MapCanvas.tsx) (Map canvas), [`src/App.tsx`](https://github.com/opengeos/anymap-studio/blob/main/src/App.tsx) (App), [`src/stores/uiStore.ts`](https://github.com/opengeos/anymap-studio/blob/main/src/stores/uiStore.ts) (UI store)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_desktop["Desktop workflow"]
  node_app["App<br/>[App.tsx]"]
  node_electron["Electron main<br/>[main.ts]"]
  node_preload["IPC bridge<br/>[preload.ts]"]
  node_landing["Landing page<br/>[LandingPage.tsx]"]
  node_shell["App shell<br/>[AppShell.tsx]"]
  node_electronapi["Electron API<br/>[electron-api.d.ts]"]
end

subgraph group_mapping["Map rendering"]
  node_backendselector["Backend selector"]
  node_mapcanvas["Map canvas<br/>[MapCanvas.tsx]"]
  node_backendfactory["Backend factory<br/>[index.ts]"]
  node_capabilities["Backend capabilities<br/>[capabilities.ts]"]
  node_adapters["Map adapters"]
  node_maplibreadapter["MapLibre adapter<br/>[MapLibreAdapter.ts]"]
end

subgraph group_layers["Layer workflow"]
  node_layerspanel["Layer panel<br/>[LayerPanel.tsx]"]
  node_layeritem["Layer item<br/>[LayerItem.tsx]"]
  node_styleeditor["Style editor<br/>[StyleEditor.tsx]"]
  node_attributetable["Attribute table<br/>[AttributeTable.tsx]"]
  node_parsers["Format parsers<br/>[parsers.ts]"]
  node_geoutils["Geospatial utilities<br/>[geo.ts]"]
end

subgraph group_projects["Project state"]
  node_projectstore[("Project store<br/>[projectStore.ts]")]
  node_projecttypes["Project format<br/>[project.ts]"]
  node_export["Export utilities<br/>[export.ts]"]
end

subgraph group_tools["Map tools"]
  node_toolbar["Toolbar<br/>[Toolbar.tsx]"]
  node_drawtool["Drawing tool<br/>[DrawTool.tsx]"]
  node_measuretool["Measurement tool<br/>[MeasureTool.tsx]"]
  node_mapcontrols["Map controls<br/>[MapControls.tsx]"]
  node_uistore[("UI store<br/>[uiStore.ts]")]
end

node_user(("GIS user"))

node_user -->|"uses"| node_app
node_app -->|"shows"| node_landing
node_app -->|"shows"| node_shell
node_electron -->|"exposes IPC"| node_preload
node_preload -->|"implements bridge"| node_electronapi
node_electron -->|"sends project events"| node_app
node_app -->|"loads and saves"| node_projectstore
node_backendselector -->|"selects view"| node_uistore
node_mapcanvas -->|"creates backend"| node_backendfactory
node_backendfactory -->|"dispatches by type"| node_adapters
node_backendfactory -->|"initializes"| node_maplibreadapter
node_mapcanvas -->|"reads layers and view"| node_projectstore
node_mapcanvas -->|"parses dropped data"| node_parsers
node_mapcanvas -->|"calculates bounds"| node_geoutils
node_layerspanel -->|"parses imports"| node_parsers
node_layerspanel -->|"updates layers"| node_projectstore
node_layerspanel -->|"adds backend layer"| node_mapcanvas
node_layeritem -->|"updates layer state"| node_projectstore
node_styleeditor -->|"updates styling"| node_projectstore
node_attributetable -->|"reads layer data"| node_projectstore
node_projectstore -->|"models project"| node_projecttypes
node_toolbar -->|"saves project state"| node_projectstore
node_toolbar -->|"computes bounds"| node_geoutils
node_toolbar -->|"sets active tool"| node_uistore
node_drawtool -->|"uses tool state"| node_uistore
node_measuretool -->|"uses tool state"| node_uistore
node_mapcontrols -->|"uses UI state"| node_uistore
node_toolbar -->|"exports data"| node_export

click node_app "https://github.com/opengeos/anymap-studio/blob/main/src/App.tsx"
click node_electron "https://github.com/opengeos/anymap-studio/blob/main/electron/main.ts"
click node_preload "https://github.com/opengeos/anymap-studio/blob/main/electron/preload.ts"
click node_landing "https://github.com/opengeos/anymap-studio/blob/main/src/components/landing/LandingPage.tsx"
click node_shell "https://github.com/opengeos/anymap-studio/blob/main/src/components/layout/AppShell.tsx"
click node_backendselector "https://github.com/opengeos/anymap-studio/blob/main/src/components/landing/BackendSelector.tsx"
click node_mapcanvas "https://github.com/opengeos/anymap-studio/blob/main/src/components/map/MapCanvas.tsx"
click node_backendfactory "https://github.com/opengeos/anymap-studio/blob/main/src/backends/index.ts"
click node_capabilities "https://github.com/opengeos/anymap-studio/blob/main/src/backends/capabilities.ts"
click node_adapters "https://github.com/opengeos/anymap-studio/tree/main/src/backends/adapters"
click node_maplibreadapter "https://github.com/opengeos/anymap-studio/blob/main/src/backends/adapters/MapLibreAdapter.ts"
click node_layerspanel "https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/LayerPanel.tsx"
click node_layeritem "https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/LayerItem.tsx"
click node_styleeditor "https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/StyleEditor.tsx"
click node_attributetable "https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/AttributeTable.tsx"
click node_parsers "https://github.com/opengeos/anymap-studio/blob/main/src/utils/parsers.ts"
click node_geoutils "https://github.com/opengeos/anymap-studio/blob/main/src/utils/geo.ts"
click node_projectstore "https://github.com/opengeos/anymap-studio/blob/main/src/stores/projectStore.ts"
click node_projecttypes "https://github.com/opengeos/anymap-studio/blob/main/src/types/project.ts"
click node_export "https://github.com/opengeos/anymap-studio/blob/main/src/utils/export.ts"
click node_toolbar "https://github.com/opengeos/anymap-studio/blob/main/src/components/layout/Toolbar.tsx"
click node_drawtool "https://github.com/opengeos/anymap-studio/blob/main/src/components/tools/DrawTool.tsx"
click node_measuretool "https://github.com/opengeos/anymap-studio/blob/main/src/components/tools/MeasureTool.tsx"
click node_mapcontrols "https://github.com/opengeos/anymap-studio/blob/main/src/components/map/MapControls.tsx"
click node_uistore "https://github.com/opengeos/anymap-studio/blob/main/src/stores/uiStore.ts"
click node_electronapi "https://github.com/opengeos/anymap-studio/blob/main/src/types/electron-api.d.ts"

classDef toneNeutral fill:#f8fafc,stroke:#334155,stroke-width:1.5px,color:#0f172a
classDef toneBlue fill:#dbeafe,stroke:#2563eb,stroke-width:1.5px,color:#172554
classDef toneAmber fill:#fef3c7,stroke:#d97706,stroke-width:1.5px,color:#78350f
classDef toneMint fill:#dcfce7,stroke:#16a34a,stroke-width:1.5px,color:#14532d
classDef toneRose fill:#ffe4e6,stroke:#e11d48,stroke-width:1.5px,color:#881337
classDef toneIndigo fill:#e0e7ff,stroke:#4f46e5,stroke-width:1.5px,color:#312e81
classDef toneTeal fill:#ccfbf1,stroke:#0f766e,stroke-width:1.5px,color:#134e4a
class node_app,node_electron,node_preload,node_landing,node_shell,node_electronapi,node_user toneBlue
class node_backendselector,node_mapcanvas,node_backendfactory,node_capabilities,node_adapters,node_maplibreadapter toneAmber
class node_layerspanel,node_layeritem,node_styleeditor,node_attributetable,node_parsers,node_geoutils toneMint
class node_projectstore,node_projecttypes,node_export toneRose
class node_toolbar,node_drawtool,node_measuretool,node_mapcontrols,node_uistore toneIndigo
```

## Components

### Desktop workflow

- [App](https://github.com/opengeos/anymap-studio/blob/main/src/App.tsx): `src/App.tsx`
- [Electron main](https://github.com/opengeos/anymap-studio/blob/main/electron/main.ts): `electron/main.ts`
- [IPC bridge](https://github.com/opengeos/anymap-studio/blob/main/electron/preload.ts): `electron/preload.ts`
- [Landing page](https://github.com/opengeos/anymap-studio/blob/main/src/components/landing/LandingPage.tsx): `src/components/landing/LandingPage.tsx`
- [App shell](https://github.com/opengeos/anymap-studio/blob/main/src/components/layout/AppShell.tsx): `src/components/layout/AppShell.tsx`
- [Electron API](https://github.com/opengeos/anymap-studio/blob/main/src/types/electron-api.d.ts): `src/types/electron-api.d.ts`

### Map rendering

- [Backend selector](https://github.com/opengeos/anymap-studio/blob/main/src/components/landing/BackendSelector.tsx): `src/components/landing/BackendSelector.tsx`
- [Map canvas](https://github.com/opengeos/anymap-studio/blob/main/src/components/map/MapCanvas.tsx): `src/components/map/MapCanvas.tsx`
- [Backend factory](https://github.com/opengeos/anymap-studio/blob/main/src/backends/index.ts): `src/backends/index.ts`
- [Backend capabilities](https://github.com/opengeos/anymap-studio/blob/main/src/backends/capabilities.ts): `src/backends/capabilities.ts`
- [Map adapters](https://github.com/opengeos/anymap-studio/tree/main/src/backends/adapters): `src/backends/adapters`
- [MapLibre adapter](https://github.com/opengeos/anymap-studio/blob/main/src/backends/adapters/MapLibreAdapter.ts): `src/backends/adapters/MapLibreAdapter.ts`

### Layer workflow

- [Layer panel](https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/LayerPanel.tsx): `src/components/layers/LayerPanel.tsx`
- [Layer item](https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/LayerItem.tsx): `src/components/layers/LayerItem.tsx`
- [Style editor](https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/StyleEditor.tsx): `src/components/layers/StyleEditor.tsx`
- [Attribute table](https://github.com/opengeos/anymap-studio/blob/main/src/components/layers/AttributeTable.tsx): `src/components/layers/AttributeTable.tsx`
- [Format parsers](https://github.com/opengeos/anymap-studio/blob/main/src/utils/parsers.ts): `src/utils/parsers.ts`
- [Geospatial utilities](https://github.com/opengeos/anymap-studio/blob/main/src/utils/geo.ts): `src/utils/geo.ts`

### Project state

- [Project store](https://github.com/opengeos/anymap-studio/blob/main/src/stores/projectStore.ts): `src/stores/projectStore.ts`
- [Project format](https://github.com/opengeos/anymap-studio/blob/main/src/types/project.ts): `src/types/project.ts`
- [Export utilities](https://github.com/opengeos/anymap-studio/blob/main/src/utils/export.ts): `src/utils/export.ts`

### Map tools

- [Toolbar](https://github.com/opengeos/anymap-studio/blob/main/src/components/layout/Toolbar.tsx): `src/components/layout/Toolbar.tsx`
- [Drawing tool](https://github.com/opengeos/anymap-studio/blob/main/src/components/tools/DrawTool.tsx): `src/components/tools/DrawTool.tsx`
- [Measurement tool](https://github.com/opengeos/anymap-studio/blob/main/src/components/tools/MeasureTool.tsx): `src/components/tools/MeasureTool.tsx`
- [Map controls](https://github.com/opengeos/anymap-studio/blob/main/src/components/map/MapControls.tsx): `src/components/map/MapControls.tsx`
- [UI store](https://github.com/opengeos/anymap-studio/blob/main/src/stores/uiStore.ts): `src/stores/uiStore.ts`

### Other components

- **GIS user**

## Connections

- GIS user → App: uses
- App → Landing page: shows
- App → App shell: shows
- Electron main → IPC bridge: exposes IPC
- IPC bridge → Electron API: implements bridge
- Electron main → App: sends project events
- App → Project store: loads and saves
- Backend selector → UI store: selects view
- Map canvas → Backend factory: creates backend
- Backend factory → Map adapters: dispatches by type
- Backend factory → MapLibre adapter: initializes
- Map canvas → Project store: reads layers and view
- Map canvas → Format parsers: parses dropped data
- Map canvas → Geospatial utilities: calculates bounds
- Layer panel → Format parsers: parses imports
- Layer panel → Project store: updates layers
- Layer panel → Map canvas: adds backend layer
- Layer item → Project store: updates layer state
- Style editor → Project store: updates styling
- Attribute table → Project store: reads layer data
- Project store → Project format: models project
- Toolbar → Project store: saves project state
- Toolbar → Geospatial utilities: computes bounds
- Toolbar → UI store: sets active tool
- Drawing tool → UI store: uses tool state
- Measurement tool → UI store: uses tool state
- Map controls → UI store: uses UI state
- Toolbar → Export utilities: exports data
