X Tutup
Skip to content

ENH: Give control whether twinx() or twiny() overlays the main axis#31181

Open
sanrishi wants to merge 5 commits intomatplotlib:mainfrom
sanrishi:fix-twinx-zorder-31122
Open

ENH: Give control whether twinx() or twiny() overlays the main axis#31181
sanrishi wants to merge 5 commits intomatplotlib:mainfrom
sanrishi:fix-twinx-zorder-31122

Conversation

@sanrishi
Copy link

@sanrishi sanrishi commented Feb 20, 2026

PR summary

This PR addresses the ergonomics issue where twinned axes default to overlaying the main axis, obscuring the primary data unless users manually manipulate z-orders and patch visibilities.

Key Changes:

  • New delta_zorder Parameter: Exposed delta_zorder as a keyword-only argument in twinx() and twiny() (and updated the type stubs in _base.pyi). This allows users to easily position twins relative to the main axes (e.g., passing delta_zorder=-1 puts the twin behind the main data).

  • Automated Patch Visibility: Added _update_twinned_axes_patch_visibility() which evaluates the whole group of twinned axes. The group is sorted by zorder (using figure insertion order as a tie-breaker), ensuring that only the bottom-most axis has a visible background patch.

  • Reactive Logic: Extended set_zorder and set_frame_on in _AxesBase to trigger the patch visibility update. If a user dynamically changes the z-order or frame state of any axis in a twinned group after creation, the background visibility automatically corrects itself.

  • Respects frameon: The visibility logic explicitly checks ax.get_frame_on() so it does not force a background onto an axis where the user explicitly disabled the frame.

  • Cleanup: Removed the legacy, hardcoded patch.set_visible(False) calls in twinx() and twiny().

Documentation & Testing:

Added a new gallery example (galleries/examples/subplots_axes_and_figures/twin_axes_zorder.py) demonstrating how to plot overlapping data with a background twin.

Added comprehensive tests in lib/matplotlib/tests/test_axes.py covering default behavior, custom delta_zorder stacking, multiple twins, and dynamic visibility updates. Verified locally that regression tests pass.

Here is a quick test using ax2 = ax.twinx(delta_zorder=-1) with a semi-transparent blue line on the main axis and a solid red line on the twin. As requested in the original issue, the main axis data (blue) is correctly layered on top of the twin axis data (red), and the background patches are handling the transparency perfectly!
image

PR checklist

@github-actions github-actions bot added the Documentation: examples files in galleries/examples label Feb 20, 2026
@sanrishi
Copy link
Author

sanrishi commented Feb 20, 2026

@rcomer @timhoffm @Archiljain Ready for review!

@Archiljain
Copy link
Contributor

Thanks for pushing this forward — this aligns well with the conclusions from the issue discussion.
I’ll review it in more detail, but at a glance the approach of zorder-based stacking with automated patch visibility makes sense.

@sanrishi
Copy link
Author

sanrishi commented Feb 20, 2026

Yea!
That's why this type of change/PR requires a day of analysis first to find best approach!

@timhoffm
Copy link
Member

Please explain you reasoning why you choose zorder over delta_zorder. The current implementation does not reflect the state of the discussion in #31122 (still open with a tendency towards delta_zorder). Implementing something different from the discussion without explantion gives the impression you are not really understanding the topic or paying not enough attention.

@sanrishi
Copy link
Author

Apologies for the oversight! I was a bit busy and lost track of in the issue discussion.

Because zorder is used everywhere else in the Matplotlib source code, I mistakenly just followed that existing pattern. I will update the PR to use delta_zorder now, as I agree it makes positioning much easier for the user.

@sanrishi sanrishi force-pushed the fix-twinx-zorder-31122 branch from 6e8e752 to 1ab3a9f Compare February 21, 2026 11:47
@timhoffm
Copy link
Member

I was a bit busy and lost track of in the issue discussion.

As a general advice: You are active on many topics. Your contributions are more valuable with more quality and less volume. Take time and care to do one thing right at a time and only then move to the next topic.

@sanrishi
Copy link
Author

sanrishi commented Feb 21, 2026

I consider you as my elder brother as i not have any big brother/sister who guide me, you are the one who guiding me, i remembered your every word since i joined with matplotlib

Your contributions are more valuable with more quality and less volume.

I was bit greedy i will definitely take care of that next time! Thanks for all @timhoffm

@sanrishi
Copy link
Author

sanrishi commented Mar 4, 2026

Could you have a moment @timhoffm, i added a tested png after testing locally!
How is this looking to you?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[ENH]: Give control whether twinx() or twiny() overlays the main axis

3 participants

X Tutup