如何在mayavi中正确显示非立方体体素的体积

8 投票
1 回答
3161 浏览
提问于 2025-04-16 18:03

我正在使用mayavi(版本3.3.2)来显示体积等值面。

通常情况下,我的体积数据并不是立方体的体素;比如说,X和Y方向的采样网格可能是1毫米 x 1毫米,但Z方向是1.4毫米。

我想知道如何使用mayavi的mlab.contour3dmlab.pipeline.iso_surface来正确显示这些体积的空间比例。我更希望不把体积数据重新采样成立方体网格。

换句话说,我想知道如何让下面的代码显示一个球体,而不是一个扁平的椭球体(假设volume的体素比例是1:1:2,并且不想重新生成或重新采样体积数据)。

import numpy as np
from enthought.mayavi import mlab

def sqr(x): return x*x

s=64
x,y,z = np.ogrid[0:s,0:s,0:s/2]

volume = np.sqrt(sqr(x-s/2)+sqr(y-s/2)+sqr(2*z-s/2))

isos = mlab.contour3d(volume,contours=[5,15,25],transparent=True)
mlab.show()

我猜应该有某种方法可以访问底层的VTK图形管道(它的变换等),并插入适当的各向异性缩放(如果没有更直接的方法通过mlab API来实现的话)。

1 个回答

7

为了这个目的,最简单的方法是从输入数据中明确创建一个 scalar_field 对象。

我其实经常这样做,因为在地质学中,我们喜欢把东西放在深度上(正值是向下的)。这就意味着在z方向上需要一个负的增量。如果这只是各种mlab函数的一个参数那就好了,但其实这样做也并不太难。

from mayavi import mlab
import numpy as np

s=64
x,y,z = np.ogrid[0:s,0:s,0:s/2]

data = np.sqrt((x-s/2)**2 + (y-s/2)**2 + (2*z-s/2)**2)

grid = mlab.pipeline.scalar_field(data)
grid.spacing = [1.0, 1.0, 2.0]

contours = mlab.pipeline.contour_surface(grid, 
                         contours=[5,15,25], transparent=True)
mlab.show()

非立方体体素的球形壳

撰写回答