Видимость заштрихованного контура matplotlib зависит от программы чтения PDF
Я борюсь с pdf бэкэндом matplotlib и функцией contourf. Я пытаюсь нанести запретные зоны на двухцветную карту. Запрещенные области представлены заштрихованным контуром с прозрачным (альфа =0,4) черным цветом. используемый код приведен ниже, с двумя классами, написанными для генерации пользовательской легенды:
import matplotlib
print matplotlib.__version__
import matplotlib.patches as mpatches
class ConstrainedArea(object):
def __init__(self,axe,_xdata,_ydata,_zdata,boundaries,fc='none',ec='none',lw=None,alpha=None,hatch='//',ls='-',fill=False,label=None):
self.bnd = boundaries
self.fc = fc
self.ec = ec
self.lw = lw
self.ls = ls
self.al = alpha
self.hh = hatch
self.fl = fill
self.lb = label
self.ctr = axe.contour(_xdata,_ydata,_zdata,boundaries,linewidths=lw,colors=ec,linestyles=ls)
#self.ctf = axe.contourf(_xdata,_ydata,_zdata,boundaries,hatches=hatch,colors=fc,facecolors=fc,alpha=alpha)
self.ctf = axe.contourf(_xdata,_ydata,_zdata,boundaries,hatches=hatch,colors=fc,alpha=alpha,antialiased=False)
pass
class ConstrainedAreaHandler(object):
def legend_artist(self,legend,orig_handle,fontsize,handlebox):
x0,y0 = handlebox.xdescent,handlebox.ydescent
wi,he = handlebox.width,handlebox.height
patch = mpatches.Rectangle([x0,y0],wi,he,facecolor=orig_handle.fc,edgecolor=orig_handle.ec,hatch=orig_handle.hh,lw=orig_handle.lw,ls=orig_handle.ls,fill=orig_handle.fl,transform=handlebox.get_transform(),label=orig_handle.lb)
handlebox.add_artist(patch)
if __name__ == "__main__":
matplotlib.rcParams['backend'] = 'PDF'
import numpy,matplotlib.pyplot as plt
xs, ys = numpy.mgrid[0:30, 0:40]
zs = (xs - 15) ** 2 + (ys - 20) ** 2 + (numpy.sin(ys) + 10) ** 2
fig = plt.figure('test',figsize=(16.0,11.8875))
axe = fig.add_subplot(111)
pcm = axe.pcolormesh(xs,ys,zs,shading='gouraud')
cas = []
for bnd,hch,ls,lb in zip([[zs.min(),200],[400,zs.max()]],['/','\\'],['-','--'],[r'$f<200$',r'$f>400$']):
cas.append(ConstrainedArea(axe,xs,ys,zs,bnd,hatch=hch,fc='k',ec='k',lw=3,ls=ls,alpha=0.2,fill=False,label=lb))
cbr = fig.colorbar(pcm)
legframe = axe.legend(cas,[c.lb for c in cas],loc=3,handler_map={ConstrainedArea:ConstrainedAreaHandler()},ncol=3,fontsize=matplotlib.rcParams['font.size']*1.2**4,numpoints=1,framealpha=0.8)
#fig.savefig('test.pdf',bbox_inches='tight',facecolor='none',edgecolor='none',transparent=True)
fig.savefig('test.pdf',bbox_inches='tight',transparent=True)
После прочтения треков о проблемах с matplotlib, GitHub matplotlib выпуск 3023 и GitHub matplotlib выпуск 7421, я установил matplotlib 2.0.0, думая, что это решит мою проблему, но это не так.
ОПРЕДЕЛЕНИЕ ПРОБЛЕМЫ
Используя бэкэнд pdf, я сохраняю результат в формате pdf, но, читая один и тот же файл с помощью evince, okular или Acrobat Reader, получаю разные скриншоты, как показано на рисунках ниже:
ИНФОРМАЦИЯ
Ожидаемый результат - тот, который дан evince (видимые штриховки). Как уже упоминалось в других треках, растеризация объекта contourf дает ожидаемый результат, но мне нужны векторные изображения. Кроме того, если растеризованные штриховки используются с высоким dpi (>300), ширина штриховки стремится к 0, что приводит к неправильному выводу. Наконец, я обнаружил, что этот PDF-файл, созданный Matplotlib, нельзя просмотреть с помощью программы Acrobat Reader, которая привела к этому решению:
- откройте выходной pdf файл matplotlib с помощью evince
- распечатать в PDF
- визуализируйте вывод, напечатанный на evince, с помощью okular, который дает скриншот ниже:
Заранее большое спасибо за любое объяснение или решение этой проблемы. Не стесняйтесь, если нужны другие детали / информация,
Тарик