As I coulnd't figure out how exactly to start a pull request here (never done that before actually),
I'm going to post my customized version of the function get_contourf_levels()
.
This will allow for passing a specific float-format of desire which will affect the labeling of the contours.
The formatting of these string-labels itself has also been improved.
def get_contourf_levels(levels, extend, float_fmt="%.2f"):
# Latest implementation using f-strings and improved formatting of all ranges
mid_levels = [
f"({float_fmt % levels[i]} - {float_fmt % levels[i+1]})"
for i in range(len(levels) - 1)
]
# Previous implementation:
#mid_levels = [float_fmt % levels[i] + '-' + float_fmt % levels[i+1] for i in range(len(levels)-1)]
# i) Decide whether to modify the mid-levels list
if extend == 'both':
return [
f"< {float_fmt % levels[0]}", *mid_levels,
f"> {float_fmt % levels[-1]}"
]
elif extend == 'max':
return [*mid_levels, f"> {float_fmt % levels[-1]}"]
elif extend == 'min':
return [f"< {float_fmt % levels[0]}", *mid_levels]
# ii) Return unchanged
else:
return mid_levels
def contourf_to_geojson_overlap(contourf,
geojson_filepath=None,
min_angle_deg=None,
ndigits=5,
unit='',
stroke_width=1,
fill_opacity=.9,
geojson_properties=None,
strdump=False,
serialize=True,
float_fmt="%.2f"):
"""Transform matplotlib.contourf to geojson with overlapping filled contours."""
polygon_features = []
contourf_idx = 0
# Pass (custom) float format to extract the contour-levels
contourf_levels = get_contourf_levels(contourf.levels,
contourf.extend,
float_fmt=float_fmt)
for collection in contourf.collections:
color = collection.get_facecolor()
for path in collection.get_paths():
for coord in path.to_polygons():
if min_angle_deg:
coord = keep_high_angle(coord, min_angle_deg)
coord = np.around(coord, ndigits) if ndigits else coord
polygon = Polygon(coordinates=[coord.tolist()])
fcolor = rgb2hex(color[0])
properties = set_contourf_properties(
stroke_width, fcolor, fill_opacity,
contourf_levels[contourf_idx], unit)
if geojson_properties:
properties.update(geojson_properties)
feature = Feature(geometry=polygon, properties=properties)
polygon_features.append(feature)
contourf_idx += 1
feature_collection = FeatureCollection(polygon_features)
return _render_feature_collection(feature_collection, geojson_filepath,
strdump, serialize)
def contourf_to_geojson(contourf,
geojson_filepath=None,
min_angle_deg=None,
ndigits=5,
unit='',
stroke_width=1,
fill_opacity=.9,
fill_opacity_range=None,
geojson_properties=None,
strdump=False,
serialize=True,
float_fmt="%.2f"):
"""Transform matplotlib.contourf to geojson with MultiPolygons."""
if fill_opacity_range:
variable_opacity = True
min_opacity, max_opacity = fill_opacity_range
opacity_increment = (max_opacity - min_opacity) / len(contourf.levels)
fill_opacity = min_opacity
else:
variable_opacity = False
polygon_features = []
# Pass (custom) float format to extract the contour-levels
contourf_levels = get_contourf_levels(contourf.levels,
contourf.extend,
float_fmt=float_fmt)
for coll, level in zip(contourf.collections, contourf_levels):
color = coll.get_facecolor()
muli = MP(coll, min_angle_deg, ndigits)
polygon = muli.mpoly()
fcolor = rgb2hex(color[0])
properties = set_contourf_properties(stroke_width, fcolor,
fill_opacity, level, unit)
if geojson_properties:
properties.update(geojson_properties)
feature = Feature(geometry=polygon, properties=properties)
polygon_features.append(feature)
if variable_opacity:
fill_opacity += opacity_increment
feature_collection = FeatureCollection(polygon_features)
return _render_feature_collection(feature_collection, geojson_filepath,
strdump, serialize)