diff --git a/docs/projections.py b/docs/projections.py index 7a139cad..6584f9db 100644 --- a/docs/projections.py +++ b/docs/projections.py @@ -126,7 +126,13 @@ # has its own :meth:`~ultraplot.axes.GeoAxes.format` command. :meth:`ultraplot.axes.GeoAxes.format` # facilitates :ref:`geographic-specific modifications ` like meridional # and parallel gridlines and land mass outlines. The syntax is very similar to -# :func:`ultraplot.axes.CartesianAxes.format`. Note that the `proj` keyword and several of +# :func:`ultraplot.axes.CartesianAxes.format`. +# .. important:: +# The internal reference system used for plotting in ultraplot is **PlateCarree**. +# External libraries, such as `contextily`, may use different internal reference systems, +# such as **EPSG:3857** (Web Mercator). When interfacing with such libraries, it is important +# to provide the appropriate `transform` parameter to ensure proper alignment between coordinate systems. +# Note that the `proj` keyword and several of # the :func:`~ultraplot.axes.GeoAxes.format` keywords are inspired by the basemap API. # In the below example, we create and format a very simple geographic plot. @@ -217,7 +223,7 @@ # when they are omitted (e.g., ``lon0=0`` as the default for most projections). # # .. warning:: -# The `basemap`_ package is now being actively maintained again witha short hiatus for a few years. We originally +# The `basemap`_ package is now being actively maintained again with a short hiatus for a few years. We originally # included basemap support because its gridline labeling was more powerful # than cartopy gridline labeling. While cartopy gridline labeling has # significantly improved since version 0.18, UltraPlot continues to support diff --git a/ultraplot/tests/test_geographic.py b/ultraplot/tests/test_geographic.py index de62695d..4b95a938 100644 --- a/ultraplot/tests/test_geographic.py +++ b/ultraplot/tests/test_geographic.py @@ -879,3 +879,19 @@ def test_dms_used_for_mercator(): assert a == expectation assert b == expectation return fig + + +@pytest.mark.mpl_image_compare +def test_imshow_with_and_without_transform(rng): + data = rng.random((100, 100)) + fig, ax = uplt.subplots(ncols=3, proj="lcc", share=0) + ax.format(land=True, labels=True) + ax[:2].format( + latlim=(-10, 10), + lonlim=(-10, 10), + ) + ax[0].imshow(data, transform=ax[0].projection) + ax[1].imshow(data, transform=None) + ax[2].imshow(data, transform=uplt.axes.geo.ccrs.PlateCarree()) + ax.format(title=["LCC", "No transform", "PlateCarree"]) + return fig diff --git a/ultraplot/tests/test_inputs.py b/ultraplot/tests/test_inputs.py index 00ad9be9..a12959da 100644 --- a/ultraplot/tests/test_inputs.py +++ b/ultraplot/tests/test_inputs.py @@ -1,5 +1,5 @@ import ultraplot as uplt, pytest, numpy as np -from unittest.mock import Mock +from unittest.mock import Mock, patch @pytest.mark.parametrize( @@ -33,3 +33,25 @@ def tripcolor(self, tri, z, extra=None, kw=None): # Test that the decorator preserves the function name assert decorated.__name__ == "tripcolor" + + +@pytest.mark.parametrize("transform", [None, uplt.constructor.Proj("merc")]) +def test_projection_set_correctly(rng, transform): + + fig, ax = uplt.subplots(proj="merc") + fig.canvas.draw() + data = rng.random((10, 10)) + + with patch.object(ax, "imshow", wraps=ax.imshow) as mock_imshow: + # Call imshow with some dummy data + settings = dict(transform=transform) + ax.imshow(data, **settings) + + # Assert that the transform keyword argument was set correctly + mock_imshow.assert_called_once() + _, kwargs = mock_imshow.call_args + assert "transform" in kwargs, "The 'transform' keyword argument is missing." + assert ( + kwargs["transform"] is transform + ), f"Expected transform to be {transform}, got {kwargs['transform']}" + uplt.close(fig)