mapbox-gl-leaflet: putting a Mapbox GL layer inside a Leaflet map
binding from Mapbox GL JS to the Leaflet API
At a glance
- What is it?
- mapbox-gl-leaflet is a binding that lets a Leaflet map host a Mapbox GL JS layer, so Leaflet plugins and markers keep working alongside vector tiles. It is explicitly experimental, it is not supported by Mapbox, and it costs you rotation, pitch and input responsiveness.
- Who is it for?
- Adopt mapbox-gl-leaflet if you already have a Leaflet map with plugins, markers and popups and need a Mapbox GL vector layer on top of it without rewriting the app. Do not adopt it for a new map, for anything needing rotation or pitch, or as a base for production work, because the project states it is experimental and not actively supported by Mapbox, and the last published version was v0.0.16 in 2023.
- Can I use it commercially?
- Yes. ISC is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 128 days ago.
- What is it written in?
- Mainly JavaScript, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.
Editorial analysis
A Leaflet map with a Mapbox GL layer behind it
mapbox-gl-leaflet is a binding from Mapbox GL JS to the Leaflet API. The problem it addresses is concrete: Leaflet is everywhere in existing applications, with a large plugin ecosystem, while Mapbox GL JS is where vector tile rendering and 3D-capable styles live. Rewriting a Leaflet application to move to Mapbox GL JS is a large piece of work, and this binding avoids most of it.
The mechanism is a Leaflet layer. You create a Leaflet map as usual, and then add a layer created with L.mapboxGL, passing an access token and a style. The result is a Mapbox GL JS map instance living inside the Leaflet map container, behind the Leaflet layer stack. Markers, popups and any Leaflet plugin continue to work exactly as before, because they are still Leaflet objects.
The audience is developers with an existing Leaflet codebase that needs a Mapbox GL layer, or who want the Leaflet plugin ecosystem together with a Mapbox style. It is a bridge, not a general purpose map library, and the README is explicit that if you only need the mapbox-gl-js features, you are probably better off using that library directly.
The top of the README carries a note that this tool is experimental and not actively supported by Mapbox, with support handled through the repository's own issue tracker. That line is the first thing to read before planning around it.
Reaching the underlying mapbox-gl map object
Once the layer is added, the binding does not hide the Mapbox GL JS object from you. The README shows that the underlying mapbox-gl map object is reachable through a getter, and that you can add a source to that map directly:
gl.getMapboxMap()....
// add a source to the mapbox-gl layer
gl.getMapboxMap().addSource({...})This is the escape hatch that makes the binding practical rather than decorative. You get Leaflet for the plugin ecosystem and the map chrome, and you reach through to Mapbox GL JS whenever you need a capability that only exists there, such as manipulating sources or layers inside the GL map.
The main example shows the whole flow in one snippet, with a Leaflet map, a marker with a popup, and the GL layer added to the same map:
// replace with your Mapbox API Access token. Only include a token if you will be using Mapbox tiles.
var token ="pk.XXXX";
var map = L.map('map').setView([38.912753, -77.032194], 15);
L.marker([38.912753, -77.032194])
.bindPopup("Hello <b>Leaflet GL</b>!<br>Whoa, it works!")
.addTo(map)
.openPopup();
var gl = L.mapboxGL({
accessToken: token,
style: 'mapbox://styles/mapbox/bright-v8'
}).addTo(map);The token is only needed if you use Mapbox tiles. The README notes that you can use any vector tile source usable by mapbox-gl, and gives an example that points the style at a MapTiler style URL with your own key instead.
Script tags, since there is no bundler story
Installation is a matter of script tags. The README asks you to add a script tag referencing mapbox-gl-leaflet after adding Leaflet and mapbox-gl-js to your page, and the order matters, because the GL library and Leaflet both have to exist before the binding loads:
<!-- Leaflet -->
<link rel="stylesheet" href="leaflet.css" />
<script src="leaflet.js"></script>
<!-- Mapbox GL -->
<link href='https://api.tiles.mapbox.com/mapbox-gl-js/v1.5.0/mapbox-gl.css' rel='stylesheet' />
<script src='https://api.tiles.mapbox.com/mapbox-gl-js/v1.5.0/mapbox-gl.js'></script>
<script src="leaflet-mapbox-gl.js"></script>The binding file itself is leaflet-mapbox-gl.js, which is also the main entry in package.json. A CDN route is documented too, through Unpkg:
<script src="https://unpkg.com/mapbox-gl-leaflet/leaflet-mapbox-gl.js"></script>There is no bundler or framework integration documented, and no npm install instructions in the README. The package manifest lists leaflet ^1.0.0 and mapbox-gl as peer dependencies, which is the packaging-level way of saying the host application supplies both libraries.
For a first use, create a Mapbox account, copy the access token from the Mapbox Studio page, and note that the token starts with pk. Then create a Leaflet map, add the L.mapboxGL layer with the token and a style, and expect a Leaflet map with a Mapbox GL base layer, a marker and a working popup. There are four example files in the repository, basic.html, cluster.html, events.html and overlay.html, which are the fastest reference for a working setup.
No rotation, no pitch, and an event round trip
The README is unusually honest about the trade-off, and it names the two main differences between a pure mapbox-gl-js map and a Leaflet map using this binding.
The first is that there is no rotation, bearing or pitch support. Those three camera capabilities simply do not work through the binding. For a map application that wants a tilted three-dimensional city view or a rotating compass, this is not a setting to enable, it is a boundary of the approach.
The second is performance, and the mechanism behind it is what makes the limitation understandable. When using mapbox-gl-leaflet, mapbox-gl-js is set as not interactive. Leaflet receives the touch and mouse events and updates the mapbox-gl-js map behind the scenes, and because mapbox-gl-js does not redraw as fast as Leaflet, the map can seem slower. Every pan, zoom and gesture is therefore routed through a second rendering stack, and the GL side draws on its own schedule.
That design is what buys the Leaflet feature set in return. The binding lets you use all the Leaflet features and plugins, which is the point of the project. But the cost is paid on the interaction path, and it shows up most in a map where the user is constantly panning and zooming on a large display.
The note about the repository's own examples being the code to look at, with the cluster, events and overlay examples included, is also a hint about where the binding is least settled: clustered layers and event handling are exactly the areas where the two libraries' models disagree.
When plain mapbox-gl-js is the better tool
The alternative is not another binding, it is using Mapbox GL JS on its own, and the README says so directly. If all you need is the mapbox-gl-js feature set, adding a map with a mapbox-style, adding a GeoJSON layer and the rest, the project advises using that library directly instead of routing it through Leaflet.
The difference in approach is not a matter of taste. A pure Mapbox GL JS map is one rendering stack with one input path, which is why it can do rotation, bearing and pitch, and why it responds directly to gestures. A Leaflet map with this binding is two stacks, with Leaflet owning input and the GL map following. You get the Leaflet plugin ecosystem in exchange for the camera features and a layer of latency.
There is a middle path the README does not spell out but the API allows, since getMapboxMap() hands you the underlying map object. If you need a Mapbox GL style and camera control but also a couple of Leaflet behaviours, using Mapbox GL JS directly and reaching for Leaflet only where its plugins matter avoids paying the event round trip for every interaction on the map.
For a team starting fresh, the choice is clear. This binding is for code that already lives in Leaflet.
An ISC licence, a 0.0.x version and a jshint smoke test
The licence is ISC, stated in the README and set in package.json, which is a short permissive licence with no copyleft obligations on anyone embedding the binding. The project is a Mapbox repository, and the copyright line reads ISC © Mapbox.
The version number is where the caution belongs. The published releases are v0.0.16 from June 2023, v0.0.15 from May 2021 and v0.0.12 from March 2020, and the last push to the repository was on 2026-06-17. A package sitting at 0.0.x is announcing that its API may change without a compatibility promise, and the README's own banner, calling the tool experimental and not actively supported by Mapbox, points the same way.
The build and test story is correspondingly thin. The package has no build step at all, the main entry is a single file, leaflet-mapbox-gl.js, and the only script in package.json is a test that runs jshint over that file. A lint pass is not a test suite, so a change to the binding has no automated behavioural coverage behind it in this repository.
What that means for you is concrete. If you adopt it, you are taking ownership of the file. Fork it, keep your changes in it, and expect to fix problems yourself, because the maintainers state that support happens through the issue tracker rather than through Mapbox support channels.
Editorial conclusion
Adopt mapbox-gl-leaflet if you already have a Leaflet map with plugins, markers and popups and need a Mapbox GL vector layer on top of it without rewriting the app. Do not adopt it for a new map, for anything needing rotation or pitch, or as a base for production work, because the project states it is experimental and not actively supported by Mapbox, and the last published version was v0.0.16 in 2023. Verify first that your Leaflet version satisfies the peer dependency of leaflet ^1.0.0, that your mapbox-gl build accepts the style URL you pass, and that the layer you need is one the binding actually forwards.
Frequently asked questions
How do I add a Mapbox GL layer to a Leaflet map with mapbox-gl-leaflet?
Create a Leaflet map as usual, then create a layer with L.mapboxGL passing an accessToken and a style, and add it to the map. The underlying mapbox-gl map object is reachable with gl.getMapboxMap().
Does mapbox-gl-leaflet work without a Mapbox access token?
Yes, if you do not use Mapbox tiles. The README notes you can use any vector tile source usable by mapbox-gl, and gives an example pointing the style at a MapTiler style URL with your own key.
What are the limitations of mapbox-gl-leaflet compared with mapbox-gl-js?
There is no rotation, bearing or pitch support, and the map can feel slower because mapbox-gl-js is set as not interactive while Leaflet handles the touch and mouse events and updates the GL map behind the scenes.
How is mapbox-gl-leaflet installed in a web page?
Add Leaflet and mapbox-gl-js first with their own script and stylesheet tags, then add the binding script tag for leaflet-mapbox-gl.js after them. A CDN version is also published through Unpkg at https://unpkg.com/mapbox-gl-leaflet/leaflet-mapbox-gl.js.
Is mapbox-gl-leaflet actively supported?
The README states the tool is experimental and not actively supported by Mapbox, with support handled through the repository's issue tracker. The last published release was v0.0.16 in 2023 and the last push was on 2026-06-17.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/mapbox-mapbox-gl-leaflet)Was this useful?