Reputation: 235
I am trying to label multiple maximum but unable to display them properly. Also the label is appearing too far from the point overlapping with the legend.
import matplotlib.pyplot as plt
import numpy as np
x1,y1= np.loadtxt('MaxMin1.txt', dtype=str, unpack=True)
x1 = x1.astype(int)
y1 = y1.astype(float)
x2,y2= np.loadtxt('MaxMin2.txt', dtype=str, unpack=True)
x2 = x2.astype(int)
y2 = y2.astype(float)
x3,y3= np.loadtxt('MaxMin3.txt', dtype=str, unpack=True)
x3 = x3.astype(int)
y3 = y3.astype(float)
#-------------------------------------------------------------
def annot_max(x,y, ax=None):
xmax = x[np.argmax(y)]
ymax = y.max()
text= "x={:.3f}, y={:.3f}".format(xmax, ymax)
if not ax:
ax=plt.gca()
bbox_props = dict(boxstyle="square,pad=0.3", fc="w", ec="k", lw=0.72)
arrowprops=dict(arrowstyle="->",connectionstyle="angle,angleA=0,angleB=60")
kw = dict(xycoords='data',textcoords="axes fraction",
arrowprops=arrowprops, bbox=bbox_props, ha="left", va="top")
ax.annotate(text, xy=(xmax, ymax), xytext=(0.94,0.96), **kw)
#-------------------------------------------------------------
fig=plt.figure()
fig.show()
ax=fig.add_subplot(111)
ax.plot(x1,y1,c='b',ls='-',label='Recovery',fillstyle='none')
ax.plot(x2,y2,c='g',ls='-',label='Normal')
ax.plot(x3,y3,c='r',ls='-',label='No-Recovery')
annot_max(x1,y1)
annot_max(x2,y2)
annot_max(x3,y3)
plt.legend(loc=1)
# naming the x axis
plt.xlabel('<------Instances(count)------>')
# naming the y axis
plt.ylabel('Acceleration (m/sq.sec)')
# giving a title to my graph
plt.title('Fall Detection Comparison graph')
plt.show()
And the output I got Output Graph I am just beginning with python so very small hint may not be understandable by me.Please help.
Upvotes: 5
Views: 4130
Reputation: 36635
You need yo change function annot_max
.
First of all, all your labels appear in the same place according to xytext=(0.94,0.96)
. You have to specify label position according to coordinates of xmax and ymax as below.
Then change textcoords
to data
value to manipulate a label position according to data not axes fraction. In my example xytext=(xmax+.5,ymax+5)
means that location of label box will shifted by +.5 point from xmax and +5 points by ymax (you have to use your own values according to your data).
But I recommend to place your labels manually since you have 3 maximum (specify a location of every label box in argument xytext
like xytext=(100,40)
- your 1st maximum).
Matplotlib can not avoid overlapping of text boxes automatically.
To squeeze label box you can place text in two rows, i.e., text= "x={:.3f},\ny={:.3f}".format(xmax, ymax)
.
import matplotlib.pyplot as plt
import numpy as np
x1=np.array([1,2,3,4,5,6,7,8,9,10])
x2 = x1[:]
x3 = x1[:]
y1=np.array([1,2,3,100,5,6,7,8,9,10])
y2=np.array([50,2,3,4,5,6,7,8,9,10])
y3=np.array([1,2,3,4,5,6,75,8,9,10])
#-------------------------------------------------------------
def annot_max(x,y, ax=None):
xmax = x[np.argmax(y)]
ymax = y.max()
text= "x={:.3f}, y={:.3f}".format(xmax, ymax)
if not ax:
ax=plt.gca()
bbox_props = dict(boxstyle="square,pad=0.3", fc="w", ec="k", lw=0.72)
arrowprops=dict(arrowstyle="->",connectionstyle="angle,angleA=0,angleB=60")
kw = dict(xycoords='data',textcoords="data",
arrowprops=arrowprops, bbox=bbox_props, ha="left", va="top")
ax.annotate(text, xy=(xmax, ymax), xytext=(xmax+.5,ymax+5), **kw)
#-------------------------------------------------------------
fig=plt.figure()
fig.show()
ax=fig.add_subplot(111)
ax.plot(x1,y1,c='b',ls='-',label='Recovery',fillstyle='none')
ax.plot(x2,y2,c='g',ls='-',label='Normal')
ax.plot(x3,y3,c='r',ls='-',label='No-Recovery')
annot_max(x1,y1)
annot_max(x2,y2)
annot_max(x3,y3)
plt.legend(loc=1)
# naming the x axis
plt.xlabel('<------Instances(count)------>')
# naming the y axis
plt.ylabel('Acceleration (m/sq.sec)')
# giving a title to my graph
plt.title('Fall Detection Comparison graph')
plt.show()
Upvotes: 4