Reputation: 51
I am in the process of creating a mesh from my 3D PointCloud data. I have obtained my mesh and will attach pictures below. I was curious if anyone knew how to only obtain the mesh of just the scanned surface. It seems that when the mesh was created it connected the sides and bottom, but that I just want the mesh of the surface.
Here is my point cloud data Point Cloud Data
and here is the mesh that is created Mesh Front Surface View
I would just like the front (curved) surface to be a mesh and not have the sides... or the bottom Bottom View
My 3D data points are stored in a numpy array with size (n_points, 3). Here is my simple code. As I stated "points" is a numpy array containing all of the data points (1000+). I then create "volume" which creates a mesh using the delaunay_3d method and then the geometry is extracted into a shell. I am assuming that the shell extraction is what creates the actual viewed image, so is there something else I can do that would get me a surface mesh instead of a shape? thanks
cloud = pv.PolyData(points)
cloud.plot()
volume = cloud.delaunay_3d(alpha=2)
shell = volume.extract_geometry()
shell.plot()
Upvotes: 4
Views: 6831
Reputation: 2532
As you can see from this pyvista tutorial, you need to use the delaunay_2d
function.
To be closer to your problem at hand, I'll will start from the points
array in the tutorial above, which is a 2D array of x
, y
and z
coordinates, like your point cloud:
To get even a better idea I will add a little bit of noise to this points
array, as you can see in the image below:
And below you can see you final mesh:
Complete code:
import numpy as np
import pyvista as pv
# Define a simple Gaussian surface
n = 20
x = np.linspace(-200, 200, num=n) + np.random.uniform(-1, 5, size=n)
y = np.linspace(-200, 200, num=n) + np.random.uniform(-7, 9, size=n)
xx, yy = np.meshgrid(x, y)
A, b = 100, 100
zz = A * np.exp(-0.5 * ((xx / b) ** 2.0 + (yy / b) ** 2.0))
# Get the points as a 2D NumPy array (N by 3)
points = np.c_[xx.reshape(-1), yy.reshape(-1), zz.reshape(-1)]
noise = np.random.randn(400, 3) * 3
points_noise = points + noise
cloud = pv.PolyData(points_noise)
cloud.plot(point_size=15)
surf = cloud.delaunay_2d()
surf.plot(show_edges=True)
Upvotes: 3