Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow crs as class name to match projection #1332

Merged
merged 8 commits into from
May 2, 2024
Merged
Show file tree
Hide file tree
Changes from 7 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
5 changes: 3 additions & 2 deletions doc/user_guide/Customization.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -184,8 +184,7 @@
" Whether to display a coastline on top of the plot, setting\n",
" coastline='10m'/'50m'/'110m' specifies a specific scale.\n",
" crs (default=None):\n",
" Coordinate reference system of the data specified as Cartopy\n",
" CRS object, proj.4 string or EPSG code.\n",
" Coordinate reference system of the data specified as a string or integer EPSG code, a CRS or Proj pyproj object, a Cartopy CRS object or class name, a WKT string, or a proj.4 string. Defaults to PlateCarree.\n",
" features (default=None): dict or list\n",
" A list of features or a dictionary of features and the scale\n",
" at which to render it. Available features include 'borders',\n",
Expand All @@ -200,6 +199,8 @@
" Whether to project the data before plotting (adds initial\n",
" overhead but avoids projecting data when plot is dynamically\n",
" updated).\n",
" projection (default=None):\n",
" Coordinate reference system of the data specified as a string or integer EPSG code, a CRS or Proj pyproj object, a Cartopy CRS object or class name, a WKT string, or a proj.4 string. Defaults to PlateCarree.\n",
" tiles (default=False):\n",
" Whether to overlay the plot on a tile source. Tiles sources\n",
" can be selected by name or a tiles object or class can be passed,\n",
Expand Down
4 changes: 2 additions & 2 deletions doc/user_guide/Geographic_Data.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -409,12 +409,12 @@
"The API provides various geo-specific options:\n",
"\n",
"- `coastline` (default=False): Whether to display a coastline on top of the plot, setting `coastline='10m'/'50m'/'110m'` specifies a specific scale\n",
"- `crs` (default=None): Coordinate reference system of the data (input projection) specified as an EPSG code (int or string), pyproj CRS or Proj object, Cartopy CRS object, proj.4 string, or WKT string. Defaults to PlateCarree.\n",
"- `crs` (default=None): Coordinate reference system of the data specified as a string or integer EPSG code, a CRS or Proj pyproj object, a Cartopy CRS object or class name, a WKT string, or a proj.4 string. Defaults to PlateCarree.\n",
"- `features` features (default=None): A list of features or a dictionary of features and the scale at which to render it. Available features include 'borders', 'coastline', 'lakes', 'land', 'ocean', 'rivers' and 'states'. Available scales include '10m'/'50m'/'110m'.\n",
"- `geo` (default=False): Whether the plot should be treated as geographic (and assume PlateCarree, i.e. lat/lon coordinates)\n",
"- `global_extent` (default=False): Whether to expand the plot extent to span the whole globe\n",
"- `project` (default=False): Whether to project the data before plotting (adds initial overhead but avoids projecting data when plot is dynamically updated)\n",
"- `projection` (default=None): Coordinate reference system of the plot (output projection) specified as Cartopy CRS object or name.\n",
"- `projection` (default=None): Coordinate reference system of the data specified as a string or integer EPSG code, a CRS or Proj pyproj object, a Cartopy CRS object or class name, a WKT string, or a proj.4 string. Defaults to PlateCarree.\n",
"- `tiles` (default=False): Whether to overlay the plot on a tile source. Accept the following values:\n",
" - `True`: OpenStreetMap layer\n",
" - `xyzservices.TileProvider` instance (requires [`xyzservices`](https://xyzservices.readthedocs.io/) to be installed)\n",
Expand Down
30 changes: 8 additions & 22 deletions hvplot/converter.py
Original file line number Diff line number Diff line change
Expand Up @@ -289,8 +289,8 @@ class HoloViewsConverter:
crs (default=None):
Coordinate reference system of the data specified as a string
or integer EPSG code, a CRS or Proj pyproj object, a Cartopy
CRS object, a WKT string, or a proj.4 string. Defaults to
PlateCarree.
CRS object or class name, a WKT string, or a proj.4 string.
Defaults to PlateCarree.
features (default=None): dict or list
A list of features or a dictionary of features and the scale
at which to render it. Available features include 'borders',
Expand All @@ -306,8 +306,10 @@ class HoloViewsConverter:
overhead but avoids projecting data when plot is dynamically
updated).
projection (default=None): str or Cartopy CRS
Coordinate reference system of the plot specified as Cartopy
CRS object or class name.
Coordinate reference system of the data specified as a string
or integer EPSG code, a CRS or Proj pyproj object, a Cartopy
CRS object or class name, a WKT string, or a proj.4 string.
Defaults to PlateCarree.
tiles (default=False):
Whether to overlay the plot on a tile source:
- `True`: OpenStreetMap layer
Expand Down Expand Up @@ -645,24 +647,8 @@ def __init__(
from cartopy import crs as ccrs
from geoviews.util import project_extents

if isinstance(projection, str):
all_crs = [
proj
for proj in dir(ccrs)
if callable(getattr(ccrs, proj))
and proj not in ['ABCMeta', 'CRS']
and proj[0].isupper()
or proj == 'GOOGLE_MERCATOR'
]
if projection in all_crs and projection != 'GOOGLE_MERCATOR':
projection = getattr(ccrs, projection)()
elif projection == 'GOOGLE_MERCATOR':
projection = getattr(ccrs, projection)
else:
raise ValueError(
'Projection must be defined as cartopy CRS or '
f'one of the following CRS string:\n {all_crs}'
)
if projection is not None:
projection = process_crs(projection)

self.output_projection = projection or (ccrs.GOOGLE_MERCATOR if tiles else self.crs)
if tiles and self.output_projection != ccrs.GOOGLE_MERCATOR:
Expand Down
1 change: 1 addition & 0 deletions hvplot/tests/testutil.py
Original file line number Diff line number Diff line change
Expand Up @@ -260,6 +260,7 @@ def test_check_crs():
'input',
[
'+init=epsg:26911',
'PlateCarree',
],
)
def test_process_crs(input):
Expand Down
16 changes: 15 additions & 1 deletion hvplot/util.py
Original file line number Diff line number Diff line change
Expand Up @@ -286,6 +286,19 @@ def process_crs(crs):
return ccrs.PlateCarree()
elif isinstance(crs, ccrs.CRS):
return crs
elif isinstance(crs, str):
all_crs = [
proj
for proj in dir(ccrs)
if callable(getattr(ccrs, proj))
and proj not in ['ABCMeta', 'CRS']
and proj[0].isupper()
or proj == 'GOOGLE_MERCATOR'
]
if crs in all_crs and crs != 'GOOGLE_MERCATOR':
return getattr(ccrs, crs)()
elif crs == 'GOOGLE_MERCATOR':
return getattr(ccrs, crs)
elif isinstance(crs, pyproj.CRS):
crs = crs.to_wkt()

Expand All @@ -303,7 +316,8 @@ def process_crs(crs):

raise ValueError(
'Projection must be defined as a EPSG code, proj4 string, '
'WKT string, cartopy CRS, pyproj.Proj, or pyproj.CRS.'
'WKT string, cartopy CRS instance, cartopy CRS class name string, '
'pyproj.Proj, or pyproj.CRS.'
) from Exception(*errors)


Expand Down
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ tests-core = [
# of those.
tests = [
"hvplot[tests-core]",
"fugue",
"fugue[sql]",
"ibis-framework[duckdb]", # ibis-duckdb on conda
"polars",
]
Expand Down
Loading