-
-
Notifications
You must be signed in to change notification settings - Fork 7.6k
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
Enable set_{x|y|}label(loc={'left'|'right'|'center'}...) #15974
Conversation
Thanks a lot for the PR! However, I think we should make sure that there is some consensus on this before you put too much effort into it. I'm -0.5, because I'm not really sure how many people want to do this, or should, and that making it available is just adding to our already impressive kwarg list and rcParams. Is there a field where putting an axis label somewhere other than the centre is common? Are there other packages that allow axis labels to be placed this way? Whats the prior art here? |
It's the default in high energy physics. |
Can you provide some examples, e.g. links to papers? |
lib/matplotlib/axes/_axes.py
Outdated
@@ -246,6 +256,15 @@ def set_ylabel(self, ylabel, fontdict=None, labelpad=None, **kwargs): | |||
""" | |||
if labelpad is not None: | |||
self.yaxis.labelpad = labelpad | |||
if loc is None: | |||
loc = rcParams['axis.titlelocation'] | |||
cbook._check_in_list(('left', 'center', 'right'), loc=loc) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
can you screenshot how does that look?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So it's really top/bottom for y, which argues for the separate rcparams?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think top/bottom is unnecessarily adding more keywords without helping the semantics. Should be still left/right even when aligning along the y axis
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What do you mean? It's clearly at the top and the bottom?...
For example, if your y axis is oriented downwards, what do left and right correspond to?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is a downward oriented y-axis ? The only case I can think of where it could be ambiguous is if someone flipped the text alignment such that one would title head right to read it as opposed to left as it usually is. Does that happen?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, I see your point. I guess it was too subtle for me :)
I still think top/bottom are clearer (and these are names used elsewhere in the library, so we're not just making them up here), but won't block over that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this also needs to be top/bottom. Even if you think this should be left/right I was surprised that you would say this was on the “right” side of the colorbar.
I'm ok with this as a feature. We already have this for |
I think the feature is fine (... and likely to be merged faster than your drawstyle PR...), just needs polishing wrt rcParams and "top"/"bottom" vs "left"/"right" and docs? |
Testing out what we talked about on this weeks call, I am going to nominate @dopplershift to be the liaison for getting this merged. |
😱 😭 |
@timhoffm I was thinking about this, but since ha and x are lower level it would maybe make sense to me the other way around. I am not sure what's the best way to handle it, I could see either a) Ignore loc is either ha/x/y are supplied or b) raise an error if they are all supplied. |
General comment on the designThe problem really is that Managing conflicting parametersBut we need to handle the technically possible case that Behavior difference between
|
I'm fine with having a hard error as well. Indeed it was not obvious where the changes should go, but it seemed the actual Text object wouldn't have the corresponding y/x axis differentiation... The
|
We could perhaps try to deprecate the triple-title system (and support just one)... and see if anyone complains. |
Triple title is useful for a) b)c) subplot labelling with a centred title. |
Not sure what you exactly mean, but I guess that works only if you have exactly three (columns of) subplots? |
No. You put the panel label on the left “a)” often w a different font face, and the title in the centre. |
Ah, I thought you meant specifically a) (left) b) (center) c) (right) :) |
I wouldn't touch I'm just saying, even though there are some discrepancies to existing API, i think this PR is going the right direction. |
Agreed re: title. |
There was a discussion before about changing the rcparam to |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like there is consensus this is useful, so that is great. But we don’t call the axis labels “titles”. We call them “labels” so please use that term...
lib/matplotlib/axes/_axes.py
Outdated
@@ -246,6 +256,15 @@ def set_ylabel(self, ylabel, fontdict=None, labelpad=None, **kwargs): | |||
""" | |||
if labelpad is not None: | |||
self.yaxis.labelpad = labelpad | |||
if loc is None: | |||
loc = rcParams['axis.titlelocation'] | |||
cbook._check_in_list(('left', 'center', 'right'), loc=loc) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this also needs to be top/bottom. Even if you think this should be left/right I was surprised that you would say this was on the “right” side of the colorbar.
@jklymak I feel like top/bottom replacement is unnecessary.
|
Intuitively, I'd expect top/center/bottom for the yaxis. Everybody will understand that, whereas left/center/right needs some explanation. Also semantically, this is the high-level approach only specifying the location. In contrast to alignment it does not have a directional/orientational character. AFAIK switching the orientation later is not possible. So it's only a matter of parameter checking/translation when creating the colorbar. Let's also not forget that this is an advanced parameter to tune your plot. If people switch the colorbar direction, it's unclear if a vertical bottom label should be translated to a horizontal left label. IMHO being more explicit and strict in this case is actually a plus. |
Well actually semantically it is just two options - min/max along the direction of the axis whatever the orientation. Whereas an ensemble of top/bottom/right/left options hints at 4 different positions, which is not the case. But I do seem to be in the minority. The code to do this for cbar would have to have the same exact logic too:
|
@timhoffm That's not how
|
Changes should be squashed (either using a force-push or by the second reviewer through the GitHub UI when merging). |
lib/matplotlib/rcsetup.py
Outdated
@@ -988,7 +988,12 @@ def validate_webagg_address(s): | |||
raise ValueError("'webagg.address' is not a valid IP address") | |||
|
|||
|
|||
validate_axes_titlelocation = ValidateInStrings('axes.titlelocation', ['left', 'center', 'right']) | |||
_validate_axes_titlelocation = ValidateInStrings('axes.titlelocation', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah yes. Sorry I missed that; it'll need to start public for now (and get properly deprecated later).
lib/matplotlib/axes/_axes.py
Outdated
_protected_kw = ['x', 'horizontalalignment', 'ha'] | ||
if any([k in kwargs for k in _protected_kw]): | ||
if loc is not None: | ||
raise KeyError('Specifying *loc* is disallowed when any of ' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be a TypeError (it's a basically a signature mismatch, which normally raise TypeErrors).
lib/matplotlib/axes/_axes.py
Outdated
_protected_kw = ['y', 'horizontalalignment', 'ha'] | ||
if any([k in kwargs for k in _protected_kw]): | ||
if loc is not None: | ||
raise KeyError('Specifying *loc* is disallowed when any of ' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
as above
looks like you messed up the rebase :( |
indeed |
flake8 is still unhappy: https://travis-ci.com/matplotlib/matplotlib/jobs/277655865#L2387 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Anyone can merge after CI passes.
Thanks for the contribution :) |
PR Summary
Addressed #15839 by adding functionality analogous to axes.set_title(loc="") for x/y axis and cbar axis as well as new rcParam to have a default config
PR Checklist