ng-simple-maps
v1.0.1
Published
Beautiful, lightweight SVG world maps for Angular applications. Create interactive choropleth maps, markers, lines, and more with D3 geo projections. Perfect for data visualization, analytics dashboards, and geographic applications.
Maintainers
Keywords
Readme
ng-simple-maps
Beautiful, lightweight SVG world maps for Angular applications. Create stunning interactive choropleth maps, data visualizations, geographic dashboards, and analytics with D3 geo projections. Perfect for business intelligence, travel apps, educational tools, and corporate websites.
🚀 Live Demo & Documentation
Angular Version Support
This library supports Angular 15+.
Peer Dependencies:
@angular/core@>=15.0.0and@angular/common@>=15.0.0
🗺️ World Map Library | 📊 Data Visualization | 🌍 Geographic Mapping | 📱 Responsive Design | ⚡ Interactive Maps
Features
- One Simple Component - Everything you need in
<asm-map> - Data-Driven - Pass arrays of markers, annotations, and lines
- Lines/Connections - Draw curved flight paths between points
- Choropleth Maps - Color countries by data values
- Country Labels - Show country names with zoom-based visibility
- Zoom to Feature - Click countries to zoom and center on them
- Graticule Grid - Latitude/longitude grid lines
- Zoom & Pan - Enable with a single property
- Tooltips - Automatic on hover, fully customizable
- 15+ Projections - Mercator, Equal Earth, Orthographic, and more
- Continent Filtering - Show only the regions you need
- Multiple Marker Shapes - Circle, diamond, pin, star
- Fully Responsive - Scales to any screen size
- TypeScript - Full type safety
Installation
npm install ng-simple-mapsQuick Start
import { Component } from '@angular/core';
import { MapComponent } from 'ng-simple-maps';
@Component({
imports: [MapComponent],
template: `
<asm-map
[geography]="worldData"
[zoomable]="true"
[showTooltip]="true">
</asm-map>
`
})
export class MyComponent {
worldData = 'https://cdn.jsdelivr.net/npm/world-atlas@2/countries-110m.json';
}That's it! You have a fully interactive world map with zoom, pan, and tooltips.
Examples
With Markers
import { MapComponent, MapMarker } from 'ng-simple-maps';
@Component({
imports: [MapComponent],
template: `
<asm-map
[geography]="worldData"
[markers]="markers"
[zoomable]="true"
[showTooltip]="true"
(markerClick)="onMarkerClick($event)">
</asm-map>
`
})
export class MyComponent {
worldData = 'https://cdn.jsdelivr.net/npm/world-atlas@2/countries-110m.json';
markers: MapMarker[] = [
{ coordinates: [-74.006, 40.7128], label: 'New York', color: '#FF5533' },
{ coordinates: [2.3522, 48.8566], label: 'Paris', color: '#FFD700', size: 8 },
{ coordinates: [37.6173, 55.7558], label: 'Moscow', shape: 'diamond' }
];
onMarkerClick(event) {
console.log('Clicked:', event.marker.label);
}
}With Annotations
markers: MapMarker[] = [
{ coordinates: [-74.006, 40.7128], label: 'New York' }
];
annotations: MapAnnotation[] = [
{ coordinates: [-74.006, 40.7128], text: 'New York', dx: 50, dy: -30, curve: 0.5 }
];<asm-map
[geography]="worldData"
[markers]="markers"
[annotations]="annotations">
</asm-map>Continent Filtering
<!-- Single continent -->
<asm-map [geography]="worldData" continents="Europe"></asm-map>
<!-- Multiple continents -->
<asm-map [geography]="worldData" [continents]="['Asia', 'Europe']"></asm-map>Custom Styling
<asm-map
[geography]="worldData"
fill="#457B9D"
stroke="#1D3557"
hoverFill="#2A4D6E"
[tooltipConfig]="{ backgroundColor: '#1D3557', textColor: '#fff' }">
</asm-map>Different Projections
<!-- Globe view -->
<asm-map [geography]="worldData" projection="geoOrthographic"></asm-map>
<!-- Mercator -->
<asm-map [geography]="worldData" projection="geoMercator"></asm-map>
<!-- Rotated orthographic (custom view) -->
<asm-map
[geography]="worldData"
projection="geoOrthographic"
[projectionConfig]="{ rotate: [-10, -20] }">
</asm-map>
<!-- Centered on Asia -->
<asm-map
[geography]="worldData"
projection="geoEqualEarth"
[projectionConfig]="{ center: [100, 30] }">
</asm-map>Lines/Connections (Flight Paths)
import { MapComponent, MapLine } from 'ng-simple-maps';
lines: MapLine[] = [
{ from: [-74.006, 40.7128], to: [-0.1276, 51.5074], color: '#E91E63', curve: 0.4 },
{ from: [-74.006, 40.7128], to: [139.6917, 35.6895], color: '#3F51B5', curve: 0.5, dashed: true }
];<asm-map
[geography]="worldData"
[lines]="lines"
(lineClick)="onLineClick($event)">
</asm-map>Choropleth Maps (Data Coloring)
import { MapComponent, ChoroplethData } from 'ng-simple-maps';
populationData: ChoroplethData = {
'United States of America': 330,
'China': 1400,
'India': 1380,
'Brazil': 212
};<asm-map
[geography]="worldData"
[choroplethData]="populationData"
[choroplethConfig]="{
matchKey: 'name',
colors: ['#FFF3E0', '#FFCC80', '#FFA726', '#F57C00', '#E65100'],
nullColor: '#ECECEC'
}">
</asm-map>Graticule (Grid Lines)
<asm-map
[geography]="worldData"
projection="geoOrthographic"
[showGraticule]="true"
[graticuleConfig]="{ step: [15, 15], color: '#B3E5FC', opacity: 0.8 }">
</asm-map>Country Labels
<asm-map
[geography]="worldData"
[showLabels]="true"
[labelMinZoom]="2"
[labelColor]="'#333'"
[labelFontSize]="14"
[zoomable]="true">
</asm-map>Zoom to Feature
<asm-map
[geography]="worldData"
[zoomable]="true"
[zoomOnClick]="true"
[zoomOnClickLevel]="4"
[zoomAnimationDuration]="1000">
</asm-map>API Reference
MapComponent Inputs
| Input | Type | Default | Description |
|-------|------|---------|-------------|
| geography | string \| object | required | Geography data URL or TopoJSON/GeoJSON object |
| width | number | 800 | Map width (for aspect ratio) |
| height | number | 400 | Map height (for aspect ratio) |
| maxWidth | number | null | Maximum width constraint |
| projection | string | 'geoEqualEarth' | D3 projection type |
| projectionConfig | ProjectionConfig | {} | Projection configuration options |
| continents | string \| string[] | null | Filter by continent(s) |
| fill | string | '#ECECEC' | Geography fill color |
| stroke | string | '#D6D6D6' | Geography stroke color |
| strokeWidth | number | 0.5 | Geography stroke width |
| hoverFill | string | null | Fill color on hover |
| markers | MapMarker[] | [] | Array of markers |
| annotations | MapAnnotation[] | [] | Array of annotations |
| markerColor | string | '#FF5533' | Default marker color |
| markerSize | number | 6 | Default marker size |
| lines | MapLine[] | [] | Array of lines/connections |
| lineColor | string | '#FF5533' | Default line color |
| lineStrokeWidth | number | 2 | Default line stroke width |
| choroplethData | ChoroplethData | null | Data for coloring geographies |
| choroplethConfig | ChoroplethConfig | null | Choropleth styling config |
| showGraticule | boolean | false | Show grid lines |
| graticuleConfig | GraticuleConfig | null | Graticule styling config |
| zoomable | boolean | false | Enable zoom and pan |
| showZoomControls | boolean | true | Show zoom buttons |
| minZoom | number | 1 | Minimum zoom level |
| maxZoom | number | 8 | Maximum zoom level |
| zoomOnClick | boolean | false | Zoom to country on click |
| zoomOnClickLevel | number | 4 | Zoom level when clicking country |
| zoomAnimationDuration | number | 800 | Animation duration in milliseconds |
| showTooltip | boolean | false | Show tooltip on hover |
| tooltipConfig | TooltipConfig | null | Tooltip styling |
| showLabels | boolean | false | Show country labels |
| labelMinZoom | number | 1 | Minimum zoom level to show labels |
| labelFontSize | number | 12 | Label font size |
| labelColor | string | '#333' | Label text color |
| labelFontWeight | string \| number | 'normal' | Label font weight |
MapComponent Outputs
| Output | Type | Description |
|--------|------|-------------|
| countryClick | MapGeographyEvent | Emitted when a country is clicked |
| countryHover | MapGeographyEvent | Emitted when hovering over a country |
| countryLeave | void | Emitted when mouse leaves a country |
| markerClick | MapMarkerEvent | Emitted when a marker is clicked |
| lineClick | MapLineEvent | Emitted when a line is clicked |
MapMarker Interface
interface MapMarker {
coordinates: [number, number]; // [longitude, latitude]
label?: string; // Optional label
color?: string; // Fill color
stroke?: string; // Stroke color
size?: number; // Size/radius (6-12 for icons, 16-24 for detailed SVGs)
shape?: 'circle' | 'diamond' | 'pin' | 'star' | 'custom';
customSvg?: string; // SVG path data for shape='custom'
customSvgSize?: number; // ViewBox size for custom SVG (default: 24)
data?: Record<string, unknown>; // Custom data
}Custom SVG Markers
Three ways to use custom SVG icons as markers:
Option 1: Path Data Only (Recommended)
Just the d attribute value - most lightweight:
const AIRPLANE = 'M21,16V14L13,9V3.5A1.5,1.5,0,0,0,11.5,2...Z';
markers: MapMarker[] = [
{ coordinates: [-118.24, 34.05], shape: 'custom', customSvg: AIRPLANE, size: 10 }
];Option 2: Full SVG Markup
For complex icons with multiple elements:
const PIN = `<svg viewBox="0 0 24 24">
<path d="M12,2C8.13,2,5,5.13,5,9c0,5.25,7,13,7,13s7-7.75,7-13C19,5.13,15.87,2,12,2z"/>
<circle cx="12" cy="9" r="2.5" fill="white"/>
</svg>`;
markers: MapMarker[] = [
{ coordinates: [121.47, 31.23], shape: 'custom', customSvg: PIN, size: 12 }
];Option 3: Load from URL
Load SVG files from your assets folder:
markers: MapMarker[] = [
{ coordinates: [0, 0], shape: 'custom', customSvgUrl: '/assets/icons/marker.svg', size: 12 }
];SVG Size Guidelines:
| Use Case | size | Description |
|----------|--------|-------------|
| Small icons | 6-8 | Simple shapes |
| Standard | 10-12 | Recommended |
| Large/detailed | 14-18 | Fine details |
| Icon Set | customSvgSize |
|----------|-----------------|
| Material Design | 24 (default) |
| Font Awesome | 24 |
| Custom 16px | 16 |
MapAnnotation Interface
interface MapAnnotation {
coordinates: [number, number]; // [longitude, latitude]
text: string; // Label text
dx?: number; // Horizontal offset (default: 30)
dy?: number; // Vertical offset (default: -30)
curve?: number; // Connector curve (0-1, default: 0)
color?: string; // Text and connector color
fontSize?: number; // Font size
fontWeight?: string | number; // Font weight
}TooltipConfig Interface
interface TooltipConfig {
backgroundColor?: string; // Default: '#fff'
textColor?: string; // Default: '#333'
titleColor?: string; // Default: same as textColor
borderColor?: string; // Default: '#ccc'
borderRadius?: number; // Default: 4
}MapLine Interface
interface MapLine {
from: [number, number]; // Starting [longitude, latitude]
to: [number, number]; // Ending [longitude, latitude]
color?: string; // Line color
strokeWidth?: number; // Line thickness
curve?: number; // Arc height (0 = straight, higher = more curved)
dashed?: boolean; // Dashed line style
data?: Record<string, unknown>; // Custom data
}ChoroplethConfig Interface
interface ChoroplethConfig {
matchKey?: string; // Property to match (default: 'name')
colors?: string[]; // Color scale from low to high
minValue?: number; // Override minimum value
maxValue?: number; // Override maximum value
nullColor?: string; // Color for missing data (default: '#ECECEC')
}GraticuleConfig Interface
interface GraticuleConfig {
step?: [number, number]; // Grid spacing in degrees (default: [10, 10])
color?: string; // Line color (default: '#ccc')
strokeWidth?: number; // Line thickness (default: 0.5)
opacity?: number; // Line opacity (default: 0.5)
}ProjectionConfig Interface
interface ProjectionConfig {
rotate?: [number, number, number?]; // Rotation angles [lambda, phi, gamma] in degrees
center?: [number, number]; // Center coordinates [longitude, latitude]
scale?: number; // Scale factor for the projection
parallels?: [number, number]; // Standard parallels for conic projections
translate?: [number, number]; // Translation offset [x, y]
precision?: number; // Precision threshold for adaptive resampling
clipAngle?: number; // Clipping angle for azimuthal projections
}Available Projections
geoEqualEarth(default)geoMercatorgeoOrthographicgeoNaturalEarth1geoAlbersgeoAlbersUsageoAzimuthalEqualAreageoAzimuthalEquidistantgeoConicConformalgeoConicEqualAreageoConicEquidistantgeoEquirectangulargeoGnomonicgeoStereographicgeoTransverseMercator
Continent Options
'Africa''Asia''Europe''North America''South America''Oceania''Antarctica'
TopoJSON Data Sources
World Atlas (Recommended)
Free, high-quality world country data maintained by Mike Bostock. Choose the right resolution for your use case:
CDN Links (Ready to Use)
// Fast loading (13KB) - for mobile apps and overview maps
worldData = 'https://cdn.jsdelivr.net/npm/world-atlas@2/countries-110m.json';
// Balanced quality (23KB) - recommended for web apps
worldData = 'https://cdn.jsdelivr.net/npm/world-atlas@2/countries-50m.json';
// High detail (94KB) - for detailed maps and print quality
worldData = 'https://cdn.jsdelivr.net/npm/world-atlas@2/countries-10m.json';Resolution Guide
| Resolution | File Size | Use Case | Best For | |------------|-----------|----------|----------| | 110m | 13KB | Fast loading | Mobile apps, overview maps, low bandwidth | | 50m | 23KB | Recommended | Web applications, general purpose | | 10m | 94KB | High detail | Desktop apps, print quality, detailed viewing |
Available Files
countries-110m.json- Low resolution, fast loadingcountries-50m.json- Medium resolution, balanced (used in all demos)countries-10m.json- High resolution, detailed
Other Data Sources
- World Atlas GitHub - Source repository
- Natural Earth - Free map data in various formats
- TopoJSON Collection - Various geographic datasets
Local Files
You can also download and serve TopoJSON files from your own assets folder:
// From local assets
worldData = '/assets/data/countries-50m.json';License
MIT
Credits
Inspired by react-simple-maps. Built with D3 Geo.
