如何生成 3D 点的凹壳?

问题描述 投票:0回答:1

我有 68 个 3d 点(我猜它被称为稀疏点云)。我想将它们连接在一起以创建一个网格。我首先使用 Delaunay 三角测量进行了尝试。然而,它效果不佳,因为 Delaunay 三角剖分仅给出凸包,因此它给出的网格基本上忽略了凹入的眼睛。

这是一张图片来说明我的意思: Delaunay

所以我尝试使用其他东西,即 alphashape。我一直在使用这个文档:https://pypi.org/project/alphashape/ 我的问题是它根本不起作用。 以下是一些图片: Alpha Shape 上图显示了我想要转换为网格的 3d 点 下面的图片显示了我使用 alpha 形状的结果!

我想要一个 3D 凸包。

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import alphashape 

points_3d = np.array(sixtyEightLandmarks3D)
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
ax.scatter(points_3d[:, 0], points_3d[:, 1], points_3d[:, 2])
plt.show()


points_3d = [
    (0., 0., 0.), (0., 0., 1.), (0., 1., 0.),
    (1., 0., 0.), (1., 1., 0.), (1., 0., 1.),
    (0., 1., 1.), (1., 1., 1.), (.25, .5, .5),
    (.5, .25, .5), (.5, .5, .25), (.75, .5, .5),
    (.5, .75, .5), (.5, .5, .75)
]

points_3d = [
    (7, 191, 325.05537989702617), (6, 217, 330.15148038438355), (8, 244, 334.2528982671654), 
    (11, 270, 340.24843864447047), (19, 296, 349.17330940379736), (34, 320, 361.04985805287333), 
    (56, 340, 373.001340480165), (80, 356, 383.03263568526376), (110, 361, 387.06330231630074), 
    (140, 356, 383.08354180256816), (165, 341, 373.1621631409058), (187, 321, 359.4022815731698), 
    (205, 298, 344.64039229318433), (214, 272, 334.72376670920755), (216, 244, 328.54984401152893), 
    (218, 217, 324.34703636691364), (217, 190, 319.189598828032), (22, 166, 353.0056656769123), (33, 152, 359.0055709874152), 
    (52, 145, 364.0), (72, 147, 368.00135869314397), (91, 153, 372.0013440835933), (125, 153, 370.0013513488836), 
    (145, 146, 366.001366117669), (167, 144, 361.0), (186, 151, 358.00558654859003), (197, 166, 351.0056979594491), 
    (108, 179, 376.02127599379264), (108, 197, 381.02099679676445), (109, 214, 387.03229839381623), 
    (109, 233, 393.04579885809744), (87, 252, 383.03263568526376), (98, 255, 386.0323820614017), (109, 257, 387.03229839381623), 
    (120, 254, 385.0324661635691), (131, 251, 383.0469945058961), (44, 183, 360.01249978299364), (55, 176, 363.00550960006103), 
    (69, 176, 363.0123964825444), (81, 186, 364.0219773585106), (69, 188, 364.0219773585106), (54, 188, 364.0219773585106), 
    (136, 185, 361.01246515875323), (147, 175, 362.0013812128346), (162, 175, 361.00554012369395), 
    (174, 183, 357.0014005574768), (163, 188, 360.01249978299364), (149, 188, 362.01243072579706), 
    (73, 289, 384.04687213932624), (86, 282, 389.0462697417879), (100, 278, 391.0319680026174), 
    (109, 281, 391.0460330958492), (120, 277, 391.0319680026174), (134, 281, 387.03229839381623), 
    (147, 289, 380.0210520484359), (135, 299, 388.03221515745315), (121, 305, 392.04591567825315), 
    (110, 307, 392.04591567825315), (100, 306, 392.04591567825315), (86, 300, 391.0626548265636), 
    (78, 290, 386.0207248322297), (100, 290, 391.0319680026174), (109, 291, 391.0319680026174), 
    (120, 289, 391.0319680026174), (142, 289, 381.03280698648507), (120, 290, 391.0319680026174), 
    (109, 292, 392.03188645823184), (100, 291, 392.04591567825315), 
    (0., 1., 1.), (1., 1., 1.), (.25, .5, .5),
    (.5, .25, .5)
]



alpha_shape = alphashape.alphashape(points_3d, lambda ind, r: 0.3 + any(np.array(points_3d)[ind][:,0] == 0.0))
fig = plt.figure()
ax = plt.axes(projection='3d')
ax.plot_trisurf(*zip(*alpha_shape.vertices), triangles=alpha_shape.faces)
plt.show()

注意:我正在获取脸部的点,然后手动将其放入 3d_points 变量中。另外由于某种原因,我发现如果我不添加:“(0., 1., 1.), (1., 1., 1.), (.25, .5, .5), (.5, .25, .5)" 到数组,那么 alphashape 将不起作用,并且会给我以下错误:数组索引太多:数组是一维的,但有 2 个被索引

python point-clouds triangulation 3d-reconstruction alpha-shape
1个回答
0
投票

这个问题的答案是使用 X 和 Y 坐标执行 2D Delaunay 三角剖分,然后在绘图上显示它们时使用 Z 坐标。

© www.soinside.com 2019 - 2024. All rights reserved.