Skip to content

Instantly share code, notes, and snippets.

@cigzigwon
Created August 19, 2021 20:14
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save cigzigwon/905a65e6670101b67bfc2ee4151dee2b to your computer and use it in GitHub Desktop.
Save cigzigwon/905a65e6670101b67bfc2ee4151dee2b to your computer and use it in GitHub Desktop.
React useMapbox hook in ES6
import mapboxgl from 'mapbox-gl/dist/mapbox-gl-csp'
import MapboxWorker from 'worker-loader!mapbox-gl/dist/mapbox-gl-csp-worker' // Load worker code separately with worker-loader
import 'mapbox-gl/dist/mapbox-gl.css'
export const useMapbox = (opts) => {
mapboxgl.workerClass = MapboxWorker
mapboxgl.accessToken = "public/private access token"
const init = (sources) => {
const [poisA, poisB, poisC] = sources
const map = new mapboxgl.Map(opts)
map.on('load', () => {
// defaults for map load event
})
// add any other default event handlers for map (operate on sources)
return map
}
return init
}
@cigzigwon
Copy link
Author

cigzigwon commented Aug 19, 2021

Then here's how you use it...
const init_mapbox = useMapbox({ container: 'mapbox-container', style: 'mapbox://styles/mapbox/bright-v9', bounds: COORD_SET.dist1, boxZoom: false, dragPan: false, dragRotate: false, doubleClickZoom: false, keyboard: false, scrollZoom: false, touchZoomRotate: false }) const [map, set_map] = useState(null) const [geojson, set_geojson] = useState([])

@cigzigwon
Copy link
Author

cigzigwon commented Aug 19, 2021

And that way when the states change you can prescribe useEffect to make an updates to the 'map' constant that gets passed back by the iniitializer. This should be decalred in a useEffect wrapper so that the map gets set but doesn't have to be. It can just be the passed as the original inititlaizer and it will only run once.
useEffect(() => set_map(!map && geojson.length ? init_mapbox(geojson) : null)) OR const [map, set_map] = useState(() => init_mapbox(geojson))

@cigzigwon
Copy link
Author

You could also chain your custom handlers per view...
const [map, set_map] = useState(() => { return init_mapbox(geojson).on('idle', () => {}) .on('click', 'yellow-fill', handle_click) .on('click', 'poi-default', handle_click) .on('touchstart', 'yellow-fill', handle_click) .on('touchstart', 'poi-default', handle_click) })
``

@kelvindecosta
Copy link

Thank you for such a detailed breakdown of the code!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment