I have created a figure with two subplots. On the left is a 3D surface plot and on the right side is 2D projection of the 3D plot with imshow. I want the colormap of the imshow plot to be linked to the 3D plot. But the scale does not fit.
import numpy as np
import matplotlib.pyplot as plt
id = np.arange(-600,750,150)
iq = np.arange(-600,750,150)
xx,yy = np.meshgrid(id,iq)
T = np.array([[-8988, -8697.5, -7847, -6923, -5610.5, -4536, -3374.35, -2572.85, -1987.65],
[-8162, -7910, -7206.5, -6160, -4798.5, -3476.55, -2479.4, -1711.5, -1374.45],
[-6513.5, -6814.5, -6398, -5218.5, -3706.5, -2362.15, -1414.7, -1013.6,-883.05],
[-4224.5,-4669, -4686.5, -3755.5, -2217.6, -1079.4, -591.85, -313.005,-211.925],
[0, 0, 0, 0, 0, 0, 0, 0, 0],
[4420.5, 4833.5, 4749.5, 3787, 2221.1, 1054.55, 567.35, 280.42, 146.51],
[6793.5, 7017.5, 6510, 5260.5, 3692.5, 2295.3, 1360.45, 914.55, 806.4],
[8421, 8008, 7287, 6160, 4725, 3400.25, 2318.4, 1628.2, 1285.55],
[9170, 8750, 7864.5, 6874, 5498.5, 4413.5, 3206.7, 2351.3, 1865.5]])
m = plt.cm.ScalarMappable()
m.set_array(T)
m.set_clim(-9000, 9000) # optional
fig = plt.figure(1, figsize=(12,6))
ax = fig.add_subplot(121, projection='3d')
ax.set_xlabel(r'$I_d$', fontsize=15)
ax.set_ylabel(r'$I_q$', fontsize=15)
ax.set_zlabel(r'$T$', fontsize=15)
ax.plot_surface(xx, yy, T, cmap=m.cmap, norm = m.norm)
ax2 = fig.add_subplot(122)
ax2.imshow(T, cmap=m.cmap, norm=m.norm,
extent=(np.min(xx), np.max(xx), np.min(yy), np.max(yy)),
interpolation=None)
cbar = fig.colorbar(
plt.cm.ScalarMappable(),
ax=ax2
)
plt.tight_layout()
plt.show()
I added a mappable to the plot but unfortunately the colormap is not linked to values of the z axis of the surface plot. The scale only shows values between 0 and 1. How can I connect the values of the T Matix to the colormap ?
There are two things here:
The default origin
for imshow
(on your 2D plot) is "upper"
, meaning the vertical axis points downwards by default. Since you have the lower numbers at the bottom of your axis, you want to set origin="lower"
.
You can use the mappable
object that is created by imshow
to create the colorbar, which will then make the colorbar limits match the data. Below I give the mappable returned by ax2.imshow
the name im
, which you can then use in fig.colorbar
.
im = ax2.imshow(T, cmap=m.cmap, norm=m.norm,
origin='lower',
extent=(np.min(xx), np.max(xx), np.min(yy), np.max(yy)),
interpolation=None)
cbar = fig.colorbar(im, ax=ax2)