Skip to content

Commit 47a0e87

Browse files
committed
WIP-CAP: working code for registration components
1 parent 3fa7097 commit 47a0e87

File tree

14 files changed

+612
-21
lines changed

14 files changed

+612
-21
lines changed

src/diffCheck/registrations/DFGlobalRegistrations.hh

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -73,10 +73,10 @@ namespace diffCheck::registrations
7373
double voxelSize = 0.005,
7474
double radiusKDTreeSearch = 0.8,
7575
int maxNeighborKDTreeSearch = 50,
76-
double maxCorrespondenceDistance = 0.05,
76+
double maxCorrespondenceDistance = 0.5,
7777
bool isTEstimatePt2Pt = false,
7878
int ransacN = 3,
79-
double correspondenceCheckerDistance = 0.05,
79+
double correspondenceCheckerDistance = 0.5,
8080
double similarityThreshold = 0.9,
8181
int ransacMaxIteration = 100000,
8282
double ransacConfidenceThreshold = 0.999);

src/diffCheck/registrations/DFRefinedRegistration.cc

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
namespace diffCheck::registrations
55
{
6-
diffCheck::transformation::DFTransformation RefinedRegistration::O3DICP(
6+
diffCheck::transformation::DFTransformation DFRefinedRegistration::O3DICP(
77
std::shared_ptr<geometry::DFPointCloud> source,
88
std::shared_ptr<geometry::DFPointCloud> target,
99
double maxCorrespondenceDistance,
@@ -57,7 +57,7 @@ namespace diffCheck::registrations
5757
= diffCheck::transformation::DFTransformation(result.transformation_);
5858
return transformation;
5959
}
60-
diffCheck::transformation::DFTransformation RefinedRegistration::O3DGeneralizedICP(
60+
diffCheck::transformation::DFTransformation DFRefinedRegistration::O3DGeneralizedICP(
6161
std::shared_ptr<geometry::DFPointCloud> source,
6262
std::shared_ptr<geometry::DFPointCloud> target,
6363
double maxCorrespondenceDistance,

src/diffCheck/registrations/DFRefinedRegistration.hh

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55

66
namespace diffCheck::registrations
77
{
8-
class RefinedRegistration
8+
class DFRefinedRegistration
99
{
1010
public: ///< open3d registration methods
1111
/**
@@ -28,7 +28,7 @@ namespace diffCheck::registrations
2828
static diffCheck::transformation::DFTransformation O3DICP(
2929
std::shared_ptr<geometry::DFPointCloud> source,
3030
std::shared_ptr<geometry::DFPointCloud> target,
31-
double maxCorrespondenceDistance = 0.05,
31+
double maxCorrespondenceDistance = 5,
3232
bool scalingForPointToPointTransformationEstimation = false,
3333
double relativeFitness = 1e-6,
3434
double relativeRMSE = 1e-6,
@@ -55,7 +55,7 @@ namespace diffCheck::registrations
5555
static diffCheck::transformation::DFTransformation O3DGeneralizedICP(
5656
std::shared_ptr<geometry::DFPointCloud> source,
5757
std::shared_ptr<geometry::DFPointCloud> target,
58-
double maxCorrespondenceDistance = 0.05,
58+
double maxCorrespondenceDistance = 5,
5959
int maxIteration = 30,
6060
double relativeFitness = 1e-6,
6161
double relativeRMSE = 1e-6);

src/diffCheckApp.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ int main()
1818

1919
// global registration
2020
diffCheck::transformation::DFTransformation xform =
21-
diffCheck::registrations::DFGlobalRegistrations::O3DFastGlobalRegistrationFeatureMatching(
21+
diffCheck::registrations::DFGlobalRegistrations::O3DRansacOnFeatureMatching(
2222
pcdSrc, pcdTgt);
2323

2424
pcdTgt->ApplyTransformation(xform);

src/diffCheckBindings.cc

Lines changed: 25 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -104,25 +104,43 @@ PYBIND11_MODULE(diffcheck_bindings, m) {
104104
.def_static("O3DFastGlobalRegistrationFeatureMatching", &diffCheck::registrations::DFGlobalRegistrations::O3DFastGlobalRegistrationFeatureMatching,
105105
py::arg("source"),
106106
py::arg("target"),
107-
py::arg("voxelize") = true,
107+
py::arg("voxelize") = false,
108108
py::arg("voxel_size") = 0.005,
109-
py::arg("radius_kd_tree_search") = 0.1,
109+
py::arg("radius_kd_tree_search") = 0.8,
110110
py::arg("max_neighbor_kd_tree_search") = 50,
111111
py::arg("max_correspondence_distance") = 0.05,
112112
py::arg("iteration_number") = 128,
113113
py::arg("max_tuple_count") = 1000)
114114
.def_static("O3DRansacOnFeatureMatching", &diffCheck::registrations::DFGlobalRegistrations::O3DRansacOnFeatureMatching,
115115
py::arg("source"),
116116
py::arg("target"),
117-
py::arg("voxelize") = true,
117+
py::arg("voxelize") = false,
118118
py::arg("voxel_size") = 0.005,
119-
py::arg("radius_kd_tree_search") = 0.1,
119+
py::arg("radius_kd_tree_search") = 1.0,
120120
py::arg("max_neighbor_kd_tree_search") = 50,
121-
py::arg("max_correspondence_distance") = 0.05,
121+
py::arg("max_correspondence_distance") = 0.5,
122122
py::arg("is_t_estimate_pt2pt") = false,
123123
py::arg("ransac_n") = 3,
124124
py::arg("correspondence_checker_distance") = 0.05,
125-
py::arg("similarity_threshold") = 0.9,
126-
py::arg("ransac_max_iteration") = 100000,
125+
py::arg("similarity_threshold") = 1.5,
126+
py::arg("ransac_max_iteration") = 5000,
127127
py::arg("ransac_confidence_threshold") = 0.999);
128+
129+
py::class_<diffCheck::registrations::DFRefinedRegistration>(submodule_registrations, "DFRefinedRegistration")
130+
.def_static("O3DICP", &diffCheck::registrations::DFRefinedRegistration::O3DICP,
131+
py::arg("source"),
132+
py::arg("target"),
133+
py::arg("max_correspondence_distance") = 0.1,
134+
py::arg("is_t_estimate_pt2pt") = false,
135+
py::arg("relative_fitness") = 1e-6,
136+
py::arg("relative_rmse") = 1e-6,
137+
py::arg("max_iteration") = 30,
138+
py::arg("use_point_to_plane") = false)
139+
.def_static("O3DGeneralizedICP", &diffCheck::registrations::DFRefinedRegistration::O3DGeneralizedICP,
140+
py::arg("source"),
141+
py::arg("target"),
142+
py::arg("max_correspondence_distance") = 0.1,
143+
py::arg("max_iteration") = 30,
144+
py::arg("relative_fitness") = 1e-6,
145+
py::arg("relative_rmse") = 1e-6);
128146
}

src/gh/components/DF_fast_global_registration/code.py

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,10 @@
1313
import diffCheck
1414
from diffCheck import diffcheck_bindings
1515
from diffCheck import df_cvt_bindings
16+
import diffCheck.df_util
1617

1718

18-
class DFGlobalRegistration(component):
19+
class DFFastGlobalRegistration(component):
1920
def RunScript(self,
2021
i_cloud_source: rg.PointCloud,
2122
i_cloud_target: rg.PointCloud,
@@ -38,16 +39,21 @@ def RunScript(self,
3839
3940
:return o_x_form : transformation matrix
4041
"""
42+
if i_cloud_source is None or i_cloud_target is None:
43+
ghenv.Component.AddRuntimeMessage(RML.Warning, "Please provide both objects of type point clouds to align")
44+
return None
45+
4146
# set default values
4247
if i_radius_kd_search is None: i_radius_kd_search = 0.8
4348
if i_neighbours_kd_search is None: i_neighbours_kd_search = 50
4449
if i_max_corrspondence_dist is None: i_max_corrspondence_dist = 0.05
4550
if i_iteration_number is None: i_iteration_number = 128
4651
if i_max_tuple_count is None: i_max_tuple_count = 1000
4752

48-
if i_cloud_source is None or i_cloud_target is None:
49-
ghenv.Component.AddRuntimeMessage(RML.Warning, "Please provide both objects of type point clouds to align")
50-
return None
53+
# get the working unit of the Rhino document, if other than meters, set a multiplier factor
54+
scalef = diffCheck.df_util.get_doc_2_meters_unitf()
55+
i_radius_kd_search *= scalef
56+
i_max_corrspondence_dist *= scalef
5157

5258
df_cloud_source = df_cvt_bindings.cvt_rhcloud_2_dfcloud(i_cloud_source)
5359
df_cloud_target = df_cvt_bindings.cvt_rhcloud_2_dfcloud(i_cloud_target)
@@ -74,14 +80,17 @@ def RunScript(self,
7480
for i in range(4):
7581
for j in range(4):
7682
rh_form[i, j] = df_xform_matrix[i, j]
77-
83+
if rh_form == rg.Transform.Identity:
84+
ghenv.Component.AddRuntimeMessage(RML.Warning, "The transformation matrix is identity, no transformation is applied")
85+
return None
86+
7887
o_x_form = rh_form
7988

8089
return o_x_form
8190

8291

8392
if __name__ == "__main__":
84-
com = DFGlobalRegistration()
93+
com = DFFastGlobalRegistration()
8594
o_x_form = com.RunScript(
8695
i_cloud_source,
8796
i_cloud_target,
Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
#! python3
2+
3+
import System
4+
import typing
5+
6+
import Rhino
7+
import Rhino.Geometry as rg
8+
from ghpythonlib.componentbase import executingcomponent as component
9+
10+
import Grasshopper as gh
11+
from Grasshopper.Kernel import GH_RuntimeMessageLevel as RML
12+
13+
import diffCheck
14+
from diffCheck import diffcheck_bindings
15+
from diffCheck import df_cvt_bindings
16+
import diffCheck.df_util
17+
18+
19+
class ICPRegistration(component):
20+
def RunScript(self,
21+
i_cloud_source: rg.PointCloud,
22+
i_cloud_target: rg.PointCloud,
23+
24+
i_use_generalized_icp: bool,
25+
26+
i_max_corrspondence_dist: float,
27+
i_max_iteration: int,
28+
29+
is_t_estimate_pt2pt: bool, # valid only for 03dicp
30+
i_use_point_to_plane: bool # valid only for 03dicp
31+
) -> rg.Transform:
32+
"""
33+
The global registration component aligns two point clouds in a rough way.
34+
35+
:param i_cloud_source: source point cloud
36+
:param i_cloud_target: target point cloud to align to
37+
:param i_use_generalized_icp: if true, it uses the generalized ICP algorithm
38+
:param i_max_corrspondence_dist: maximum correspondence distance
39+
:param i_max_iteration: maximum number of iterations
40+
:param is_t_estimate_pt2pt: (valid only for 03dicp) if true, it deforms the point cloud
41+
:param i_use_point_to_plane: (valid only for 03dicp) if true, it uses point to plane registration
42+
43+
:return o_x_form : transformation matrix
44+
"""
45+
if i_cloud_source is None or i_cloud_target is None:
46+
ghenv.Component.AddRuntimeMessage(RML.Warning, "Please provide both objects of type point clouds to align")
47+
return None
48+
49+
# set default values
50+
if i_use_generalized_icp is None: i_use_generalized_icp = True
51+
if i_max_corrspondence_dist is None: i_max_corrspondence_dist = 5
52+
if i_max_iteration is None: i_max_iteration = 50
53+
54+
# get the working unit of the Rhino document, if other than meters, set a multiplier factor
55+
scalef = diffCheck.df_util.get_doc_2_meters_unitf()
56+
i_max_corrspondence_dist *= scalef
57+
58+
# conversion
59+
df_cloud_source = df_cvt_bindings.cvt_rhcloud_2_dfcloud(i_cloud_source)
60+
df_cloud_target = df_cvt_bindings.cvt_rhcloud_2_dfcloud(i_cloud_target)
61+
62+
# fast registration
63+
# these are the only hardcoded values since it will get the best result
64+
RELATIVE_FITNESS = 1e-6
65+
RELATIVE_RMSE = 1e-6
66+
67+
df_xform = None
68+
if i_use_generalized_icp:
69+
df_xform = diffcheck_bindings.dfb_registrations.DFRefinedRegistration.O3DGeneralizedICP(
70+
source=df_cloud_source,
71+
target=df_cloud_target,
72+
max_correspondence_distance=i_max_corrspondence_dist,
73+
max_iteration=i_max_iteration,
74+
relative_fitness=RELATIVE_FITNESS,
75+
relative_rmse=RELATIVE_RMSE
76+
)
77+
else:
78+
df_xform = diffcheck_bindings.dfb_registrations.DFRefinedRegistration.O3DICP(
79+
source=df_cloud_source,
80+
target=df_cloud_target,
81+
max_correspondence_distance=i_max_corrspondence_dist,
82+
is_t_estimate_pt2pt=is_t_estimate_pt2pt,
83+
relative_fitness=RELATIVE_FITNESS,
84+
relative_rmse=RELATIVE_RMSE,
85+
max_iteration=i_max_iteration,
86+
use_point_to_plane=i_use_point_to_plane
87+
)
88+
print("-------------------")
89+
print("Estimated transformation matrix:")
90+
print(df_xform.transformation_matrix)
91+
print("-------------------")
92+
93+
# cvt df xform to rhino xform
94+
df_xform_matrix = df_xform.transformation_matrix
95+
rh_form = rg.Transform()
96+
for i in range(4):
97+
for j in range(4):
98+
rh_form[i, j] = df_xform_matrix[i, j]
99+
if rh_form == rg.Transform.Identity:
100+
ghenv.Component.AddRuntimeMessage(RML.Warning, "The transformation matrix is identity, no transformation is applied")
101+
return None
102+
103+
o_x_form = rh_form
104+
105+
return o_x_form
106+
107+
108+
if __name__ == "__main__":
109+
com = ICPRegistration()
110+
o_x_form = com.RunScript(
111+
i_cloud_source,
112+
i_cloud_target,
113+
114+
i_use_generalized_icp,
115+
116+
i_max_corrspondence_dist,
117+
i_max_iteration,
118+
119+
is_t_estimate_pt2pt,
120+
i_use_point_to_plane
121+
)
5.84 KB
Loading

0 commit comments

Comments
 (0)