Reputation: 361
I came up with the following code to produce a figure in python+matplotlib:
fig = plt.figure(figsize=(10,8))
ax = fig.add_subplot(1,1,1, projection='3d')
ax.plot_surface(KX[kxl3d:kxr3d,kxl3d:kxr3d], KY[kxl3d:kxr3d,kxl3d:kxr3d],
BLP[kxl3d:kxr3d,kxl3d:kxr3d], rstride=8, cstride=8, alpha=0.4)
for idx in range(3):
ax.plot(kx[x_points]+momentum_spi[idx,0], ky[y_points]+momentum_spi[idx,1],
energy_spi[idx], linestyle='none', marker='o',
markerfacecolor=color_spi[idx], markersize=5)
ax.set_xlim(kl3d, kr3d)
ax.set_ylim(kl3d, kr3d)
ax.set_xlabel(r'$k_x[\mu m^{-1}]$')
ax.set_ylabel(r'$k_y[\mu m^{-1}]$')
ax.set_zlabel(r'$\epsilon-\omega_X[\gamma_p]$')
The output is:
My question is, how can I
Upvotes: 5
Views: 15196
Reputation: 13477
You can snap zaxis to the left with the code posted here:
tmp_planes = ax.zaxis._PLANES
ax.zaxis._PLANES = ( tmp_planes[2], tmp_planes[3],
tmp_planes[0], tmp_planes[1],
tmp_planes[4], tmp_planes[5])
view_1 = (25, -135)
view_2 = (25, -45)
init_view = view_2
ax.view_init(*init_view)
You can control the distance of label to the axis, by adding a new line, and setting linespacing
:
ax.set_xlabel('\n' + 'xlabel', linespacing=4)
Here's a complete example:
#!/usr/bin/python3
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
X = np.arange(-5, 5, 0.25)
Y = np.arange(-5, 5, 0.25)
X, Y = np.meshgrid(X, Y)
R = np.sqrt(X**2 + Y**2)
Z = np.sin(R)
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
tmp_planes = ax.zaxis._PLANES
ax.zaxis._PLANES = ( tmp_planes[2], tmp_planes[3],
tmp_planes[0], tmp_planes[1],
tmp_planes[4], tmp_planes[5])
view_1 = (25, -135)
view_2 = (25, -45)
init_view = view_2
ax.view_init(*init_view)
ax.plot_surface(X, Y, Z)
ax.set_xlabel('\n' + 'xlabel', linespacing=4)
ax.set_ylabel('ylabel')
fig.tight_layout()
fig.savefig('test.png')
(Note though that the zx and zy grid goes on the wrong side of the box. I don't know how to fix that).
Upvotes: 7
Reputation: 23500
The official way would be to use:
ax.tick_params(axis='z', pad=50)
ax.set_zlabel(r'k_z...', labelpad=30)
However, there is a bit of bad luck. With tick_params
the official API documentation for 1.3.1 says: While this function is currently implemented, the core part of the Axes3D object may ignore some of these settings. Seems to be that pad
is one of these.
With set_zlabel
the documentation says: Currently, labelpad does not have an effect on the labels.
There is a simple workaround for the second one. It is ugly but works:
ax.set_zlabel('\n' + r'$\epsilon-\omega_X[\gamma_p]$', linespacing=2.5)
You may adjust the position by adjusting the linespacing
keyword. The unit is the height of a row of text. (Beware, if you do interactive adjustments, they are not drawn unless you change the text somehow.)
For the z tick labels you could use a similar trick:
ax.set_zticklabels([" "+tl.get_text() for tl in ax.get_zticklabels()])
This allows you to adjust the position one space at a time. Of course, in math text mode you may use the spacing commands as well ('\/'
).
Upvotes: 5