python-3.xmacosmatplotlibmatplotlib-widget

Matplotlib MultiCursor is not displaying on multiple subplots


I have a Matplotlib plot with 6 adjacent, vertical plots, all with sharey=True. When I move the cursor on any one plot, I want a horizontal cursor/marker to show on the other 5. I understand MultiCursor is the best method. I have looked at this and it works correctly when I run it, all be it on horizontal plots. My code is not running in any GUI (if it makes a difference), but nor is this demo. Matplotlib gallery demo

When I try it with my plot, nothing happens. The plot code below only links two subplots rather than all 6, but it is not functioning anyway. I have imported MultiCursor in the main body of the code.

def Raw_Plot():  #Raw Data Plot

global unitW
fig, axs=plt.subplots(1,6,constrained_layout=True, sharey=True)
fig.suptitle(tail)
axs[0].plot(df['Cone'],df['Depth'],'r-',linewidth=0.8)
axs[0].set_xlabel('$q_c$ (MPa)')
axs[0].set_ylabel('Depth (m)')
axs[0].set_title('Cone resistance',fontsize=10)
axs[0].grid()
axs[0].set_ylim(dmax,0)
axs[0].set_xlim(0,None)
axs[1].plot(df['Friction'],df['Depth'],'b-',linewidth=0.8)
axs[1].set_xlabel('$f_s$ (MPa)')
axs[1].set_title('Sleeve Friction',fontsize=10)    
axs[1].grid()
axs[1].set_xlim(0,None)
axs[1].set_ylabel('Depth (m)')
axs[2].plot(df['Pore'],df['Depth'],'g-',linewidth=0.8)
axs[2].plot(df['AmbientM'],df['Depth'],'r-',linewidth=0.8)
axs[2].plot(df['Bq'],df['Depth'],'g--',linewidth=0.8)
axs[2].set_xlabel('$U_2$, $U_0$ (MPa) & $B_q$')
axs[2].set_title('Raw, Ambient and \n Normalised Pore Pressures',fontsize=10)    
axs[2].grid()
axs[2].set_ylabel('Depth (m)')
axs[3].plot(df['Rf'],df['Depth'],'c-',linewidth=0.8,label='$R_f$')
axs[3].plot(df['Fr'],df['Depth'],'b-',linewidth=0.8, label='$F_r$')
axs[3].set_xlabel('$F_r$ & $R_f$ (%)')
axs[3].set_xlim(0,10)
axs[3].set_title('Friction Ratios',fontsize=10)
axs[3].set_ylabel('Depth (m)',fontsize=10)
axs[3].legend(loc='upper right',bbox_to_anchor=(1,1),fontsize=6.5)
axs[3].grid()
axs[4].plot(df['Qtn'],df['Depth'],'r-',linewidth=0.8)
axs[4].set_xlabel('$Q_{tn}$')
axs[4].set_ylabel('Depth (m)')
axs[4].set_title('Normalised Cone resistance',fontsize=10)
axs[4].grid()
axs[4].set_ylim(dmax,0)
axs[4].set_xlim(0,None)
axs[5].plot(df['GammaS'],df['Depth'],'c-',linewidth=0.8, label='Calculated')
axs[5].plot(df['GaDef'],df['Depth'],'b-',linewidth=1.0, label='Default '+str(unitW))
axs[5].legend(loc='upper right',bbox_to_anchor=(1,1),fontsize=6.5)
axs[5].set_xlabel('$\gamma$ $(kN/m^3)$')
axs[5].set_xlim(14,20)
axs[5].xaxis.set_major_formatter(FormatStrFormatter('%.1f'))    
axs[5].set_title('Soil Unit Weight',fontsize=10)
axs[5].set_ylabel('Depth (m)')
axs[5].grid()

fig.canvas.set_window_title(tail)
multi=MultiCursor(fig.canvas,(axs[1],axs[4]),color='r',lw=1)
plt.ion() #makes plot non-blocking - Can open multiple plots
plt.show()

Solution

  • At least when using Spyder as my editor, multiple plots are possible without needing plt.ion().

    multi = MultiCursor(fig.... was still not being actioned ("local variable multi is assigned but never used") and there was no cursor on multiple subplots.

    I have resolved this by using plt.multi = MultiCursor(fig.... This still only works on one plot at a time but at least I have the MultiCursor on which ever is the last plot to open.