[Git][debian-gis-team/python-cartopy][upstream] New upstream version 0.18.0~rc1+dfsg

Bas Couwenberg gitlab at salsa.debian.org
Mon Apr 27 09:45:26 BST 2020



Bas Couwenberg pushed to branch upstream at Debian GIS Project / python-cartopy


Commits:
4dfdf815 by Bas Couwenberg at 2020-04-27T10:33:29+02:00
New upstream version 0.18.0~rc1+dfsg
- - - - -


18 changed files:

- .circleci/config.yml
- docs/source/matplotlib/gridliner.rst
- lib/cartopy/_version.py
- lib/cartopy/examples/favicon.py
- + lib/cartopy/examples/gridliner.py
- lib/cartopy/img_transform.py
- lib/cartopy/mpl/contour.py
- lib/cartopy/mpl/geoaxes.py
- lib/cartopy/mpl/gridliner.py
- lib/cartopy/mpl/slippy_image_artist.py
- lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa.png
- lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa_1.5.png
- lib/cartopy/tests/mpl/test_caching.py
- lib/cartopy/tests/mpl/test_gridliner.py
- lib/cartopy/tests/mpl/test_mpl_integration.py
- lib/cartopy/tests/mpl/test_web_services.py
- lib/cartopy/tests/test_img_transform.py
- setup.py


Changes:

=====================================
.circleci/config.yml
=====================================
@@ -85,26 +85,6 @@ jobs:
       - store_artifacts:
           path: docs/build/html
 
-  docs-python2:
-    docker:
-      - image: continuumio/miniconda:latest
-    steps:
-      - checkout
-
-      - run: *apt-install
-      - run:
-          <<: *env-setup
-          environment:
-            PYTHON_VERSION: 2
-            EXTRA_PACKAGES: "futures"
-      - run: *deps-install
-      - run: *cp-install
-
-      - run: *doc-build
-
-      - store_artifacts:
-          path: docs/build/html
-
 
 #########################################
 # Defining workflows gets us parallelism.
@@ -115,4 +95,3 @@ workflows:
   build:
     jobs:
       - docs-python3
-      - docs-python2


=====================================
docs/source/matplotlib/gridliner.rst
=====================================
@@ -18,6 +18,25 @@ used to determine draw time behaviour of the gridlines and labels.
     :undoc-members:
 
 
+In this first example, gridines and tick labels are plotted in a
+non-rectangular projection, with most default values and
+no tuning of the gridliner attributes:
+
+.. plot::
+    :include-source:
+
+    import matplotlib.pyplot as plt
+    import cartopy.crs as ccrs
+
+    rotated_crs = ccrs.RotatedPole(pole_longitude=120.0, pole_latitude=70.0)
+
+    ax = plt.axes(projection=rotated_crs)
+    ax.set_extent([-6, 3, 48, 58], crs=ccrs.PlateCarree())
+    ax.coastlines(resolution='50m')
+    ax.gridlines(draw_labels=True, dms=True, x_inline=False, y_inline=False)
+
+    plt.show()
+
 
 The following contrived example makes use of many of the features of the Gridliner
 class to produce customized gridlines and tick labels:
@@ -29,7 +48,8 @@ class to produce customized gridlines and tick labels:
     import matplotlib.ticker as mticker
     import cartopy.crs as ccrs
 
-    from cartopy.mpl.gridliner import LONGITUDE_FORMATTER, LATITUDE_FORMATTER
+    from cartopy.mpl.ticker import (LongitudeFormatter, LatitudeFormatter,
+                                    LatitudeLocator)
 
 
     ax = plt.axes(projection=ccrs.Mercator())
@@ -41,8 +61,9 @@ class to produce customized gridlines and tick labels:
     gl.left_labels = False
     gl.xlines = False
     gl.xlocator = mticker.FixedLocator([-180, -45, 0, 45, 180])
-    gl.xformatter = LONGITUDE_FORMATTER
-    gl.yformatter = LATITUDE_FORMATTER
+    gl.ylocator = LatitudeLocator()
+    gl.xformatter = LongitudeFormatter()
+    gl.yformatter = LatitudeFormatter()
     gl.xlabel_style = {'size': 15, 'color': 'gray'}
     gl.xlabel_style = {'color': 'red', 'weight': 'bold'}
 


=====================================
lib/cartopy/_version.py
=====================================
@@ -23,8 +23,8 @@ def get_keywords():
     # setup.py/versioneer.py will grep for the variable names, so they must
     # each be defined on a line of their own. _version.py will just call
     # get_keywords().
-    git_refnames = " (HEAD -> master, tag: v0.18.0b2)"
-    git_full = "b46098785a9edf4e85bdb34dd5d92890d09ffda2"
+    git_refnames = " (HEAD -> master, tag: v0.18.0rc1, v0.18.x)"
+    git_full = "e6c1d06b7a7ecf808c8e65d26c3644c0af990c00"
     keywords = {"refnames": git_refnames, "full": git_full}
     return keywords
 


=====================================
lib/cartopy/examples/favicon.py
=====================================
@@ -19,22 +19,7 @@ def main():
 
     ax.coastlines()
     ax.gridlines()
-
-    im = ax.stock_img()
-
-    def on_draw(event=None):
-        """
-        Hook into matplotlib's event mechanism to define the clip path of the
-        background image.
-
-        """
-        # Clip the image to the current background boundary.
-        im.set_clip_path(ax.patch.get_path(),
-                         transform=ax.patch.get_transform())
-
-    # Register the on_draw method and call it once now.
-    fig.canvas.mpl_connect('draw_event', on_draw)
-    on_draw()
+    ax.stock_img()
 
     # Generate a matplotlib path representing the character "C".
     fp = FontProperties(family='Bitstream Vera Sans', weight='bold')


=====================================
lib/cartopy/examples/gridliner.py
=====================================
@@ -0,0 +1,44 @@
+"""
+Gridlines and tick labels
+-------------------------
+
+These examples demonstrate how to quickly add longitude
+and latitude gridlines and tick labels on a non-rectangular projection.
+
+As you can see on the first example,
+longitude labels may be drawn on left and right sides,
+and latitude labels may be drawn on bottom and top sides.
+Thanks to the ``dms`` keyword, minutes are used when appropriate
+to display fractions of degree.
+
+
+In the second example, labels are still drawn at the map edges
+despite its complexity, and some others are also drawn within the map
+boundary.
+
+"""
+import cartopy.crs as ccrs
+import cartopy.feature as cfeature
+import matplotlib.pyplot as plt
+
+__tags__ = ['Gridlines', 'Tick labels', 'Lines and polygons']
+
+
+def main():
+
+    rotated_crs = ccrs.RotatedPole(pole_longitude=120.0, pole_latitude=70.0)
+    ax0 = plt.axes(projection=rotated_crs)
+    ax0.set_extent([-6, 1, 47.5, 51.5], crs=ccrs.PlateCarree())
+    ax0.add_feature(cfeature.LAND.with_scale('110m'))
+    ax0.gridlines(draw_labels=True, dms=True, x_inline=False, y_inline=False)
+
+    plt.figure(figsize=(6.9228, 3))
+    ax1 = plt.axes(projection=ccrs.InterruptedGoodeHomolosine())
+    ax1.coastlines(resolution='110m')
+    ax1.gridlines(draw_labels=True)
+
+    plt.show()
+
+
+if __name__ == '__main__':
+    main()


=====================================
lib/cartopy/img_transform.py
=====================================
@@ -1,4 +1,4 @@
-# (C) British Crown Copyright 2011 - 2018, Met Office
+# (C) British Crown Copyright 2011 - 2020, Met Office
 #
 # This file is part of cartopy.
 #
@@ -34,8 +34,8 @@ import cartopy.crs as ccrs
 
 
 def mesh_projection(projection, nx, ny,
-                    x_extents=[None, None],
-                    y_extents=[None, None]):
+                    x_extents=(None, None),
+                    y_extents=(None, None)):
     """
     Return sample points in the given projection which span the entire
     projection range evenly.
@@ -69,11 +69,17 @@ def mesh_projection(projection, nx, ny,
 
     """
 
+    def extent(specified, default, index):
+        if specified[index] is not None:
+            return specified[index]
+        else:
+            return default[index]
+
     # Establish the x-direction and y-direction extents.
-    x_lower = x_extents[0] or projection.x_limits[0]
-    x_upper = x_extents[1] or projection.x_limits[1]
-    y_lower = y_extents[0] or projection.y_limits[0]
-    y_upper = y_extents[1] or projection.y_limits[1]
+    x_lower = extent(x_extents, projection.x_limits, 0)
+    x_upper = extent(x_extents, projection.x_limits, 1)
+    y_lower = extent(y_extents, projection.y_limits, 0)
+    y_upper = extent(y_extents, projection.y_limits, 1)
 
     # Calculate evenly spaced sample points spanning the
     # extent - excluding endpoint.


=====================================
lib/cartopy/mpl/contour.py
=====================================
@@ -1,4 +1,4 @@
-# (C) British Crown Copyright 2011 - 2019, Met Office
+# (C) British Crown Copyright 2011 - 2020, Met Office
 #
 # This file is part of cartopy.
 #
@@ -52,7 +52,14 @@ class GeoContourSet(QuadContourSet):
             # list in-place (as the contour label code does in mpl).
             paths = col.get_paths()
 
-            data_t = self.ax.transData
+            # The ax attribute is deprecated in MPL 3.3 in favor of
+            # axes. So, here we test if axes is present and fall back
+            # on the old self.ax to support MPL versions less than 3.3
+            if hasattr(self, "axes"):
+                data_t = self.axes.transData
+            else:
+                data_t = self.ax.transData
+
             # Define the transform that will take us from collection
             # coordinates through to axes projection coordinates.
             col_to_data = col.get_transform() - data_t
@@ -64,7 +71,7 @@ class GeoContourSet(QuadContourSet):
 
             # The collection will now be referenced in axes projection
             # coordinates.
-            col.set_transform(self.ax.transData)
+            col.set_transform(data_t)
 
             # Clear the now incorrectly referenced paths.
             del paths[:]


=====================================
lib/cartopy/mpl/geoaxes.py
=====================================
@@ -441,7 +441,7 @@ class GeoAxes(matplotlib.axes.Axes):
                     self._autoscaleXon, self._autoscaleYon) = other
 
     @matplotlib.artist.allow_rasterization
-    def draw(self, renderer=None, inframe=False):
+    def draw(self, renderer=None, **kwargs):
         """
         Extend the standard behaviour of :func:`matplotlib.axes.Axes.draw`.
 
@@ -475,8 +475,8 @@ class GeoAxes(matplotlib.axes.Axes):
                 self.imshow(img, extent=extent, origin=origin,
                             transform=factory.crs, *args[1:], **kwargs)
         self._done_img_factory = True
-        return matplotlib.axes.Axes.draw(self, renderer=renderer,
-                                         inframe=inframe)
+
+        return matplotlib.axes.Axes.draw(self, renderer=renderer, **kwargs)
 
     def _update_title_position(self, renderer):
         matplotlib.axes.Axes._update_title_position(self, renderer)
@@ -1312,8 +1312,9 @@ class GeoAxes(matplotlib.axes.Axes):
 
     def gridlines(self, crs=None, draw_labels=False,
                   xlocs=None, ylocs=None, dms=False,
-                  x_inline=None, y_inline=None,
-                  auto_inline=True, **kwargs):
+                  x_inline=None, y_inline=None, auto_inline=True,
+                  xformatter=None, yformatter=None,
+                  **kwargs):
         """
         Automatically add gridlines to the axes, in the given coordinate
         system, at draw time.
@@ -1350,6 +1351,18 @@ class GeoAxes(matplotlib.axes.Axes):
             Toggle whether the y labels drawn should be inline.
         auto_inline: optional
             Set x_inline and y_inline automatically based on projection
+        xformatter: optional
+            A :class:`matplotlib.ticker.Formatter` instance to format labels
+            for x-coordinate gridlines. It defaults to None, which implies the
+            use of a :class:`cartopy.mpl.ticker.LongitudeFormatter` initiated
+            with the ``dms`` argument, if the crs is of
+            :class:`~cartopy.crs.PlateCarree` type.
+        yformatter: optional
+            A :class:`matplotlib.ticker.Formatter` instance to format labels
+            for y-coordinate gridlines. It defaults to None, which implies the
+            use of a :class:`cartopy.mpl.ticker.LatitudeFormatter` initiated
+            with the ``dms`` argument, if the crs is of
+            :class:`~cartopy.crs.PlateCarree` type.
 
         Keyword Parameters
         ------------------
@@ -1377,7 +1390,8 @@ class GeoAxes(matplotlib.axes.Axes):
         gl = Gridliner(
             self, crs=crs, draw_labels=draw_labels, xlocator=xlocs,
             ylocator=ylocs, collection_kwargs=kwargs, dms=dms,
-            x_inline=x_inline, y_inline=y_inline, auto_inline=auto_inline)
+            x_inline=x_inline, y_inline=y_inline, auto_inline=auto_inline,
+            xformatter=xformatter, yformatter=yformatter)
         self._gridliners.append(gl)
         return gl
 
@@ -1569,13 +1583,20 @@ class GeoAxes(matplotlib.axes.Axes):
         cmap = kwargs.pop('cmap', None)
         vmin = kwargs.pop('vmin', None)
         vmax = kwargs.pop('vmax', None)
-        shading = kwargs.pop('shading', 'flat').lower()
         antialiased = kwargs.pop('antialiased', False)
         kwargs.setdefault('edgecolors', 'None')
 
-        allmatch = (shading == 'gouraud')
+        if matplotlib.__version__ < "3.3":
+            shading = kwargs.pop('shading', 'flat')
+            allmatch = (shading == 'gouraud')
+            X, Y, C = self._pcolorargs('pcolormesh', *args, allmatch=allmatch)
+        else:
+            shading = kwargs.pop('shading', 'auto')
+            if shading is None:
+                shading = 'auto'
+            X, Y, C, shading = self._pcolorargs('pcolormesh', *args,
+                                                shading=shading)
 
-        X, Y, C = self._pcolorargs('pcolormesh', *args, allmatch=allmatch)
         Ny, Nx = X.shape
 
         # convert to one dimensional arrays


=====================================
lib/cartopy/mpl/gridliner.py
=====================================
@@ -1,19 +1,8 @@
-# (C) British Crown Copyright 2011 - 2020, Met Office
+# Copyright Cartopy Contributors
 #
-# This file is part of cartopy.
-#
-# cartopy is free software: you can redistribute it and/or modify it under
-# the terms of the GNU Lesser General Public License as published by the
-# Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# cartopy is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU Lesser General Public License for more details.
-#
-# You should have received a copy of the GNU Lesser General Public License
-# along with cartopy.  If not, see <https://www.gnu.org/licenses/>.
+# This file is part of Cartopy and is released under the LGPL license.
+# See COPYING and COPYING.LESSER in the root of the repository for full
+# licensing details.
 
 from __future__ import (absolute_import, division, print_function)
 
@@ -36,6 +25,7 @@ from cartopy.mpl.ticker import (
 
 degree_locator = mticker.MaxNLocator(nbins=9, steps=[1, 1.5, 1.8, 2, 3, 6, 10])
 classic_locator = mticker.MaxNLocator(nbins=9)
+classic_formatter = mticker.ScalarFormatter
 
 _DEGREE_SYMBOL = u'\u00B0'
 _X_INLINE_PROJS = (
@@ -146,12 +136,14 @@ class Gridliner(object):
             A :class:`matplotlib.ticker.Formatter` instance to format labels
             for x-coordinate gridlines. It defaults to None, which implies the
             use of a :class:`cartopy.mpl.ticker.LongitudeFormatter` initiated
-            with the ``dms`` argument.
+            with the ``dms`` argument, if the crs is of
+            :class:`~cartopy.crs.PlateCarree` type.
         yformatter: optional
             A :class:`matplotlib.ticker.Formatter` instance to format labels
             for y-coordinate gridlines. It defaults to None, which implies the
             use of a :class:`cartopy.mpl.ticker.LatitudeFormatter` initiated
-            with the ``dms`` argument.
+            with the ``dms`` argument, if the crs is of
+            :class:`~cartopy.crs.PlateCarree` type.
         collection_kwargs: optional
             Dictionary controlling line properties, passed to
             :class:`matplotlib.collections.Collection`. Defaults to None.
@@ -199,11 +191,21 @@ class Gridliner(object):
         else:
             self.ylocator = classic_locator
 
+        if xformatter is None:
+            if isinstance(crs, cartopy.crs.PlateCarree):
+                xformatter = LongitudeFormatter(dms=dms)
+            else:
+                xformatter = classic_formatter()
         #: The :class:`~matplotlib.ticker.Formatter` to use for the lon labels.
-        self.xformatter = xformatter or LongitudeFormatter(dms=dms)
+        self.xformatter = xformatter
 
+        if yformatter is None:
+            if isinstance(crs, cartopy.crs.PlateCarree):
+                yformatter = LatitudeFormatter(dms=dms)
+            else:
+                yformatter = classic_formatter()
         #: The :class:`~matplotlib.ticker.Formatter` to use for the lat labels.
-        self.yformatter = yformatter or LatitudeFormatter(dms=dms)
+        self.yformatter = yformatter
 
         #: Whether to draw labels on the top of the map.
         self.top_labels = draw_labels
@@ -597,6 +599,7 @@ class Gridliner(object):
                                     continue
                                 x = x_midpoints[i]
                                 y = tick_value
+                                kw.update(clip_on=True)
                                 y_set = True
                             else:
                                 x = pt0[0]
@@ -607,6 +610,7 @@ class Gridliner(object):
                                     continue
                                 x = tick_value
                                 y = y_midpoints[i]
+                                kw.update(clip_on=True)
                             elif not y_set:
                                 y = pt0[1]
 
@@ -737,10 +741,10 @@ class Gridliner(object):
                 warnings.warn('The labels of this gridliner do not belong to '
                               'the gridliner axes')
 
-            # Compute angles to try
             orig_specs = {'rotation': artist.get_rotation(),
                           'ha': artist.get_ha(),
                           'va': artist.get_va()}
+            # Compute angles to try
             angles = [None]
             for abs_delta_angle in np.arange(delta_angle, max_delta_angle+1,
                                              delta_angle):
@@ -763,6 +767,8 @@ class Gridliner(object):
                     this_patch.get_transform())
                 if '3.1.0' <= matplotlib.__version__ <= '3.1.2':
                     this_path = remove_path_dupes(this_path)
+                center = artist.get_transform().transform_point(
+                    artist.get_position())
                 visible = False
 
                 for path in paths:
@@ -779,9 +785,16 @@ class Gridliner(object):
                                         .transformed(self.axes.transData))
                         if '3.1.0' <= matplotlib.__version__ <= '3.1.2':
                             outline_path = remove_path_dupes(outline_path)
-                    visible = (not outline_path.intersects_path(this_path) or
-                               (lonlat == 'lon' and self.x_inline) or
-                               (lonlat == 'lat' and self.y_inline))
+                    # Inline must be within the map.
+                    if ((lonlat == 'lon' and self.x_inline) or
+                            (lonlat == 'lat' and self.y_inline)):
+                        # TODO: When Matplotlib clip path works on text, this
+                        # clipping can be left to it.
+                        if outline_path.contains_point(center):
+                            visible = True
+                    # Non-inline must not run through the outline.
+                    elif not outline_path.intersects_path(this_path):
+                        visible = True
 
                     # Good
                     if visible:


=====================================
lib/cartopy/mpl/slippy_image_artist.py
=====================================
@@ -39,6 +39,9 @@ class SlippyImageArtist(AxesImage):
     """
     def __init__(self, ax, raster_source, **kwargs):
         self.raster_source = raster_source
+        if matplotlib.__version__ >= '3':
+            # This artist fills the Axes, so should not influence layout.
+            kwargs.setdefault('in_layout', False)
         super(SlippyImageArtist, self).__init__(ax, **kwargs)
         self.cache = []
 
@@ -54,6 +57,9 @@ class SlippyImageArtist(AxesImage):
         self.user_is_interacting = False
         self.stale = True
 
+    def get_window_extent(self, renderer=None):
+        return self.axes.get_window_extent(renderer=renderer)
+
     @matplotlib.artist.allow_rasterization
     def draw(self, renderer, *args, **kwargs):
         if not self.get_visible():


=====================================
lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa.png
=====================================
Binary files a/lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa.png and b/lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa.png differ


=====================================
lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa_1.5.png
=====================================
Binary files a/lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa_1.5.png and b/lib/cartopy/tests/mpl/baseline_images/mpl/test_gridliner/gridliner_labels_inline_usa_1.5.png differ


=====================================
lib/cartopy/tests/mpl/test_caching.py
=====================================
@@ -1,4 +1,4 @@
-# (C) British Crown Copyright 2011 - 2019, Met Office
+# (C) British Crown Copyright 2011 - 2020, Met Office
 #
 # This file is part of cartopy.
 #
@@ -151,8 +151,9 @@ def test_shapefile_transform_cache():
 
 
 def test_contourf_transform_path_counting():
+    fig = plt.figure()
     ax = plt.axes(projection=ccrs.Robinson())
-    ax.figure.canvas.draw()
+    fig.canvas.draw()
 
     # Capture the size of the cache before our test.
     gc.collect()


=====================================
lib/cartopy/tests/mpl/test_gridliner.py
=====================================
@@ -12,7 +12,11 @@ import pytest
 
 import cartopy.crs as ccrs
 from cartopy.mpl.geoaxes import GeoAxes
-from cartopy.mpl.gridliner import LATITUDE_FORMATTER, LONGITUDE_FORMATTER
+from cartopy.mpl.ticker import LongitudeLocator, LongitudeFormatter
+from cartopy.mpl.gridliner import (
+    LATITUDE_FORMATTER, LONGITUDE_FORMATTER,
+    classic_locator, classic_formatter)
+
 
 from cartopy.tests.mpl import MPL_VERSION, ImageTesting
 
@@ -286,3 +290,34 @@ def test_grid_labels_inline_usa():
             ax.gridlines(draw_labels=True, auto_inline=True, clip_on=True)
         ax.coastlines(resolution="110m")
     plt.subplots_adjust(wspace=0.35, hspace=0.35)
+
+
+ at pytest.mark.parametrize(
+    "proj,gcrs,xloc,xfmt,xloc_expected,xfmt_expected",
+    [
+       (ccrs.PlateCarree(), ccrs.PlateCarree(),
+        [10, 20], None, mticker.FixedLocator, LongitudeFormatter),
+       (ccrs.PlateCarree(), ccrs.Mercator(),
+        [10, 20], None, mticker.FixedLocator, classic_formatter),
+       (ccrs.PlateCarree(), ccrs.PlateCarree(),
+        mticker.MaxNLocator(nbins=9), None,
+        mticker.MaxNLocator, LongitudeFormatter),
+       (ccrs.PlateCarree(), ccrs.Mercator(),
+        mticker.MaxNLocator(nbins=9), None,
+        mticker.MaxNLocator, classic_formatter),
+       (ccrs.PlateCarree(), ccrs.PlateCarree(),
+        None, None, LongitudeLocator, LongitudeFormatter),
+       (ccrs.PlateCarree(), ccrs.Mercator(),
+        None, None, classic_locator.__class__, classic_formatter),
+       (ccrs.PlateCarree(), ccrs.PlateCarree(),
+        None, mticker.StrMethodFormatter('{x}'),
+        LongitudeLocator, mticker.StrMethodFormatter),
+     ])
+def test_gridliner_default_fmtloc(
+        proj, gcrs, xloc, xfmt, xloc_expected, xfmt_expected):
+    plt.figure()
+    ax = plt.subplot(111, projection=proj)
+    gl = ax.gridlines(crs=gcrs, draw_labels=False, xlocs=xloc, xformatter=xfmt)
+    plt.close()
+    assert isinstance(gl.xlocator, xloc_expected)
+    assert isinstance(gl.xformatter, xfmt_expected)


=====================================
lib/cartopy/tests/mpl/test_mpl_integration.py
=====================================
@@ -93,7 +93,7 @@ def test_global_pcolor_wrap_new_transform():
     ax = plt.axes(projection=ccrs.PlateCarree())
     ax.coastlines()
     x, y = np.meshgrid(np.linspace(0, 360), np.linspace(-90, 90))
-    data = np.sin(np.sqrt(x ** 2 + y ** 2))
+    data = np.sin(np.sqrt(x ** 2 + y ** 2))[:-1, :-1]
     plt.pcolor(x, y, data, transform=ccrs.PlateCarree())
 
 
@@ -103,7 +103,7 @@ def test_global_pcolor_wrap_no_transform():
     ax = plt.axes(projection=ccrs.PlateCarree())
     ax.coastlines()
     x, y = np.meshgrid(np.linspace(0, 360), np.linspace(-90, 90))
-    data = np.sin(np.sqrt(x ** 2 + y ** 2))
+    data = np.sin(np.sqrt(x ** 2 + y ** 2))[:-1, :-1]
     plt.pcolor(x, y, data)
 
 
@@ -148,6 +148,7 @@ def test_global_map():
              transform=ccrs.Geodetic())
 
 
+ at pytest.mark.filterwarnings("ignore:Unable to determine extent")
 @pytest.mark.natural_earth
 @ImageTesting(['simple_global'])
 def test_simple_global():
@@ -156,6 +157,7 @@ def test_simple_global():
     # produces a global map, despite not having needed to set the limits
 
 
+ at pytest.mark.filterwarnings("ignore:Unable to determine extent")
 @pytest.mark.natural_earth
 @ImageTesting(['multiple_projections4' if ccrs.PROJ4_VERSION < (5, 0, 0)
                else 'multiple_projections5'],
@@ -187,7 +189,7 @@ def test_multiple_projections():
                    ccrs.EckertVI(),
                    ]
 
-    rows = np.ceil(len(projections) / 5)
+    rows = np.ceil(len(projections) / 5).astype(int)
 
     fig = plt.figure(figsize=(10, 2 * rows))
     for i, prj in enumerate(projections, 1):


=====================================
lib/cartopy/tests/mpl/test_web_services.py
=====================================
@@ -18,6 +18,7 @@
 from __future__ import (absolute_import, division, print_function)
 
 import matplotlib.pyplot as plt
+from matplotlib.testing.decorators import cleanup
 import pytest
 
 from cartopy.tests.mpl import MPL_VERSION, ImageTesting
@@ -36,6 +37,17 @@ def test_wmts():
     ax.add_wmts(url, 'MODIS_Water_Mask')
 
 
+ at pytest.mark.network
+ at pytest.mark.skipif(not _OWSLIB_AVAILABLE, reason='OWSLib is unavailable.')
+ at cleanup
+def test_wms_tight_layout():
+    ax = plt.axes(projection=ccrs.PlateCarree())
+    url = 'http://vmap0.tiles.osgeo.org/wms/vmap0'
+    layer = 'basic'
+    ax.add_wms(url, layer)
+    ax.figure.tight_layout()
+
+
 @pytest.mark.network
 @pytest.mark.xfail((5, 0, 0) <= ccrs.PROJ4_VERSION < (5, 1, 0),
                    reason='Proj Orthographic projection is buggy.',


=====================================
lib/cartopy/tests/test_img_transform.py
=====================================
@@ -1,4 +1,4 @@
-# (C) British Crown Copyright 2014 - 2017, Met Office
+# (C) British Crown Copyright 2014 - 2020, Met Office
 #
 # This file is part of cartopy.
 #
@@ -19,11 +19,43 @@ from __future__ import (absolute_import, division, print_function)
 
 import numpy as np
 from numpy.testing import assert_array_equal
+import pytest
 
 import cartopy.img_transform as img_trans
 import cartopy.crs as ccrs
 
 
+ at pytest.mark.parametrize('xmin, xmax', [
+    (-90, 0), (-90, 90), (-90, None),
+    (0, 90), (0, None),
+    (None, 0), (None, 90), (None, None)])
+ at pytest.mark.parametrize('ymin, ymax', [
+    (-45, 0), (-45, 45), (-45, None),
+    (0, 45), (0, None),
+    (None, 0), (None, 45), (None, None)])
+def test_mesh_projection_extent(xmin, xmax, ymin, ymax):
+    proj = ccrs.PlateCarree()
+    nx = 4
+    ny = 2
+
+    target_x, target_y, extent = img_trans.mesh_projection(
+        proj, nx, ny,
+        x_extents=(xmin, xmax),
+        y_extents=(ymin, ymax))
+
+    if xmin is None:
+        xmin = proj.x_limits[0]
+    if xmax is None:
+        xmax = proj.x_limits[1]
+    if ymin is None:
+        ymin = proj.y_limits[0]
+    if ymax is None:
+        ymax = proj.y_limits[1]
+    assert_array_equal(extent, [xmin, xmax, ymin, ymax])
+    assert_array_equal(np.diff(target_x, axis=1), (xmax - xmin) / nx)
+    assert_array_equal(np.diff(target_y, axis=0), (ymax - ymin) / ny)
+
+
 def test_griding_data_std_range():
     # Data which exists inside the standard projection bounds i.e.
     # [-180, 180].


=====================================
setup.py
=====================================
@@ -96,7 +96,8 @@ def find_package_tree(root_path, root_package):
 # GEOS
 try:
     geos_version = subprocess.check_output(['geos-config', '--version'])
-    geos_version = tuple(int(v) for v in geos_version.split(b'.'))
+    geos_version = tuple(int(v) for v in geos_version.split(b'.')
+                         if 'dev' not in str(v))
     geos_includes = subprocess.check_output(['geos-config', '--includes'])
     geos_clibs = subprocess.check_output(['geos-config', '--clibs'])
 except (OSError, ValueError, subprocess.CalledProcessError):



View it on GitLab: https://salsa.debian.org/debian-gis-team/python-cartopy/-/commit/4dfdf81578a44f7325d966fd503bca7bf25b67e3

-- 
View it on GitLab: https://salsa.debian.org/debian-gis-team/python-cartopy/-/commit/4dfdf81578a44f7325d966fd503bca7bf25b67e3
You're receiving this email because of your account on salsa.debian.org.


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://alioth-lists.debian.net/pipermail/pkg-grass-devel/attachments/20200427/cb6d1096/attachment-0001.html>


More information about the Pkg-grass-devel mailing list