4

I am trying to draw a grid using matplotlib. The zorder of the grid should be behind all other lines in the plot. My problem so far is that the minor grid lines are always drawn in front of the major grid lines i.e.

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import MultipleLocator, FormatStrFormatter

plt.rc('text', usetex=True)
plt.rc('font', family='serif')

f = plt.figure(figsize=(4,4))
ax = f.add_subplot(111)

ax.xaxis.set_minor_locator(MultipleLocator(1))
ax.xaxis.set_major_locator(MultipleLocator(10))
ax.yaxis.set_minor_locator(MultipleLocator(1))
ax.yaxis.set_major_locator(MultipleLocator(10))

majc ="#3182bd"
minc ="#deebf7"

ax.xaxis.grid(True,'minor',color=minc, ls='-', lw=0.2)
ax.yaxis.grid(True,'minor',color=minc, ls='-', lw=0.2)
ax.xaxis.grid(True,'major',color=majc, ls='-')
ax.yaxis.grid(True,'major',color=majc,ls ='-')
ax.set_axisbelow(True)

x = np.linspace(0, 30, 100)
ax.plot(x, x, 'r-', lw=0.7)

[line.set_zorder(3) for line in ax.lines]
plt.savefig('test.pdf')

Any suggestions? Thank you.

EDIT: close-up example enter image description here

jrsm
  • 1,595
  • 2
  • 18
  • 39

1 Answers1

4

Even more specifically, it looks like it draws vertical majors, vertical minors, horizontal majors, horizontal minors, and plotted lines, in that order. Probably pretty deep in the matplotlib basics.

For the colors you're using, you could work around by distinguishing major and minor by alpha, not RGB. Changing two lines of your example:

ax.xaxis.grid(True,'minor',color=majc, alpha=0.2, ls='-', lw=0.2)
ax.yaxis.grid(True,'minor',color=majc, alpha=0.2, ls='-', lw=0.2)

result:

enter image description here

cphlewis
  • 15,759
  • 4
  • 46
  • 55
  • 1
    the problem with that approach is that pdf doesn't support transparency or am i wrong? thx for your reply – jrsm Jul 04 '15 at 21:17
  • I saved to pdf and that's the result I got (literally only changed the two lines I show). If pdf doesn't handle transparency, the "flattening" algorithm is handling the colors correctly. – cphlewis Jul 04 '15 at 22:43
  • It seems you are right. I think your reply is a good workaround, but it would be nice to know what goes wrong in the maplotlib api and how to fix it. – jrsm Jul 04 '15 at 23:04
  • I'm not a matplotlib developer, but I think this might be a bug in the internals, yes; the docstring for ax.xaxis.grid says " *kwargs* are used to set the line properties of the grids ", but I can't get the vertical gridlines on top/drawn second with any set of zorder values I've tried. – cphlewis Jul 05 '15 at 08:39
  • @cphlewis. I know this is an old comment, but could you elaborate on the flattening algorithm? I can't find it anywhere. Some PDF writer/reader combinations don't handle transparency well and "flattening" would be a nice workaround. – bfris Jul 29 '21 at 18:42
  • @bfris I've forgotten writing this, but I seem to have been using transparency in matplotlib as a workaround to get the PDF to look the same as it would have with the (matplotlib) zorder we wanted. I'm assuming the existence of a "flattening" algorithm I don't know anything about. – cphlewis Aug 01 '21 at 20:34
  • 1
    @cphlewis. That's a shame. I may have to ask this as a separate question. I have discovered that there is a corner case that pops up for me a lot. When you create a PDF from LibreOffice with SVGs, some PDF readers (like Acrobat) will crash if there is transparency in the SVG. – bfris Aug 02 '21 at 15:48
  • That really does sound like a PDF problem, separate from the [known issues with zorder in matplotlib grids](https://stackoverflow.com/questions/31506361/grid-zorder-seems-not-to-take-effect-matplotlib) – cphlewis Aug 03 '21 at 19:48