Skip to content

Commit

Permalink
Merge pull request #17 from Skytek/wl/more-features
Browse files Browse the repository at this point in the history
Support for map resolution, viewport handling
  • Loading branch information
wlatanowicz authored Mar 1, 2024
2 parents 873f46e + af432fa commit d1ffb2a
Show file tree
Hide file tree
Showing 3 changed files with 37 additions and 3 deletions.
7 changes: 7 additions & 0 deletions generic_map_api/constants.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
from enum import Enum


class ViewportHandling(Enum):
TILES = "tiles"
SPLIT = "split"
SINGLE = "single"
16 changes: 14 additions & 2 deletions generic_map_api/values.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
from __future__ import annotations

import re

import geohash2
from shapely.geometry import Point, Polygon
from skytek_utils.spatial import tiles
Expand All @@ -8,6 +10,11 @@


class BaseViewPort:
def __init__(self) -> None:
self.size = None
self.meters_per_pixel = None
self.zoom = None

def to_polygon(self) -> Polygon:
raise NotImplementedError()

Expand All @@ -17,6 +24,7 @@ def get_dimensions(self):

class ViewPort(BaseViewPort):
def __init__(self, upper_left, lower_right) -> None:
super().__init__()
self.upper_left = upper_left
self.lower_right = lower_right

Expand All @@ -37,7 +45,8 @@ def get_dimensions(self):
def from_geohashes_query_param(cls, geohashes):
if geohashes is None:
return None
geohashes_arr = geohashes.split("/")
split_by = r"[\/,\- ]"
geohashes_arr = re.split(split_by, geohashes)
if len(geohashes_arr) >= 2:
lat1, lon1, lat1_err, lon1_err = geohash2.decode_exactly(geohashes_arr[0])
lat2, lon2, lat2_err, lon2_err = geohash2.decode_exactly(geohashes_arr[1])
Expand All @@ -58,6 +67,7 @@ def from_geohashes_query_param(cls, geohashes):

class Tile(BaseViewPort):
def __init__(self, x: int, y: int, z: int) -> None:
super().__init__()
self.x = x
self.y = y
self.z = z
Expand Down Expand Up @@ -99,7 +109,9 @@ def from_query_param(cls, param):
if param is None:
return None

param_arr = param.split("/")
split_by = r"[\/,\- ]"
param_arr = re.split(split_by, param)

if len(param_arr) != 3:
raise ValueError("Tile has to be defined by exactly 3 integers")

Expand Down
17 changes: 16 additions & 1 deletion generic_map_api/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
from rest_framework.viewsets import ViewSet

from .clustering import Clustering
from .constants import ViewportHandling
from .serializers import BaseFeatureSerializer, ClusterSerializer
from .values import BaseViewPort, Tile, ViewPort

Expand Down Expand Up @@ -104,8 +105,10 @@ class MapFeaturesBaseView(MapApiBaseView):

require_viewport_zoom: bool = False
require_viewport_size: bool = False
require_viewport_meters_per_pixel: bool = False

preferred_viewport_handling: str = "viewport"
preferred_viewport_handling: str = ViewportHandling.SPLIT
preferred_viewport_chunks: int = 10

def get_meta(self, request):
return {
Expand All @@ -116,6 +119,7 @@ def get_meta(self, request):
"icon": self.get_icon(),
"clustering": self.clustering,
"preferred_viewport_handling": self.preferred_viewport_handling,
"preferred_viewport_chunks": self.preferred_viewport_chunks,
"query_params": self.render_query_params_meta(request),
"requirements": self.render_requirements(request),
"urls": {
Expand All @@ -135,6 +139,15 @@ def list(self, request):
request.GET.get("viewport", None)
)

if "viewport.zoom" in request.GET:
viewport.zoom = request.GET["viewport.zoom"]

if "viewport.mpp" in request.GET:
viewport.meters_per_pixel = request.GET["viewport.mpp"]

if "viewport.size" in request.GET:
viewport.size = tuple(request.GET["viewport.size"].split("x"))

params = self._parse_params(request)
clustering_config = self._parse_clustering_config(request)

Expand Down Expand Up @@ -170,6 +183,8 @@ def render_requirements(self, request): # pylint: disable=unused-argument
requirements.append("viewport.size")
if self.require_viewport_zoom:
requirements.append("viewport.zoom")
if self.require_viewport_meters_per_pixel:
requirements.append("viewport.mpp")
return requirements

def retrieve(self, request, pk): # pylint: disable=unused-argument
Expand Down

0 comments on commit d1ffb2a

Please sign in to comment.