Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 16 additions & 13 deletions src/rok4/layer.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,18 +5,21 @@
- `Layer` - Descriptor to broadcast pyramids' data
"""

# -- IMPORTS --

# standard library
import json
import os
import re
from json.decoder import JSONDecodeError
from typing import Dict, List, Tuple, Union
from typing import Dict, List, Tuple

# package
from rok4.enums import PyramidType
from rok4.exceptions import *
from rok4.exceptions import FormatError, MissingAttributeError
from rok4.pyramid import Pyramid
from rok4.storage import *
from rok4.tile_matrix_set import TileMatrixSet
from rok4.utils import *
from rok4.storage import get_data_str, get_infos_from_path, put_data_str
from rok4.utils import reproject_bbox


class Layer:
Expand Down Expand Up @@ -92,8 +95,8 @@ def from_descriptor(cls, descriptor: str) -> "Layer":
)
layer.__bbox = reproject_bbox(layer.__geobbox, "EPSG:4326", layer.__tms.srs, 5)
# On force l'emprise de la couche, on recalcule donc les tuiles limites correspondantes pour chaque niveau
for l in layer.__levels.values():
l.set_limits_from_bbox(layer.__bbox)
for level in layer.__levels.values():
level.set_limits_from_bbox(layer.__bbox)
else:
layer.__bbox = layer.__best_level.bbox
layer.__geobbox = reproject_bbox(layer.__bbox, layer.__tms.srs, "EPSG:4326", 5)
Expand Down Expand Up @@ -184,7 +187,7 @@ def __load_pyramids(self, pyramids: List[Dict[str, str]]) -> None:
Exception: Overlapping in usage pyramids' levels
"""

## Toutes les pyramides doivent avoir les même caractéristiques
# Toutes les pyramides doivent avoir les même caractéristiques
channels = None
for p in pyramids:
pyramid = Pyramid.from_descriptor(p["path"])
Expand Down Expand Up @@ -221,16 +224,16 @@ def __load_pyramids(self, pyramids: List[Dict[str, str]]) -> None:
self.__resampling = pyramid.raster_specifications["interpolation"]

levels = pyramid.get_levels(bottom_level, top_level)
for l in levels:
if l.id in self.__levels:
raise Exception(f"Level {l.id} is present in two used pyramids")
self.__levels[l.id] = l
for level in levels:
if level.id in self.__levels:
raise Exception(f"Level {level.id} is present in two used pyramids")
self.__levels[level.id] = level

self.__pyramids.append(
{"pyramid": pyramid, "bottom_level": bottom_level, "top_level": top_level}
)

self.__best_level = sorted(self.__levels.values(), key=lambda l: l.resolution)[0]
self.__best_level = sorted(self.__levels.values(), key=lambda level: level.resolution)[0]

def __str__(self) -> str:
return f"{self.type.name} layer '{self.__name}'"
Expand Down
68 changes: 42 additions & 26 deletions src/rok4/pyramid.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,24 +6,40 @@
- `Level` - Level of a pyramid
"""

# -- IMPORTS --

# standard library
import io
import json
import os
import re
import tempfile
import zlib
from json.decoder import JSONDecodeError
from typing import Dict, Iterator, List, Tuple, Union
from typing import Dict, Iterator, List, Tuple

# 3rd party
import mapbox_vector_tile
import numpy
from PIL import Image

# package
from rok4.enums import PyramidType, SlabType, StorageType
from rok4.exceptions import *
from rok4.storage import *
from rok4.exceptions import FormatError, MissingAttributeError
from rok4.storage import (
copy,
get_data_binary,
get_data_str,
get_infos_from_path,
get_path_from_infos,
put_data_str,
remove,
size_path,
)
from rok4.tile_matrix_set import TileMatrix, TileMatrixSet
from rok4.utils import *
from rok4.utils import reproject_point, srs_to_spatialreference

# -- GLOBALS --
ROK4_IMAGE_HEADER_SIZE = 2048
"""Slab's header size, 2048 bytes"""

Expand Down Expand Up @@ -441,8 +457,8 @@ def from_descriptor(cls, descriptor: str) -> "Pyramid":
pyramid.__masks = False

# Niveaux
for l in data["levels"]:
lev = Level.from_descriptor(l, pyramid)
for level in data["levels"]:
lev = Level.from_descriptor(level, pyramid)
pyramid.__levels[lev.id] = lev

if pyramid.__tms.get_level(lev.id) is None:
Expand Down Expand Up @@ -510,12 +526,12 @@ def from_other(cls, other: "Pyramid", name: str, storage: Dict) -> "Pyramid":
pyramid.__raster_specifications = other.__raster_specifications

# Niveaux
for l in other.__levels.values():
lev = Level.from_other(l, pyramid)
for level in other.__levels.values():
lev = Level.from_other(level, pyramid)
pyramid.__levels[lev.id] = lev

except KeyError as e:
raise MissingAttributeError(descriptor, e)
raise MissingAttributeError(pyramid.descriptor, e)

return pyramid

Expand All @@ -540,10 +556,12 @@ def serializable(self) -> Dict:
serialization = {"tile_matrix_set": self.__tms.name, "format": self.__format}

serialization["levels"] = []
sorted_levels = sorted(self.__levels.values(), key=lambda l: l.resolution, reverse=True)
sorted_levels = sorted(
self.__levels.values(), key=lambda level: level.resolution, reverse=True
)

for l in sorted_levels:
serialization["levels"].append(l.serializable)
for level in sorted_levels:
serialization["levels"].append(level.serializable)

if self.type == PyramidType.RASTER:
serialization["raster_specifications"] = self.__raster_specifications
Expand Down Expand Up @@ -639,9 +657,7 @@ def storage_depth(self, d: int) -> None:
Exception: the depth is not equal to the already known depth
"""
if "depth" in self.__storage and self.__storage["depth"] != d:
raise Exception(
f"Pyramid {pyramid.__descriptor} owns levels with different path depths"
)
raise Exception(f"Pyramid {self.__descriptor} owns levels with different path depths")
self.__storage["depth"] = d

@property
Expand Down Expand Up @@ -683,7 +699,7 @@ def bottom_level(self) -> "Level":
Returns:
Level: the bottom level
"""
return sorted(self.__levels.values(), key=lambda l: l.resolution)[0]
return sorted(self.__levels.values(), key=lambda level: level.resolution)[0]

@property
def top_level(self) -> "Level":
Expand All @@ -692,7 +708,7 @@ def top_level(self) -> "Level":
Returns:
Level: the top level
"""
return sorted(self.__levels.values(), key=lambda l: l.resolution)[-1]
return sorted(self.__levels.values(), key=lambda level: level.resolution)[-1]

@property
def type(self) -> PyramidType:
Expand Down Expand Up @@ -862,7 +878,7 @@ def get_levels(self, bottom_id: str = None, top_id: str = None) -> List[Level]:
List[Level]: asked sorted levels
"""

sorted_levels = sorted(self.__levels.values(), key=lambda l: l.resolution)
sorted_levels = sorted(self.__levels.values(), key=lambda level: level.resolution)

levels = []

Expand All @@ -881,13 +897,13 @@ def get_levels(self, bottom_id: str = None, top_id: str = None) -> List[Level]:

end = False

for l in sorted_levels:
if not begin and l.id == bottom_id:
for level in sorted_levels:
if not begin and level.id == bottom_id:
begin = True

if begin:
levels.append(l)
if top_id is not None and l.id == top_id:
levels.append(level)
if top_id is not None and level.id == top_id:
end = True
break
else:
Expand Down Expand Up @@ -1059,7 +1075,7 @@ def get_tile_data_binary(self, level: str, column: int, row: int) -> str:
raise Exception(f"No level {level} in the pyramid")

if level_object.slab_width == 1 and level_object.slab_height == 1:
raise NotImplementedError(f"One-tile slab pyramid is not handled")
raise NotImplementedError("One-tile slab pyramid is not handled")

if not level_object.is_in_limits(column, row):
return None
Expand Down Expand Up @@ -1090,7 +1106,7 @@ def get_tile_data_binary(self, level: str, column: int, row: int) -> str:
2 * 4 * level_object.slab_width * level_object.slab_height,
),
)
except FileNotFoundError as e:
except FileNotFoundError:
# L'absence de la dalle est gérée comme simplement une absence de données
return None

Expand Down Expand Up @@ -1277,7 +1293,7 @@ def get_tile_data_vector(self, level: str, column: int, row: int) -> Dict:
if binary_tile is None:
return None

level_object = self.get_level(level)
self.get_level(level)

if self.__format == "TIFF_PBF_MVT":
try:
Expand Down Expand Up @@ -1334,7 +1350,7 @@ def get_tile_indices(
level_object = self.get_level(level)

if level_object is None:
raise Exception(f"Cannot found the level to calculate indices")
raise Exception("Cannot found the level to calculate indices")

if (
"srs" in kwargs
Expand Down
7 changes: 7 additions & 0 deletions src/rok4/raster.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,17 +6,24 @@
- RasterSet - Structure describing a set of raster data.
"""

# -- IMPORTS --

# standard library
import copy
import json
import re
from typing import Dict, Tuple

# 3rd party
from osgeo import gdal, ogr

# package
from rok4.enums import ColorFormat
from rok4.storage import exists, get_osgeo_path, put_data_str
from rok4.utils import compute_bbox, compute_format

# -- GLOBALS --

# Enable GDAL/OGR exceptions
ogr.UseExceptions()
gdal.UseExceptions()
Expand Down
Loading