我必须在图像的特定位置放置一个圆圈。问题在于,图像以半对数比例绘制,除非我使用某些特定的变换,否则会使圆失真。但是,当我这样做时,圆会根据我将图像另存为A PDF还是PNG来改变位置。这是MWE:
import matplotlib.pyplot as plt
from matplotlib.patches import Ellipse, Circle
import numpy as np
from matplotlib.text import OffsetFrom
fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(11,5), squeeze=False,
gridspec_kw = {'width_ratios':[3, 1]}, subplot_kw=dict(aspect="auto"))
x=np.logspace(-2,1)
y=np.linspace(.5,0,x.size)
ax=axes[0,0]
ax.semilogx(x, y)
circ = Circle((.5, .5), .1, transform="none", facecolor="none", edgecolor="k")
ax.add_patch(circ)
ax.set(xlim=(1e-2, 1e1), ylim=(0, .6))
fig.savefig("circle.png")
这是两个输出,具体取决于我如何保存图像:
我也尝试过使用transform=ax.transAxes
,尽管它保留了圆的位置,但在半对数转换后,它不再是圆了。
有什么想法吗?
答案 0 :(得分:1)
我认为这是known issue。问题在于,pdf总是以dpi为72保存,而png会考虑数字dpi。
但是,我建议不要使用Annotation BBox tools来代替在图形或轴上直接创建一个圆。
您可以创建一个内部带有DrawingArea的AnnotationBBox。 DrawingArea可能包含圆。 DrawingArea的坐标为点。 AnnotationBbox可以放置在轴或图形上的任何位置,并且可以在其他坐标系(例如轴坐标或数据坐标)中指定其位置。
import matplotlib.pyplot as plt
from matplotlib.patches import Ellipse, Circle
import numpy as np
from matplotlib.offsetbox import DrawingArea, AnnotationBbox
fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(11,5), squeeze=False,
gridspec_kw = {'width_ratios':[3, 1]}, subplot_kw=dict(aspect="auto"))
x=np.logspace(-2,1)
y=np.linspace(.5,0,x.size)
ax=axes[0,0]
ax.semilogx(x, y)
##################
# Axes Coordinates
# Create circle of 10 points radius
da = DrawingArea(1,1, 0, 0)
p = Circle((0, 0), 10)
da.add_artist(p)
# Place box in the middle ((.5,.5)) of the axes.
# Add circle inside drawing area to box
ab = AnnotationBbox(da, (.5,.5), xycoords='axes fraction',
box_alignment=(0, 0), frameon=False, pad=0.0)
ax.add_artist(ab)
###################
# Data Coordinates
# Create circle of 10 points radius
da = DrawingArea(1,1, 0, 0)
p = Circle((0, 0), 10, color="crimson")
da.add_artist(p)
# Place box at (0.1,0.3) in data coordinates.
# Add circle inside drawing area to box
ab = AnnotationBbox(da, (0.1,0.3), xycoords='data',
box_alignment=(0, 0), frameon=False, pad=0.0)
ax.add_artist(ab)
ax.set(xlim=(1e-2, 1e1), ylim=(0, .6))
fig.savefig("circle.png")
fig.savefig("circle.pdf")
plt.show()
生成的pdf和png现在相同