2008-08-06 02:13:06 +08:00
|
|
|
from django.contrib.admin import ModelAdmin
|
|
|
|
from django.contrib.gis.admin.widgets import OpenLayersWidget
|
|
|
|
from django.contrib.gis.db import models
|
2016-06-14 22:18:33 +08:00
|
|
|
from django.contrib.gis.gdal import OGRGeomType
|
2015-04-25 00:16:40 +08:00
|
|
|
|
|
|
|
spherical_mercator_srid = 3857
|
2008-08-06 02:13:06 +08:00
|
|
|
|
2013-11-03 01:18:46 +08:00
|
|
|
|
2008-08-06 02:13:06 +08:00
|
|
|
class GeoModelAdmin(ModelAdmin):
|
|
|
|
"""
|
|
|
|
The administration options class for Geographic models. Map settings
|
|
|
|
may be overloaded from their defaults to create custom maps.
|
|
|
|
"""
|
|
|
|
# The default map settings that may be overloaded -- still subject
|
|
|
|
# to API changes.
|
|
|
|
default_lon = 0
|
|
|
|
default_lat = 0
|
|
|
|
default_zoom = 4
|
|
|
|
display_wkt = False
|
|
|
|
display_srid = False
|
|
|
|
extra_js = []
|
|
|
|
num_zoom = 18
|
|
|
|
max_zoom = False
|
|
|
|
min_zoom = False
|
|
|
|
units = False
|
|
|
|
max_resolution = False
|
|
|
|
max_extent = False
|
|
|
|
modifiable = True
|
|
|
|
mouse_position = True
|
|
|
|
scale_text = True
|
|
|
|
layerswitcher = True
|
|
|
|
scrollable = True
|
|
|
|
map_width = 600
|
|
|
|
map_height = 400
|
|
|
|
map_srid = 4326
|
|
|
|
map_template = 'gis/admin/openlayers.html'
|
2016-08-10 23:13:08 +08:00
|
|
|
openlayers_url = 'https://cdnjs.cloudflare.com/ajax/libs/openlayers/2.13.1/OpenLayers.js'
|
2009-04-26 14:01:59 +08:00
|
|
|
point_zoom = num_zoom - 6
|
2012-03-18 04:13:06 +08:00
|
|
|
wms_url = 'http://vmap0.tiles.osgeo.org/wms/vmap0'
|
2008-08-06 02:13:06 +08:00
|
|
|
wms_layer = 'basic'
|
|
|
|
wms_name = 'OpenLayers WMS'
|
2012-05-26 03:00:44 +08:00
|
|
|
wms_options = {'format': 'image/jpeg'}
|
2008-08-06 02:13:06 +08:00
|
|
|
debug = False
|
|
|
|
widget = OpenLayersWidget
|
|
|
|
|
2011-09-10 11:04:30 +08:00
|
|
|
@property
|
|
|
|
def media(self):
|
2008-08-06 02:13:06 +08:00
|
|
|
"Injects OpenLayers JavaScript into the admin."
|
2017-01-21 21:13:44 +08:00
|
|
|
media = super().media
|
2008-08-06 02:13:06 +08:00
|
|
|
media.add_js([self.openlayers_url])
|
|
|
|
media.add_js(self.extra_js)
|
|
|
|
return media
|
|
|
|
|
2015-12-24 23:25:59 +08:00
|
|
|
def formfield_for_dbfield(self, db_field, request, **kwargs):
|
2008-08-06 02:13:06 +08:00
|
|
|
"""
|
|
|
|
Overloaded from ModelAdmin so that an OpenLayersWidget is used
|
2012-09-22 02:22:54 +08:00
|
|
|
for viewing/editing 2D GeometryFields (OpenLayers 2 does not support
|
|
|
|
3D editing).
|
2008-08-06 02:13:06 +08:00
|
|
|
"""
|
2012-09-22 02:22:54 +08:00
|
|
|
if isinstance(db_field, models.GeometryField) and db_field.dim < 3:
|
2008-08-06 02:13:06 +08:00
|
|
|
# Setting the widget with the newly defined widget.
|
|
|
|
kwargs['widget'] = self.get_map_widget(db_field)
|
|
|
|
return db_field.formfield(**kwargs)
|
|
|
|
else:
|
2017-01-21 21:13:44 +08:00
|
|
|
return super().formfield_for_dbfield(db_field, request, **kwargs)
|
2008-08-06 02:13:06 +08:00
|
|
|
|
|
|
|
def get_map_widget(self, db_field):
|
|
|
|
"""
|
2017-01-25 04:31:57 +08:00
|
|
|
Return a subclass of the OpenLayersWidget (or whatever was specified
|
2010-04-17 00:34:42 +08:00
|
|
|
in the `widget` attribute) using the settings from the attributes set
|
2008-08-06 02:13:06 +08:00
|
|
|
in this class.
|
|
|
|
"""
|
2009-04-25 04:34:48 +08:00
|
|
|
is_collection = db_field.geom_type in ('MULTIPOINT', 'MULTILINESTRING', 'MULTIPOLYGON', 'GEOMETRYCOLLECTION')
|
2008-08-06 02:13:06 +08:00
|
|
|
if is_collection:
|
2013-10-17 16:17:41 +08:00
|
|
|
if db_field.geom_type == 'GEOMETRYCOLLECTION':
|
|
|
|
collection_type = 'Any'
|
|
|
|
else:
|
|
|
|
collection_type = OGRGeomType(db_field.geom_type.replace('MULTI', ''))
|
2008-08-06 02:13:06 +08:00
|
|
|
else:
|
|
|
|
collection_type = 'None'
|
|
|
|
|
|
|
|
class OLMap(self.widget):
|
2016-12-28 06:00:56 +08:00
|
|
|
template_name = self.map_template
|
2009-04-25 04:34:48 +08:00
|
|
|
geom_type = db_field.geom_type
|
2012-05-26 03:00:44 +08:00
|
|
|
|
|
|
|
wms_options = ''
|
|
|
|
if self.wms_options:
|
|
|
|
wms_options = ["%s: '%s'" % pair for pair in self.wms_options.items()]
|
|
|
|
wms_options = ', %s' % ', '.join(wms_options)
|
|
|
|
|
2013-10-27 09:27:42 +08:00
|
|
|
params = {'default_lon': self.default_lon,
|
|
|
|
'default_lat': self.default_lat,
|
|
|
|
'default_zoom': self.default_zoom,
|
|
|
|
'display_wkt': self.debug or self.display_wkt,
|
|
|
|
'geom_type': OGRGeomType(db_field.geom_type),
|
|
|
|
'field_name': db_field.name,
|
|
|
|
'is_collection': is_collection,
|
|
|
|
'scrollable': self.scrollable,
|
|
|
|
'layerswitcher': self.layerswitcher,
|
|
|
|
'collection_type': collection_type,
|
|
|
|
'is_generic': db_field.geom_type == 'GEOMETRY',
|
|
|
|
'is_linestring': db_field.geom_type in ('LINESTRING', 'MULTILINESTRING'),
|
|
|
|
'is_polygon': db_field.geom_type in ('POLYGON', 'MULTIPOLYGON'),
|
|
|
|
'is_point': db_field.geom_type in ('POINT', 'MULTIPOINT'),
|
|
|
|
'num_zoom': self.num_zoom,
|
|
|
|
'max_zoom': self.max_zoom,
|
|
|
|
'min_zoom': self.min_zoom,
|
|
|
|
'units': self.units, # likely should get from object
|
|
|
|
'max_resolution': self.max_resolution,
|
|
|
|
'max_extent': self.max_extent,
|
|
|
|
'modifiable': self.modifiable,
|
|
|
|
'mouse_position': self.mouse_position,
|
|
|
|
'scale_text': self.scale_text,
|
|
|
|
'map_width': self.map_width,
|
|
|
|
'map_height': self.map_height,
|
|
|
|
'point_zoom': self.point_zoom,
|
|
|
|
'srid': self.map_srid,
|
|
|
|
'display_srid': self.display_srid,
|
|
|
|
'wms_url': self.wms_url,
|
|
|
|
'wms_layer': self.wms_layer,
|
|
|
|
'wms_name': self.wms_name,
|
|
|
|
'wms_options': wms_options,
|
|
|
|
'debug': self.debug,
|
2008-08-06 02:13:06 +08:00
|
|
|
}
|
|
|
|
return OLMap
|
|
|
|
|
2011-03-16 10:58:35 +08:00
|
|
|
|
2015-04-25 00:16:40 +08:00
|
|
|
class OSMGeoAdmin(GeoModelAdmin):
|
|
|
|
map_template = 'gis/admin/osm.html'
|
|
|
|
num_zoom = 20
|
|
|
|
map_srid = spherical_mercator_srid
|
|
|
|
max_extent = '-20037508,-20037508,20037508,20037508'
|
|
|
|
max_resolution = '156543.0339'
|
|
|
|
point_zoom = num_zoom - 6
|
|
|
|
units = 'm'
|