Matplotlib plot_surface transparency artefact

fro*_*nts 7 python numpy matplotlib

我试图从一组指定z值的数据中绘制3D表面.虽然我设置了alpha = 1.0,但我得到了一些奇怪的透明效果,我可以在表面看到.

在绘图时和保存到文件时(包括png和pdf)都会出现人工制品: 在此输入图像描述

我试过改变线宽,并将步幅数从1改为10(在后一种情况下,由于分辨率太粗糙,表面不可见).

问:我怎样才能摆脱这种透明度?

这是我的代码:

import sys
import numpy as np
import numpy.ma as ma
import matplotlib as mpl
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D

y_label = r'x'
x_label = r'y'
z_label = r'z'

x_scale = 2.0*np.pi
y_scale = 2.0*np.pi

y_numPoints = 250
x_numPoints = 250

def quasiCrystal(x, y):
    z = 0
    for i in range(0,5):
        z += np.sin(x * np.cos(float(i)*np.pi/5.0) +
                    y * np.sin(float(i)*np.pi/5.0))
    return z

x = np.linspace(-x_scale, x_scale, x_numPoints)
y = np.linspace(-y_scale, y_scale, y_numPoints)
X,Y = np.meshgrid(x,y)

Z = quasiCrystal(X, Y)


f = plt.figure()
ax = f.gca(projection='3d')

surf = ax.plot_surface( X, Y, Z,
                        rstride=5, cstride=5,
                        cmap='seismic',
                        alpha=1,
                        linewidth=0,
                        antialiased=True,
                        vmin=np.min(Z),
                        vmax=np.max(Z)
                      )

ax.set_zlim3d(np.min(Z), np.max(Z))

f.colorbar(surf, label=z_label)

ax.set_xlabel(x_label)
ax.set_ylabel(y_label)
ax.set_zlabel(z_label)

plt.show()
Run Code Online (Sandbox Code Playgroud)

这是我的实际数据的另一张图片,它更容易看到人工制品: 在此输入图像描述

arm*_*ita 6

Matplotlib不是一个"真正的"3D引擎.这是一个众所周知的问题,偶尔出现一个与你类似的问题(见本节).问题是同样的人工制品可能会产生似乎不同的问题.我相信你就是这种情况.

在继续我的推荐之前,让我引用maplotlib网站上的这些信息:

我的3D绘图在某些视角看起来并不正确

这可能是mplot3d最常报告的问题.问题在于 - 从某些视角 - 一个3D物体会出现在另一个物体的前面,即使它在物体后面.这可能会导致图形看起来"物理上不正确".

不幸的是,虽然正在做一些工作来减少这个工件的出现,但它目前是一个棘手的问题,并且在matplotlib支持其核心的3D图形渲染之前无法 完全解决 .

由于3D数据减少到2D + z阶标量,会出现问题.单个值表示集合中3D对象的所有部分的第三维.因此,当两个集合的边界框相交时,可能会发生此工件.此外,matplotlib的2D渲染引擎无法正确渲染两个3D对象(如多边形或面片)的交集.

在将OpenGL支持添加 到所有后端之前,这个问题可能无法解决(非常欢迎补丁).在此之前,如果您需要复杂的3D场景,我们建议您使用MayaVi.

似乎Mayavi终于转向了Python 3,所以它肯定有可能.如果你想坚持matplotlib用于这种情节我的建议是你使用rstride和cstride值来看看哪些产生了令你满意的情节.

surf = ax.plot_surface( X, Y, Z,
                        rstride=5, cstride=5,
                        cmap='jet',
                        alpha=1,
                        linewidth=0,
                        antialiased=True,
                        vmin=0,
                        rstride=10,
                        cstride=10,
                        vmax=z_scale
                      )
Run Code Online (Sandbox Code Playgroud)

其他可能性是试图看看其他类型的3D图表是否做得更好.检查plot_trisurf,contourcontourf.我知道它并不理想,但在过去,我还设法绕过使用3D多边形的其他类型的人工制品.

很抱歉没有更满意的答案.也许其他SO用户有更好的解决方案.祝你好运.


aqu*_*tle 6

我遇到了一些类似的问题,发现他们抗锯齿文物和可以通过设置固定antialiased=Falseplot_surface