Open3D
Open3D copied to clipboard
Cropping point cloud using a convex polygon
Introduction
Hi!
I added a function that crops a point cloud using a convex hull polygon.
Points within the convex hull will be cropped.
Also , we can use 'invert' argument to select the points outside the convex hull
Test
I tested the function using the following code
import open3d as o3d
import numpy as np
import os,sys,time
import json
from threading import Thread
import copy
x = 3.
y = 3.
z = 3.
vertices = np.array([[0.,0.,0.],
[x,y,z],
[x,y,-z],
[x,-y,z],
[x,-y,-z]])
def get_bounding_convex_hull(points):
points_v3 = o3d.utility.Vector3dVector(points)
pcd = o3d.geometry.PointCloud(points_v3)
ch = o3d.geometry.BoundingConvexHull(pcd)
return ch
filt = get_bounding_convex_hull(vertices)
filt_ls = o3d.geometry.LineSet.create_from_triangle_mesh(filt.get_convex_hull())
N_iter = 1000
N = 100
start_time = time.time()
axis = o3d.geometry.TriangleMesh.create_coordinate_frame()
pcd_vis = o3d.geometry.PointCloud()
pcd_cropped_vis = o3d.geometry.PointCloud()
gd = {}
gd['axis'] = axis
gd['pcd'] = pcd_vis
gd['pcd_filt'] = pcd_cropped_vis
gd['fov'] = filt_ls
def run_visualizer(geo_dict):
vis = o3d.visualization.Visualizer()
vis.create_window()
for k,v in geo_dict.items():
vis.add_geometry(v)
ctrl = vis.get_view_control()
ctrl.set_up(np.array([0.,1.,0.]))
p = copy.deepcopy( ctrl.convert_to_pinhole_camera_parameters() )
temp = p.extrinsic.copy()
temp[:3,3] = np.array([0.,0.,20.])
p.extrinsic = temp
ctrl.convert_from_pinhole_camera_parameters(p,allow_arbitrary=True)
cnt = 0
while True:
for k,v in geo_dict.items():
vis.update_geometry(v)
poll_result = vis.poll_events()
vis.update_renderer()
# vis.capture_screen_image('screenshots/%02d.png'%cnt)
time.sleep(0.05)
cnt += 1
thr = Thread(target=run_visualizer,args=(gd,))
thr.daemon = True
thr.start()
points_raw_np = np.random.uniform(-3.,3.,(N,3))
points_raw_np[:,2] *= 0.1
transform_mat = np.array([ [0.9848077, -0.1736482, 0.0000000, 0.3],
[0.1736482, 0.9848077, 0.0000000, 0.2],
[0.0000000, 0.0000000, 1.0000000, 0.],
[0.0000000, 0.0000000, 0.0000000, 1.],
])
for i in range(N_iter):
# Create point cloud from a numpy array
points_raw = o3d.utility.Vector3dVector(points_raw_np)
pcd_raw = o3d.geometry.PointCloud(points_raw).paint_uniform_color([1.,0.,0.])
# Move the bounding convex hull to check whether transform works correctly
filt.transform(transform_mat)
filt_ls.transform(transform_mat)
pcd_cropped = pcd_raw.crop_convex_hull(filt,invert=False).paint_uniform_color([0.,1.,0.])
pcd_vis.clear()
pcd_vis += pcd_raw
pcd_cropped_vis.clear()
pcd_cropped_vis += pcd_cropped
time.sleep(0.2)
print('Done!')
- Screenshot

Please feel free to point out any issues.
Thanks for submitting this pull request! The maintainers of this repository would appreciate if you could update the CHANGELOG.md based on your changes.
Hello,
I am very interested about using the function (crop_convex_hull) to crop a pointcloud and most importly retrieve the remaining points! Despite updating the open3d python package to currently 0.14.1, I didn't find out your function : AttributeError: 'open3d.cpu.pybind.geometry.PointCloud' object has no attribute 'crop_convex_hull'. Is this function only available in the github code meaning that I have to build from source to be able to have access to this specific function?
Thanks in advance for your help!
@gliese581gg Are you going to implement the comments of @errissa? I am looking forward to use such function :D Cheers
Hi ! I'm very interested in your functionality, Do you think I could be implemented in the main branch ? Very thank you !
Hi @benjaminum is this functionality now available in tensor point cloud?
Hi @benjaminum is this functionality now available in tensor point cloud?
No but general cropping can be implemented with RaycastingScene and inside outside tests. This here can be more efficient if the convex bounding volume is small like in the example.
I am not sure about the ctor. It always computes the convex hull. Maybe it makes sense to assume a convex mesh for the TriMesh arg ctor.
- Add convex hull to mesh function for visualization.
- Any other changes?
Any chance this will get merged with the main branch? Looks super useful for trimming poisson meshes for organic shapes...