Skip to content

Commit 1548ee5

Browse files
authored
feat: Add view parameter to viz (#1013)
### Change list - Allow passing `view="globe"` parameter to `viz` - Render in interleaved maplibre basemap by default - When using a known basemap style with labels, render layers underneath labels
1 parent b99243d commit 1548ee5

File tree

3 files changed

+38
-5
lines changed

3 files changed

+38
-5
lines changed

lonboard/_map.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -718,7 +718,7 @@ def as_html(self) -> HTML:
718718

719719
@t.default("view_state")
720720
def _default_initial_view_state(self) -> dict[str, Any]:
721-
if isinstance(self.view, (MapView, GlobeView)):
721+
if self.view is None or isinstance(self.view, (MapView, GlobeView)):
722722
return compute_view(self.layers) # type: ignore
723723

724724
return {}

lonboard/_viz.py

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
import json
88
from textwrap import dedent
9-
from typing import TYPE_CHECKING, Any, Protocol, TypeAlias, cast
9+
from typing import TYPE_CHECKING, Any, Literal, Protocol, TypeAlias, cast
1010

1111
import numpy as np
1212
from arro3.core import Array, ChunkedArray, Schema, Table, struct_field
@@ -26,6 +26,7 @@
2626
)
2727
from lonboard.basemap import CartoStyle, MaplibreBasemap
2828
from lonboard.layer import PathLayer, PolygonLayer, ScatterplotLayer
29+
from lonboard.view import BaseView, GlobeView
2930

3031
if TYPE_CHECKING:
3132
import duckdb
@@ -81,13 +82,14 @@ def __geo_interface__(self) -> dict: ...
8182
DEFAULT_POLYGON_LINE_COLOR = [0, 0, 0, 200]
8283

8384

84-
def viz(
85+
def viz( # noqa: PLR0913
8586
data: VizDataInput | list[VizDataInput] | tuple[VizDataInput, ...],
8687
*,
8788
scatterplot_kwargs: ScatterplotLayerKwargs | None = None,
8889
path_kwargs: PathLayerKwargs | None = None,
8990
polygon_kwargs: PolygonLayerKwargs | None = None,
9091
map_kwargs: MapKwargs | None = None,
92+
view: BaseView | Literal["globe"] | None = None,
9193
) -> Map:
9294
"""Plot your data easily.
9395
@@ -165,6 +167,7 @@ def viz(
165167
[`PolygonLayer`][lonboard.PolygonLayer]s.
166168
map_kwargs: a `dict` of parameters to pass down to the generated
167169
[`Map`][lonboard.Map].
170+
view: a [view instance][lonboard.view.BaseView] to use for the map view, or the string "globe".
168171
169172
For more control over rendering, construct [`Map`][lonboard.Map] and `Layer` objects
170173
directly.
@@ -200,8 +203,26 @@ def viz(
200203

201204
map_kwargs = map_kwargs if map_kwargs else {}
202205

206+
if "view" not in map_kwargs and view is not None:
207+
if view == "globe":
208+
map_kwargs["view"] = GlobeView()
209+
else:
210+
map_kwargs["view"] = view
211+
203212
if "basemap_style" not in map_kwargs and "basemap" not in map_kwargs:
204-
map_kwargs["basemap"] = MaplibreBasemap(style=CartoStyle.DarkMatter)
213+
map_kwargs["basemap"] = MaplibreBasemap(
214+
mode="interleaved",
215+
style=CartoStyle.DarkMatter,
216+
)
217+
218+
# If we're using a known style that has labels, set layers to be below labels
219+
if map_kwargs["basemap"].style in [
220+
CartoStyle.DarkMatter,
221+
CartoStyle.Positron,
222+
CartoStyle.Voyager,
223+
]:
224+
for layer in layers:
225+
layer.before_id = "watername_ocean"
205226

206227
return Map(layers=layers, **map_kwargs)
207228

tests/test_map.py

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
1+
import geopandas as gpd
12
import pytest
3+
from geodatasets import get_path
24
from traitlets import TraitError
35

4-
from lonboard import Map, ScatterplotLayer, SolidPolygonLayer
6+
from lonboard import Map, ScatterplotLayer, SolidPolygonLayer, viz
57
from lonboard.basemap import MaplibreBasemap
68
from lonboard.view import FirstPersonView, GlobeView, OrthographicView
79
from lonboard.view_state import (
@@ -182,3 +184,13 @@ def test_map_view_validate_globe_view_basemap():
182184
match=r"GlobeView requires the basemap mode to be 'interleaved'.",
183185
):
184186
m.view = GlobeView()
187+
188+
189+
def test_default_view_state_inferred():
190+
gdf = gpd.read_file(get_path("nybb"))
191+
m = viz(gdf)
192+
view_state = m.view_state
193+
assert isinstance(view_state, MapViewState)
194+
assert view_state.longitude - (-73.90) < 1e-2
195+
assert view_state.latitude - 40.67 < 1e-2
196+
assert view_state.zoom == 9

0 commit comments

Comments
 (0)