如何在3D图中旋转偏移文本?

5

我正在尝试使用 Matplotlib 绘制一个带有偏移文本刻度的三维图形。为此,我使用了 ImportanceOfBeingErnest 的自定义坐标轴主要格式化程序,以便将此刻度以 LaTeX 格式表示:

import matplotlib
import matplotlib.pyplot as plt
import matplotlib.ticker as ticker
from mpl_toolkits.mplot3d import Axes3D  
from matplotlib import cm
import numpy as np

class OOMFormatter(matplotlib.ticker.ScalarFormatter):
    def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=True):
        self.oom = order
        self.fformat = fformat
        matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
    def _set_order_of_magnitude(self):
        self.orderOfMagnitude = self.oom
    def _set_format(self, vmin=None, vmax=None):
        self.format = self.fformat
        if self._useMathText:
             self.format = r'$\mathdefault{%s}$' % self.format


x = np.linspace(0, 22, 23)
y = np.linspace(-10, 10, 21)
X, Y = np.meshgrid(x, y)
V = -(np.cos(X/10)*np.cos(Y/10))**2*1e-4

fig, ax = plt.subplots(subplot_kw={"projection": "3d"})
surf = ax.plot_surface(X, Y, V, cmap=cm.jet,
                       linewidth=0, antialiased=False)
ax.zaxis.set_major_formatter(OOMFormatter(int('{:.2e}'.format(np.min(V)).split('e')[1]), mathText=True))
ax.zaxis.set_rotate_label(False) 
ax.set_xlabel(r'$x$ (cm)', size=20, labelpad=10)
ax.set_ylabel(r'$y$ (cm)', size=20, labelpad=10)
ax.set_zlabel(r'$A_z$', size=20, labelpad=10)

这导致出现以下图像:Figure 1: 初始图表 请注意,比例尺(z轴偏移文本,x 10^{-4})被旋转了90度。为了解决这个问题,我尝试访问偏移文本的元素并将其旋转为0:
ax.zaxis.get_offset_text().set_rotation(0)
ax.zaxis.get_offset_text().get_rotation()
>>> 0

然而这没有任何用,因为偏移的文本并没有旋转一英寸。之后我尝试在运行绘图函数时打印文本对象:

surf = ax.plot_surface(X, Y, V, cmap=cm.jet,
                       linewidth=0, antialiased=False)
.
.
.
print(ax.zaxis.get_offset_text())
>>>Text(1, 0, '')

这让我想到,也许偏移文本并没有存储在这个变量中。但是,当我运行相同的命令而不调用绘图函数时,它返回了我预期的结果。
print(ax.zaxis.get_offset_text())
>>>Text(-0.1039369506424546, 0.050310729257045626, '$\\times\\mathdefault{10^{−4}}\\mathdefault{}$')

我做错了什么?


你应该使用你所介绍的类吗? 你也可以使用通过ax.zaxis.get_offset_text()获得的幂符号字符串,并用text2d()进行注释。在这样做之前,需要隐藏现有的注释。 - r-beginners
1个回答

3
我必须说,这是一个非常优秀和有趣的问题,我曾经花了一段时间思考它...
你可以使用ax.zaxis.get_offset_text()访问偏移文本。很容易将其隐藏ot.set_visible(False),但出于某种未知原因,旋转ot.set_rotation(90)无效。我尝试使用print(ot.get_text())打印文本值,但除非绘制了图表,否则不会输出任何内容。只有在绘制图表之后,它才返回'$\\times\\mathdefault{10^{-4}}\\mathdefault{}$'。这告诉我这可能是问题的源头。无论你对偏移文本应用什么操作,在图形生成的最后一步中都会被覆盖,并且失败。
我得出结论,最好的方法是隐藏偏移并手动注释图形。你可以使用以下代码片段自动完成:
```python # 隐藏偏移 ot = ax.zaxis.get_offset_text() ot.set_visible(False)
# 添加注释 ax.text(x, y, '文本', fontsize=12, color='red') ```
ax.zaxis.get_offset_text().set_visible(False)
exponent = int('{:.2e}'.format(np.min(V)).split('e')[1])
ax.text(ax.get_xlim()[1]*1.1, ax.get_ylim()[1], ax.get_zlim()[1],
        '$\\times\\mathdefault{10^{%d}}\\mathdefault{}$' % exponent)

结果:

具有自定义偏移文本的图形


(翻译提示:该内容为HTML代码,无需翻译)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接