maplibre-gl-components 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (56) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +380 -0
  3. package/dist/HtmlControl-BbinjIOJ.cjs +1190 -0
  4. package/dist/HtmlControl-BbinjIOJ.cjs.map +1 -0
  5. package/dist/HtmlControl-iggZQwXP.js +1191 -0
  6. package/dist/HtmlControl-iggZQwXP.js.map +1 -0
  7. package/dist/index.cjs +86 -0
  8. package/dist/index.cjs.map +1 -0
  9. package/dist/index.mjs +86 -0
  10. package/dist/index.mjs.map +1 -0
  11. package/dist/maplibre-gl-components.css +243 -0
  12. package/dist/react.cjs +342 -0
  13. package/dist/react.cjs.map +1 -0
  14. package/dist/react.mjs +342 -0
  15. package/dist/react.mjs.map +1 -0
  16. package/dist/types/index.d.ts +7 -0
  17. package/dist/types/index.d.ts.map +1 -0
  18. package/dist/types/lib/colormaps/diverging.d.ts +30 -0
  19. package/dist/types/lib/colormaps/diverging.d.ts.map +1 -0
  20. package/dist/types/lib/colormaps/index.d.ts +32 -0
  21. package/dist/types/lib/colormaps/index.d.ts.map +1 -0
  22. package/dist/types/lib/colormaps/misc.d.ts +38 -0
  23. package/dist/types/lib/colormaps/misc.d.ts.map +1 -0
  24. package/dist/types/lib/colormaps/sequential.d.ts +22 -0
  25. package/dist/types/lib/colormaps/sequential.d.ts.map +1 -0
  26. package/dist/types/lib/core/Colorbar.d.ts +122 -0
  27. package/dist/types/lib/core/Colorbar.d.ts.map +1 -0
  28. package/dist/types/lib/core/ColorbarReact.d.ts +34 -0
  29. package/dist/types/lib/core/ColorbarReact.d.ts.map +1 -0
  30. package/dist/types/lib/core/HtmlControl.d.ts +114 -0
  31. package/dist/types/lib/core/HtmlControl.d.ts.map +1 -0
  32. package/dist/types/lib/core/HtmlControlReact.d.ts +32 -0
  33. package/dist/types/lib/core/HtmlControlReact.d.ts.map +1 -0
  34. package/dist/types/lib/core/Legend.d.ts +136 -0
  35. package/dist/types/lib/core/Legend.d.ts.map +1 -0
  36. package/dist/types/lib/core/LegendReact.d.ts +34 -0
  37. package/dist/types/lib/core/LegendReact.d.ts.map +1 -0
  38. package/dist/types/lib/core/types.d.ts +238 -0
  39. package/dist/types/lib/core/types.d.ts.map +1 -0
  40. package/dist/types/lib/hooks/index.d.ts +4 -0
  41. package/dist/types/lib/hooks/index.d.ts.map +1 -0
  42. package/dist/types/lib/hooks/useColorbar.d.ts +36 -0
  43. package/dist/types/lib/hooks/useColorbar.d.ts.map +1 -0
  44. package/dist/types/lib/hooks/useHtmlControl.d.ts +33 -0
  45. package/dist/types/lib/hooks/useHtmlControl.d.ts.map +1 -0
  46. package/dist/types/lib/hooks/useLegend.d.ts +41 -0
  47. package/dist/types/lib/hooks/useLegend.d.ts.map +1 -0
  48. package/dist/types/lib/utils/color.d.ts +47 -0
  49. package/dist/types/lib/utils/color.d.ts.map +1 -0
  50. package/dist/types/lib/utils/helpers.d.ts +48 -0
  51. package/dist/types/lib/utils/helpers.d.ts.map +1 -0
  52. package/dist/types/lib/utils/index.d.ts +3 -0
  53. package/dist/types/lib/utils/index.d.ts.map +1 -0
  54. package/dist/types/react.d.ts +6 -0
  55. package/dist/types/react.d.ts.map +1 -0
  56. package/package.json +109 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Open Geospatial Solutions
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,380 @@
1
+ # maplibre-gl-components
2
+
3
+ Legend, colorbar, and HTML control components for MapLibre GL JS maps.
4
+
5
+ [![npm version](https://badge.fury.io/js/maplibre-gl-components.svg)](https://badge.fury.io/js/maplibre-gl-components)
6
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
7
+
8
+ ## Features
9
+
10
+ - **Colorbar** - Continuous gradient legends with built-in matplotlib colormaps
11
+ - **Legend** - Categorical legends with color swatches and labels
12
+ - **HtmlControl** - Flexible HTML content control for custom info panels
13
+ - **React Support** - First-class React components and hooks
14
+ - **TypeScript** - Full type definitions included
15
+ - **20+ Built-in Colormaps** - viridis, plasma, terrain, jet, and more
16
+
17
+ ## Installation
18
+
19
+ ```bash
20
+ npm install maplibre-gl-components
21
+ ```
22
+
23
+ ## Quick Start
24
+
25
+ ### Vanilla JavaScript/TypeScript
26
+
27
+ ```typescript
28
+ import maplibregl from 'maplibre-gl';
29
+ import { Colorbar, Legend, HtmlControl } from 'maplibre-gl-components';
30
+ import 'maplibre-gl-components/style.css';
31
+
32
+ const map = new maplibregl.Map({
33
+ container: 'map',
34
+ style: 'https://basemaps.cartocdn.com/gl/positron-gl-style/style.json',
35
+ center: [-98, 38.5],
36
+ zoom: 4,
37
+ });
38
+
39
+ // Add a colorbar
40
+ const colorbar = new Colorbar({
41
+ colormap: 'viridis',
42
+ vmin: 0,
43
+ vmax: 100,
44
+ label: 'Temperature',
45
+ units: '°C',
46
+ orientation: 'vertical',
47
+ });
48
+ map.addControl(colorbar, 'bottom-right');
49
+
50
+ // Add a legend
51
+ const legend = new Legend({
52
+ title: 'Land Cover',
53
+ items: [
54
+ { label: 'Forest', color: '#228B22' },
55
+ { label: 'Water', color: '#4169E1' },
56
+ { label: 'Urban', color: '#808080' },
57
+ ],
58
+ collapsible: true,
59
+ });
60
+ map.addControl(legend, 'bottom-left');
61
+
62
+ // Add an HTML control
63
+ const htmlControl = new HtmlControl({
64
+ html: '<div><strong>Stats:</strong> 1,234 features</div>',
65
+ });
66
+ map.addControl(htmlControl, 'top-left');
67
+
68
+ // Update HTML dynamically
69
+ htmlControl.setHtml('<div><strong>Stats:</strong> 5,678 features</div>');
70
+ ```
71
+
72
+ ### React
73
+
74
+ ```tsx
75
+ import { useState, useEffect, useRef } from 'react';
76
+ import maplibregl from 'maplibre-gl';
77
+ import { ColorbarReact, LegendReact, HtmlControlReact } from 'maplibre-gl-components/react';
78
+ import 'maplibre-gl-components/style.css';
79
+
80
+ function MyMap() {
81
+ const mapContainer = useRef<HTMLDivElement>(null);
82
+ const [map, setMap] = useState<maplibregl.Map | null>(null);
83
+ const [stats, setStats] = useState('Loading...');
84
+
85
+ useEffect(() => {
86
+ if (!mapContainer.current) return;
87
+
88
+ const mapInstance = new maplibregl.Map({
89
+ container: mapContainer.current,
90
+ style: 'https://basemaps.cartocdn.com/gl/positron-gl-style/style.json',
91
+ center: [-98, 38.5],
92
+ zoom: 4,
93
+ });
94
+
95
+ mapInstance.on('load', () => setMap(mapInstance));
96
+
97
+ return () => mapInstance.remove();
98
+ }, []);
99
+
100
+ return (
101
+ <div style={{ width: '100%', height: '100vh' }}>
102
+ <div ref={mapContainer} style={{ width: '100%', height: '100%' }} />
103
+
104
+ {map && (
105
+ <>
106
+ <ColorbarReact
107
+ map={map}
108
+ colormap="viridis"
109
+ vmin={0}
110
+ vmax={100}
111
+ label="Temperature"
112
+ units="°C"
113
+ position="bottom-right"
114
+ />
115
+
116
+ <LegendReact
117
+ map={map}
118
+ title="Categories"
119
+ items={[
120
+ { label: 'Low', color: '#2166ac' },
121
+ { label: 'High', color: '#b2182b' },
122
+ ]}
123
+ position="bottom-left"
124
+ collapsible
125
+ />
126
+
127
+ <HtmlControlReact
128
+ map={map}
129
+ html={`<div><strong>Stats:</strong> ${stats}</div>`}
130
+ position="top-left"
131
+ />
132
+ </>
133
+ )}
134
+ </div>
135
+ );
136
+ }
137
+ ```
138
+
139
+ ## API Reference
140
+
141
+ ### Colorbar
142
+
143
+ A continuous gradient colorbar control.
144
+
145
+ ```typescript
146
+ interface ColorbarOptions {
147
+ colormap?: ColormapName | string[]; // Colormap name or custom colors
148
+ colorStops?: ColorStop[]; // Fine-grained color control
149
+ vmin?: number; // Minimum value (default: 0)
150
+ vmax?: number; // Maximum value (default: 1)
151
+ label?: string; // Title/label
152
+ units?: string; // Units suffix
153
+ orientation?: 'horizontal' | 'vertical';
154
+ position?: 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right';
155
+ barThickness?: number; // Bar width/height in pixels
156
+ barLength?: number; // Bar length in pixels
157
+ ticks?: { count?: number; values?: number[]; format?: (v: number) => string };
158
+ visible?: boolean;
159
+ backgroundColor?: string;
160
+ opacity?: number;
161
+ fontSize?: number;
162
+ fontColor?: string;
163
+ }
164
+
165
+ // Methods
166
+ colorbar.show()
167
+ colorbar.hide()
168
+ colorbar.update(options)
169
+ colorbar.getState()
170
+ colorbar.on(event, handler)
171
+ colorbar.off(event, handler)
172
+ ```
173
+
174
+ ### Legend
175
+
176
+ A categorical legend control.
177
+
178
+ ```typescript
179
+ interface LegendOptions {
180
+ title?: string;
181
+ items?: LegendItem[]; // { label, color, shape?, icon? }
182
+ position?: ControlPosition;
183
+ visible?: boolean;
184
+ collapsible?: boolean;
185
+ collapsed?: boolean;
186
+ width?: number;
187
+ maxHeight?: number;
188
+ swatchSize?: number;
189
+ backgroundColor?: string;
190
+ opacity?: number;
191
+ fontSize?: number;
192
+ fontColor?: string;
193
+ }
194
+
195
+ interface LegendItem {
196
+ label: string;
197
+ color: string;
198
+ shape?: 'square' | 'circle' | 'line';
199
+ strokeColor?: string;
200
+ icon?: string; // URL to icon image
201
+ }
202
+
203
+ // Methods
204
+ legend.show()
205
+ legend.hide()
206
+ legend.expand()
207
+ legend.collapse()
208
+ legend.toggle()
209
+ legend.setItems(items)
210
+ legend.addItem(item)
211
+ legend.removeItem(label)
212
+ legend.update(options)
213
+ legend.getState()
214
+ ```
215
+
216
+ ### HtmlControl
217
+
218
+ A flexible HTML content control.
219
+
220
+ ```typescript
221
+ interface HtmlControlOptions {
222
+ html?: string; // HTML content
223
+ element?: HTMLElement; // Or provide a DOM element
224
+ position?: ControlPosition;
225
+ visible?: boolean;
226
+ backgroundColor?: string;
227
+ padding?: number;
228
+ borderRadius?: number;
229
+ opacity?: number;
230
+ maxWidth?: number;
231
+ maxHeight?: number;
232
+ }
233
+
234
+ // Methods
235
+ htmlControl.show()
236
+ htmlControl.hide()
237
+ htmlControl.setHtml(html) // Update HTML content
238
+ htmlControl.setElement(element) // Set DOM element
239
+ htmlControl.getElement() // Get content container
240
+ htmlControl.update(options)
241
+ htmlControl.getState()
242
+ ```
243
+
244
+ ## Built-in Colormaps
245
+
246
+ ### Sequential
247
+ - `viridis` - Perceptually uniform, colorblind-friendly
248
+ - `plasma` - Perceptually uniform
249
+ - `inferno` - Perceptually uniform
250
+ - `magma` - Perceptually uniform
251
+ - `cividis` - Colorblind-friendly
252
+
253
+ ### Diverging
254
+ - `coolwarm` - Blue to red through white
255
+ - `bwr` - Blue-white-red
256
+ - `seismic` - Blue to red
257
+ - `RdBu` - Red to blue
258
+ - `RdYlBu` - Red-yellow-blue
259
+ - `RdYlGn` - Red-yellow-green
260
+ - `spectral` - Rainbow-like diverging
261
+
262
+ ### Miscellaneous
263
+ - `jet` - Classic rainbow
264
+ - `rainbow` - Full spectrum
265
+ - `turbo` - Improved rainbow
266
+ - `terrain` - Elevation-like
267
+ - `ocean` - Ocean depths
268
+ - `hot` - Black-red-yellow-white
269
+ - `cool` - Cyan to magenta
270
+ - `gray` - Grayscale
271
+ - `bone` - Blue-tinted grayscale
272
+
273
+ ### Custom Colors
274
+
275
+ ```typescript
276
+ // Use an array of colors
277
+ const colorbar = new Colorbar({
278
+ colormap: ['#0000ff', '#00ff00', '#ffff00', '#ff0000'],
279
+ vmin: 0,
280
+ vmax: 100,
281
+ });
282
+
283
+ // Or use color stops for precise control
284
+ const colorbar = new Colorbar({
285
+ colorStops: [
286
+ { position: 0, color: '#0000ff' },
287
+ { position: 0.3, color: '#00ff00' },
288
+ { position: 0.7, color: '#ffff00' },
289
+ { position: 1, color: '#ff0000' },
290
+ ],
291
+ vmin: 0,
292
+ vmax: 100,
293
+ });
294
+ ```
295
+
296
+ ## React Hooks
297
+
298
+ ```typescript
299
+ import { useColorbar, useLegend, useHtmlControl } from 'maplibre-gl-components/react';
300
+
301
+ function MyComponent() {
302
+ const colorbar = useColorbar({ colormap: 'viridis', vmin: 0, vmax: 100 });
303
+ const legend = useLegend({ items: [...] });
304
+ const htmlControl = useHtmlControl({ html: '...' });
305
+
306
+ return (
307
+ <>
308
+ <button onClick={() => colorbar.setColormap('plasma')}>
309
+ Change Colormap
310
+ </button>
311
+ <button onClick={() => legend.toggle()}>
312
+ Toggle Legend
313
+ </button>
314
+ <button onClick={() => htmlControl.setHtml('<div>Updated!</div>')}>
315
+ Update HTML
316
+ </button>
317
+
318
+ <ColorbarReact
319
+ map={map}
320
+ {...colorbar.state}
321
+ vmin={colorbar.state.vmin}
322
+ vmax={colorbar.state.vmax}
323
+ />
324
+ </>
325
+ );
326
+ }
327
+ ```
328
+
329
+ ## Styling
330
+
331
+ The default styles can be customized using CSS:
332
+
333
+ ```css
334
+ /* Override colorbar styles */
335
+ .maplibre-gl-colorbar {
336
+ background: rgba(0, 0, 0, 0.8);
337
+ color: white;
338
+ }
339
+
340
+ /* Override legend styles */
341
+ .maplibre-gl-legend {
342
+ font-size: 14px;
343
+ border-radius: 8px;
344
+ }
345
+
346
+ /* Override HTML control styles */
347
+ .maplibre-gl-html-control {
348
+ max-width: 400px;
349
+ }
350
+ ```
351
+
352
+ ## Examples
353
+
354
+ See the [examples](./examples/) directory for complete working examples:
355
+
356
+ - **Basic Example** - Vanilla TypeScript with all three components
357
+ - **React Example** - React with hooks and dynamic updates
358
+
359
+ ## Development
360
+
361
+ ```bash
362
+ # Install dependencies
363
+ npm install
364
+
365
+ # Start development server
366
+ npm run dev
367
+
368
+ # Run tests
369
+ npm test
370
+
371
+ # Build for production
372
+ npm run build
373
+
374
+ # Build examples
375
+ npm run build:examples
376
+ ```
377
+
378
+ ## License
379
+
380
+ MIT License - see [LICENSE](./LICENSE) for details.