Skip to content

Navigation Menu

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit bb30bef

Browse filesBrowse files
committed
MNT: Registered 3rd party scales do not need an axis parameter anymore
First step of #29349.
1 parent a18354a commit bb30bef
Copy full SHA for bb30bef

File tree

3 files changed

+63
-2
lines changed
Filter options

3 files changed

+63
-2
lines changed
+10Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
3rd party scales do not need to have an *axis* parameter anymore
2+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3+
4+
Since matplotlib 3.1 `PR 12831 <https://github.com/matplotlib/matplotlib/pull/12831>`_
5+
scales should be reusable and therefore independent of the Axis. Therefore the use of
6+
of the *axis* parameter in the ``__init__`` had been discouraged. However, that
7+
parameter was still necessary for API compatibility. This is no longer the case.
8+
9+
`.register_scale` now accepts scale classes with and without this parameter.
10+
3rd party scales can and should remove that parameter.

‎lib/matplotlib/scale.py

Copy file name to clipboardExpand all lines: lib/matplotlib/scale.py
+16-1Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -690,6 +690,9 @@ def limit_range_for_scale(self, vmin, vmax, minpos):
690690
'functionlog': FuncScaleLog,
691691
}
692692

693+
# caching of signature info
694+
_scale_has_axis_parameter = {}
695+
693696

694697
def get_scale_names():
695698
"""Return the names of the available scales."""
@@ -706,7 +709,19 @@ def scale_factory(scale, axis, **kwargs):
706709
axis : `~matplotlib.axis.Axis`
707710
"""
708711
scale_cls = _api.check_getitem(_scale_mapping, scale=scale)
709-
return scale_cls(axis, **kwargs)
712+
713+
# We support scales that may or may not have an initial *axis* parameter.
714+
# This information is cached, so that we do not need to inspect the signature
715+
# on every time we create a scale.
716+
if scale not in _scale_has_axis_parameter:
717+
_scale_has_axis_parameter[scale] = (
718+
"axis" in inspect.signature(scale_cls).parameters
719+
)
720+
721+
if _scale_has_axis_parameter[scale]:
722+
return scale_cls(axis, **kwargs)
723+
else:
724+
return scale_cls(**kwargs)
710725

711726

712727
if scale_factory.__doc__:

‎lib/matplotlib/tests/test_scale.py

Copy file name to clipboardExpand all lines: lib/matplotlib/tests/test_scale.py
+37-1Lines changed: 37 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,12 @@
66
LogTransform, InvertedLogTransform,
77
SymmetricalLogTransform)
88
import matplotlib.scale as mscale
9-
from matplotlib.ticker import AsinhLocator, LogFormatterSciNotation
9+
from matplotlib.ticker import (
10+
AsinhLocator, AutoLocator, LogFormatterSciNotation,
11+
NullFormatter, NullLocator, ScalarFormatter
12+
)
1013
from matplotlib.testing.decorators import check_figures_equal, image_comparison
14+
from matplotlib.transforms import IdentityTransform
1115

1216
import numpy as np
1317
from numpy.testing import assert_allclose
@@ -293,3 +297,35 @@ def test_bad_scale(self):
293297
AsinhScale(axis=None, linear_width=-1)
294298
s0 = AsinhScale(axis=None, )
295299
s1 = AsinhScale(axis=None, linear_width=3.0)
300+
301+
302+
def test_custom_scale_without_axis():
303+
"""
304+
Test that one can register and use custom scales that don't take an *axis* param.
305+
"""
306+
class CustomTransform(IdentityTransform):
307+
pass
308+
309+
class CustomScale(mscale.ScaleBase):
310+
name = "custom"
311+
312+
def __init__(self):
313+
self._transform = CustomTransform()
314+
315+
def get_transform(self):
316+
return self._transform
317+
318+
def set_default_locators_and_formatters(self, axis):
319+
axis.set_major_locator(AutoLocator())
320+
axis.set_major_formatter(ScalarFormatter())
321+
axis.set_minor_locator(NullLocator())
322+
axis.set_minor_formatter(NullFormatter())
323+
324+
try:
325+
mscale.register_scale(CustomScale)
326+
fig, ax = plt.subplots()
327+
ax.set_xscale('custom')
328+
assert isinstance(ax.xaxis.get_transform(), CustomTransform)
329+
finally:
330+
# cleanup - there's no public unregister_scale()
331+
del mscale._scale_mapping["custom"]

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.