Skip to content

Commit

Permalink
Rename the conditional maps config variable
Browse files Browse the repository at this point in the history
Previously the Flask app config option `FLASK_ADMIN_MAPBOX_MAP_ID` was
required to enable map widgets, even if MapBox wasn't being used.

Let's clear up this confusion by having a clearer config name for
toggling maps on/off: `FLASK_ADMIN_MAPS`.

And then finally update the documentation around maps to talk about this
new configuration, and also talk about how to override the default
MapBox integration.

Finally, we update the geoalchemy example app to have some pages use the
default MapBox integration and some use OSM instead.
  • Loading branch information
samuelhwilliams committed Jul 23, 2024
1 parent 7bf6b72 commit 40ad805
Show file tree
Hide file tree
Showing 7 changed files with 55 additions and 33 deletions.
33 changes: 23 additions & 10 deletions doc/advanced.rst
Original file line number Diff line number Diff line change
Expand Up @@ -273,27 +273,40 @@ Some of the Geometry field types that are available include:
Have a look at https://github.com/flask-admin/flask-admin/tree/master/examples/geo_alchemy
to get started.

Loading Tiles From Mapbox
*************************
Display map widgets
*******************

Flask-Admin uses `Leaflet <https://leafletjs.com/>`_ to display map widgets for
geographical data. By default, this uses `MapBox <https://www.mapbox.com>`_.

To have map data display correctly, you'll have to sign up for an account at https://www.mapbox.com/
and include some credentials in your application's config::
To have MapBox data display correctly, you'll have to sign up for an account and include
some credentials in your application's config::

app = Flask(__name__)
app.config['FLASK_ADMIN_MAPS'] = True

# Required: configure the default centre position for blank maps
app.config['FLASK_ADMIN_DEFAULT_CENTER_LAT'] = -33.918861
app.config['FLASK_ADMIN_DEFAULT_CENTER_LONG'] = 18.423300

# Required if using the default Mapbox integration
app.config['FLASK_ADMIN_MAPBOX_MAP_ID'] = "example.abc123"
app.config['FLASK_ADMIN_MAPBOX_ACCESS_TOKEN'] = "pk.def456"
app.config['FLASK_ADMIN_DEFAULT_CENTER_LAT'] = -33.918861 # Replace with your own value
app.config['FLASK_ADMIN_DEFAULT_CENTER_LONG'] = 18.423300 # Replace with your own value

Leaflet supports loading map tiles from any arbitrary map tile provider, but
at the moment, Flask-Admin only supports Mapbox. If you want to use other
providers, make a pull request!
If you want to use a map provider other than MapBox (eg OpenStreetMaps), you can override
the tile layer URLs and tile attribution attributes::

class CityView(ModelView):
tile_layer_url = '{s}.tile.openstreetmap.org/{z}/{x}/{y}.png'
tile_layer_attribution = '&copy; <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors'

If you want to include a search box on map widgets for looking up locations, you need the following additional configuration::

app.config['FLASK_ADMIN_MAPBOX_SEARCH'] = True
app.config['FLASK_ADMIN_MAPS_SEARCH'] = True
app.config['FLASK_ADMIN_GOOGLE_MAPS_API_KEY'] = 'secret'

Flask-Admin currently only supports Google Maps for map search.

Limitations
***********

Expand Down
19 changes: 12 additions & 7 deletions examples/geo_alchemy/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,16 +61,21 @@ def index():
admin = admin.Admin(app, name='Example: GeoAlchemy', theme=Bootstrap4Theme())


class ModalModelView(ModelView):
class LeafletModelView(ModelView):
edit_modal = True


class OSMModelView(ModelView):
tile_layer_url = '{s}.tile.openstreetmap.org/{z}/{x}/{y}.png'
tile_layer_attribution = '&copy; <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors'

# Add views
admin.add_view(ModalModelView(Point, db.session, category='Points'))
admin.add_view(ModalModelView(MultiPoint, db.session, category='Points'))
admin.add_view(ModalModelView(Polygon, db.session, category='Polygons'))
admin.add_view(ModalModelView(MultiPolygon, db.session, category='Polygons'))
admin.add_view(ModalModelView(LineString, db.session, category='Lines'))
admin.add_view(ModalModelView(MultiLineString, db.session, category='Lines'))
admin.add_view(LeafletModelView(Point, db.session, category='Points'))
admin.add_view(OSMModelView(MultiPoint, db.session, category='Points'))
admin.add_view(LeafletModelView(Polygon, db.session, category='Polygons'))
admin.add_view(OSMModelView(MultiPolygon, db.session, category='Polygons'))
admin.add_view(LeafletModelView(LineString, db.session, category='Lines'))
admin.add_view(OSMModelView(MultiLineString, db.session, category='Lines'))

if __name__ == '__main__':

Expand Down
3 changes: 2 additions & 1 deletion examples/geo_alchemy/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,13 @@
SQLALCHEMY_ECHO = True

# credentials for loading map tiles from mapbox
FLASK_ADMIN_MAPS = True
FLASK_ADMIN_MAPS_SEARCH = False
FLASK_ADMIN_MAPBOX_MAP_ID = 'light-v10' # example map id
FLASK_ADMIN_MAPBOX_ACCESS_TOKEN = '...'

# when the creating new shapes, use this default map center
FLASK_ADMIN_DEFAULT_CENTER_LAT = -33.918861
FLASK_ADMIN_DEFAULT_CENTER_LONG = 18.423300

FLASK_ADMIN_MAPBOX_SEARCH = True
FLASK_ADMIN_GOOGLE_MAPS_API_KEY = '...'
6 changes: 3 additions & 3 deletions flask_admin/static/admin/js/form.js
Original file line number Diff line number Diff line change
Expand Up @@ -74,8 +74,8 @@
* Process Leaflet (map) widget
*/
function processLeafletWidget($el, name) {
if (!window.FLASK_ADMIN_MAPBOX_MAP_ID) {
console.error("You must set FLASK_ADMIN_MAPBOX_MAP_ID in your Flask settings to use the map widget");
if (!window.FLASK_ADMIN_MAPS) {
console.error("You must set FLASK_ADMIN_MAPS in your Flask settings to use the map widget");
return false;
}
if (!window.FLASK_ADMIN_DEFAULT_CENTER_LAT || !window.FLASK_ADMIN_DEFAULT_CENTER_LONG) {
Expand Down Expand Up @@ -201,7 +201,7 @@
}
var drawControl = new L.Control.Draw(drawOptions);
map.addControl(drawControl);
if (window.FLASK_ADMIN_MAPBOX_SEARCH) {
if (window.FLASK_ADMIN_MAPS_SEARCH) {
var circle = L.circleMarker([0, 0]);
var $autocompleteEl = $('<input style="position: absolute; z-index: 9999; display: block; margin: -42px 0 0 10px; width: 50%">');
var $form = $($el.get(0).form);
Expand Down
9 changes: 5 additions & 4 deletions flask_admin/templates/bootstrap2/admin/lib.html
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,7 @@ <h3>{{ text }}</h3>
{% macro form_css() %}
<link href="{{ admin_static.url(filename='vendor/select2/select2.css', v='3.5.2') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/bootstrap-daterangepicker/daterangepicker-bs2.css', v='1.3.22') }}" rel="stylesheet">
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.css', v='1.0.2') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.css', v='0.4.6') }}" rel="stylesheet">
{% endif %}
Expand All @@ -228,8 +228,9 @@ <h3>{{ text }}</h3>
{% endmacro %}

{% macro form_js() %}
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<script>
window.FLASK_ADMIN_MAPS = true;
window.FLASK_ADMIN_MAPBOX_MAP_ID = "{{ config.FLASK_ADMIN_MAPBOX_MAP_ID }}";
{% if config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN %}
window.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN = "{{ config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN }}";
Expand All @@ -241,9 +242,9 @@ <h3>{{ text }}</h3>
</script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.js', v='1.0.2') }}"></script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.js', v='0.4.6') }}"></script>
{% if config.FLASK_ADMIN_MAPBOX_SEARCH %}
{% if config.FLASK_ADMIN_MAPS_SEARCH %}
<script>
window.FLASK_ADMIN_MAPBOX_SEARCH = "{{ config.FLASK_ADMIN_MAPBOX_SEARCH }}";
window.FLASK_ADMIN_MAPS_SEARCH = "{{ config.FLASK_ADMIN_MAPS_SEARCH }}";
</script>
<script src="https://maps.googleapis.com/maps/api/js?v=3&libraries=places&key={{ config.get('FLASK_ADMIN_GOOGLE_MAPS_API_KEY') }}"></script>
{% endif %}
Expand Down
9 changes: 5 additions & 4 deletions flask_admin/templates/bootstrap3/admin/lib.html
Original file line number Diff line number Diff line change
Expand Up @@ -209,7 +209,7 @@ <h3>{{ text }}</h3>
<link href="{{ admin_static.url(filename='vendor/select2/select2.css', v='3.5.2') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/select2/select2-bootstrap3.css', v='1.4.6') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/bootstrap-daterangepicker/daterangepicker-bs3.css', v='1.3.22') }}" rel="stylesheet">
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.css', v='1.0.2') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.css', v='0.4.6') }}" rel="stylesheet">
{% endif %}
Expand All @@ -219,8 +219,9 @@ <h3>{{ text }}</h3>
{% endmacro %}

{% macro form_js() %}
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<script>
window.FLASK_ADMIN_MAPS = true;
window.FLASK_ADMIN_MAPBOX_MAP_ID = "{{ config.FLASK_ADMIN_MAPBOX_MAP_ID }}";
{% if config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN %}
window.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN = "{{ config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN }}";
Expand All @@ -232,9 +233,9 @@ <h3>{{ text }}</h3>
</script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.js', v='1.0.2') }}"></script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.js', v='0.4.6') }}"></script>
{% if config.FLASK_ADMIN_MAPBOX_SEARCH %}
{% if config.FLASK_ADMIN_MAPS_SEARCH %}
<script>
window.FLASK_ADMIN_MAPBOX_SEARCH = "{{ config.FLASK_ADMIN_MAPBOX_SEARCH }}";
window.FLASK_ADMIN_MAPS_SEARCH = "{{ config.FLASK_ADMIN_MAPS_SEARCH }}";
</script>
<script src="https://maps.googleapis.com/maps/api/js?v=3&libraries=places&key={{ config.get('FLASK_ADMIN_GOOGLE_MAPS_API_KEY') }}"></script>
{% endif %}
Expand Down
9 changes: 5 additions & 4 deletions flask_admin/templates/bootstrap4/admin/lib.html
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ <h3>{{ text }}</h3>
<link href="{{ admin_static.url(filename='vendor/select2/select2.css', v='4.2.1') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/select2/select2-bootstrap4.css', v='1.4.6') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/bootstrap-daterangepicker/daterangepicker-bs4.css', v='1.3.22') }}" rel="stylesheet">
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.css', v='1.0.2') }}" rel="stylesheet">
<link href="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.css', v='0.4.6') }}" rel="stylesheet">
{% endif %}
Expand All @@ -257,8 +257,9 @@ <h3>{{ text }}</h3>
{% endmacro %}

{% macro form_js() %}
{% if config.FLASK_ADMIN_MAPBOX_MAP_ID %}
{% if config.FLASK_ADMIN_MAPS %}
<script>
window.FLASK_ADMIN_MAPS = true;
window.FLASK_ADMIN_MAPBOX_MAP_ID = "{{ config.FLASK_ADMIN_MAPBOX_MAP_ID }}";
{% if config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN %}
window.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN = "{{ config.FLASK_ADMIN_MAPBOX_ACCESS_TOKEN }}";
Expand All @@ -270,9 +271,9 @@ <h3>{{ text }}</h3>
</script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.js', v='1.0.2') }}"></script>
<script src="{{ admin_static.url(filename='vendor/leaflet/leaflet.draw.js', v='0.4.6') }}"></script>
{% if config.FLASK_ADMIN_MAPBOX_SEARCH %}
{% if config.FLASK_ADMIN_MAPS_SEARCH %}
<script>
window.FLASK_ADMIN_MAPBOX_SEARCH = "{{ config.FLASK_ADMIN_MAPBOX_SEARCH }}";
window.FLASK_ADMIN_MAPS_SEARCH = "{{ config.FLASK_ADMIN_MAPS_SEARCH }}";
</script>
<script src="https://maps.googleapis.com/maps/api/js?v=3&libraries=places&key={{ config.get('FLASK_ADMIN_GOOGLE_MAPS_API_KEY') }}"></script>
{% endif %}
Expand Down

0 comments on commit 40ad805

Please sign in to comment.