Installation
Package Manager Installation
Vue3 MapLibre GL is available on npm and can be installed using your preferred package manager.
Every command below installs two packages, because maplibre-gl is a peer dependency since v6. npm and Bun would pull it in on their own, but Yarn and pnpm would not, and naming it explicitly is the one command that is correct everywhere — it also pins the MapLibre version your app runs against.
Why a peer dependency
This package re-exports MapLibre's own classes and types, and your app imports MapLibre's stylesheet directly. If both your app and this package resolved their own copy of maplibre-gl, a Map produced by one would fail an instanceof check in the other and two copies of the runtime would ship. Declaring it as a peer means there is exactly one, on a version you choose.
Since v6 the two stylesheets are separate: this package ships only its own rules, and you import MapLibre's own stylesheet the way MapLibre documents it. A combined dist/style-with-maplibre.css is published for apps that would rather import one file. See Stylesheets.
pnpm
pnpm's isolated node_modules does not expose a dependency your app did not install itself, so import 'maplibre-gl/dist/maplibre-gl.css' fails unless maplibre-gl is in your own package.json. This has been true since v6 split the stylesheets, independently of the peer dependency. Importing vue3-maplibre-gl/dist/style-with-maplibre.css sidesteps it, since that specifier resolves inside this package.
bun add vue3-maplibre-gl maplibre-glnpm install vue3-maplibre-gl maplibre-glyarn add vue3-maplibre-gl maplibre-glpnpm add vue3-maplibre-gl maplibre-glCDN Installation
You can also use Vue MapLibre GL directly from a CDN.
For the UMD build, load the global maplibregl script first: maplibre-gl is externalized there, exactly as it is for a package-manager install.
Pin the majors rather than @latest. maplibre-gl@latest now resolves to v6, which is outside this package's ^5.6.1 peer range and no longer ships dist/maplibre-gl.js at all, so the tag silently 404s.
<script src="https://unpkg.com/maplibre-gl@5/dist/maplibre-gl.js"></script>
<script src="https://unpkg.com/vue3-maplibre-gl@6/dist/index.umd.cjs"></script>
<link
href="https://unpkg.com/maplibre-gl@5/dist/maplibre-gl.css"
rel="stylesheet"
/>
<link
href="https://unpkg.com/vue3-maplibre-gl@6/dist/style.css"
rel="stylesheet"
/>Stylesheets
The build externalises MapLibre entirely, so dist/style.css carries only this package's own rules — the map container's sizing. MapLibre's controls, popups and markers are styled by MapLibre's own stylesheet, and omitting it produces an unstyled map rather than an error.
dist/style-with-maplibre.css is MapLibre's stylesheet followed by this package's, so one import covers both:
import 'vue3-maplibre-gl/dist/style-with-maplibre.css';Import dist/style.css instead when your app already loads maplibre-gl/dist/maplibre-gl.css — through another map library, a shared stylesheet, or a <link> tag — so that ~69KB is not shipped twice:
import 'maplibre-gl/dist/maplibre-gl.css';
import 'vue3-maplibre-gl/dist/style.css';Never import both style-with-maplibre.css and maplibre-gl.css; the second copy wins on identical rules and changes nothing, but it doubles the CSS payload.
Setup in Vue 3
Global Registration
Register the components globally in your main.js:
import { createApp } from 'vue';
import VueMapLibreGl from 'vue3-maplibre-gl';
import 'maplibre-gl/dist/maplibre-gl.css';
import 'vue3-maplibre-gl/dist/style.css';
const app = createApp(App);
app.use(VueMapLibreGl);
app.mount('#app');Local Registration (Recommended)
Import components as needed in your components for better tree-shaking:
<script setup>
import {
Maplibre,
GeoJsonSource,
FillLayer,
CircleLayer,
Marker,
Popup,
} from 'vue3-maplibre-gl';
import 'maplibre-gl/dist/maplibre-gl.css';
import 'vue3-maplibre-gl/dist/style.css';
</script>Available Components
All components are exported from the main package:
import {
// Main Components
Maplibre,
GeoJsonSource,
// Layer Components
FillLayer,
CircleLayer,
LineLayer,
SymbolLayer,
// Interactive Components
Marker,
Popup,
// Utility Components
Image,
GeolocateControls,
// Composables
useCreateMaplibre,
useMaplibre,
useCreateGeoJsonSource,
useGeoJsonSource,
useCreateFillLayer,
useCreateCircleLayer,
useCreateLineLayer,
useCreateSymbolLayer,
useGeolocateControl,
useMapEventListener,
useLayerEventListener,
useFlyTo,
useEaseTo,
useJumpTo,
useFitBounds,
useCameraForBounds,
useZoomTo,
useZoomIn,
useZoomOut,
useLogger,
} from 'vue3-maplibre-gl';TypeScript Support
Vue MapLibre GL includes full TypeScript support. If you're using TypeScript, you'll get automatic type checking and IntelliSense support.
Type Definitions
The package includes comprehensive type definitions for:
- All component props and events
- MapLibre GL JS types
- Composable return types
- Configuration options
Example with TypeScript
<script setup lang="ts">
import { ref } from 'vue';
import { Maplibre, GeoJsonSource, FillLayer } from 'vue3-maplibre-gl';
import type {
LngLatLike,
StyleSpecification,
FillLayerStyle,
GeoJSONSourceSpecification,
} from 'vue3-maplibre-gl';
const center = ref<LngLatLike>([0, 0]);
const mapStyle = ref<string | StyleSpecification>(
'https://demotiles.maplibre.org/style.json',
);
const geoJsonData = ref<GeoJSONSourceSpecification['data']>({
type: 'FeatureCollection',
features: [],
});
const fillStyle = ref<FillLayerStyle>({
'fill-color': '#088',
'fill-opacity': 0.8,
});
</script>Type Definitions
Vue3 MapLibre GL exports comprehensive TypeScript definitions:
Component prop types are not exported. Each component declares its props interface locally, so MaplibreProps, FillLayerProps and the rest cannot be imported — use defineProps inference in your own wrapper, or read the shapes in the components API reference.
What is exported:
// Style Types
import type {
FillLayerStyle,
CircleLayerStyle,
LineLayerStyle,
SymbolLayerStyle,
} from 'vue3-maplibre-gl';
// Composable Types
import type {
CreateMaplibreActions,
CreateGeoJsonSourceActions,
CreateLayerActions,
} from 'vue3-maplibre-gl';
// Re-exported MapLibre GL Types
import type {
Map,
LngLat,
LngLatLike,
MapOptions,
StyleSpecification,
GeoJSONSourceSpecification,
} from 'vue3-maplibre-gl';Raw MapLibre GL classes come from the /maplibre subpath rather than the root. Keeping them off the root is what lets a bundler drop the MapLibre runtime when you only use components:
import {
Map,
NavigationControl,
GeolocateControl,
MaplibreMarker,
} from 'vue3-maplibre-gl/maplibre';Marker and Popup are already used by Vue components, so the raw MapLibre GL classes are available as MaplibreMarker, MaplibrePopup, or under the maplibregl namespace:
import { MaplibrePopup, maplibregl } from 'vue3-maplibre-gl/maplibre';
const popup = new MaplibrePopup();
const marker = new maplibregl.Marker();Importing them directly from maplibre-gl works just as well.
Vite Configuration
If you're using Vite, you might need to add some configuration for optimal performance:
// vite.config.js
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
export default defineConfig({
plugins: [vue()],
optimizeDeps: {
include: ['maplibre-gl'],
},
});Webpack Configuration
For Webpack users, you might need to configure module resolution:
// webpack.config.js
module.exports = {
resolve: {
alias: {
'maplibre-gl': 'maplibre-gl/dist/maplibre-gl.js',
},
},
};Nuxt 3 Setup
For Nuxt 3 applications, create a plugin:
// plugins/vue-maplibre-gl.client.js
import VueMapLibreGl from 'vue3-maplibre-gl';
import 'maplibre-gl/dist/maplibre-gl.css';
import 'vue3-maplibre-gl/dist/style.css';
export default defineNuxtPlugin((nuxtApp) => {
nuxtApp.vueApp.use(VueMapLibreGl);
});Troubleshooting
Common Issues
- CSS not loading: Import
vue3-maplibre-gl/dist/style-with-maplibre.css, or bothmaplibre-gl/dist/maplibre-gl.cssandvue3-maplibre-gl/dist/style.css. See Stylesheets. - Module not found: Reinstall
vue3-maplibre-glso itsmaplibre-gldependency is present innode_modules - TypeScript errors: Update your TypeScript configuration to include the package types
Browser Compatibility
Vue MapLibre GL supports all modern browsers that support:
- ES6+ features
- WebGL
- Vue 3
Minimum browser versions:
- Chrome 51+
- Firefox 53+
- Safari 10+
- Edge 79+