0

i try to draw a 3d solid that represents an annulus. I have used the scipy module and Delaunay to do the calculation. Unfortunately the plot shows a 3d cylinder and not an annulus. Has somebody an idea how to modify the code? Is scipy the right module? Can i use Delaunay with retangular shapes? thanks in advance!

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
from scipy.spatial import Delaunay

points = 50

theta = np.linspace(0,2*np.pi,points)
radius_middle = 7.5
radius_inner = 7
radius_outer = 8

x_m_cartesian = radius_middle * np.cos(theta)
y_m_cartesian = radius_middle * np.sin(theta)
z_m_cartesian = np.zeros(points)
M_m = np.c_[x_m_cartesian,y_m_cartesian,z_m_cartesian]

x_i_cartesian = radius_inner * np.cos(theta)
y_i_cartesian = radius_inner * np.sin(theta)
z_i_cartesian = np.zeros(points)
M_i = np.c_[x_i_cartesian,y_i_cartesian,z_i_cartesian]

x1_m_cartesian = radius_middle * np.cos(theta)
y1_m_cartesian = radius_middle * np.sin(theta)
z1_m_cartesian = np.ones(points)
M1_m = np.c_[x1_m_cartesian,y1_m_cartesian,z1_m_cartesian]

x2_i_cartesian = radius_inner * np.cos(theta)
y2_i_cartesian = radius_inner * np.sin(theta)
z2_i_cartesian = np.ones(points)
M2_i = np.c_[x2_i_cartesian,y2_i_cartesian,z2_i_cartesian]

M = np.vstack((M_m,M_i,M1_m,M2_i))

# Delaunay
CH = Delaunay(M).convex_hull

x,y,z = M[:,0],M[:,1],M[:,2]

fig = plt.figure(figsize=(12,8))
ax = fig.add_subplot(111,projection='3d')
#ax.scatter(x[:,0],y[:,1],z[:,2])
ax.plot_trisurf(x,y,z,triangles=CH, shade=False, color='lightblue',lw=1, edgecolor='k')

plt.show()
  • The `convex_hull` of a ring of points is whole disk, not an annulus. There may be a way of 'subtracting' the inner disk, but the basic *convex* shape does not have holes. – hpaulj Jan 13 '21 at 15:58
  • Thanks for your feedback. Can you propose an other tool/module to create annulus. Subtracting the inner ring is not possible with convex_hull... – user14155947 Jan 13 '21 at 16:19

1 Answers1

0

As noted in the comments the convex hull is a convex shape and therefore cannot represent an annulus. However, the concept of the concave hull (also known as the alpha-shape) is probably appropriate for your needs. Basically, the alpha-shape removes from the Delaunay triangulation the triangles (tetrahedra in your 3D case) that have a circumradius greater than some value (defined by the alpha parameter).

This answer provides an implementation of the alpha-shape surface (i.e., the outer boundary) for 3D points. Using the alpha_shape_3D function from that answer, with an alpha value of 3, resulted in the figure below.

The following two lines in the code (replacing the assignment to CH and the plot function) do the job.

vertices, edges, facets = alpha_shape_3D(pos=M, alpha=3.)

ax.plot_trisurf(x,y,z,triangles=facets, shade=False, color='lightblue',lw=1, edgecolor='k')

enter image description here

Iddo Hanniel
  • 1,636
  • 10
  • 18