Measurement: Circles filtering (part 1)
This commit is contained in:
parent
76064fc2ba
commit
4b9630c23b
@ -196,14 +196,17 @@ void MeasuringImpl::update_planes()
|
||||
|
||||
if (last_border.size() == 1)
|
||||
m_planes[plane_id].borders.pop_back();
|
||||
else {
|
||||
assert(m_planes[plane_id].borders.front() == m_planes[plane_id].borders.back());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
continue; // There was no failure.
|
||||
|
||||
PLANE_FAILURE:
|
||||
m_planes[plane_id].borders.clear();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -233,15 +236,16 @@ void MeasuringImpl::extract_features()
|
||||
for (const std::vector<Vec3d>& border : plane.borders) {
|
||||
if (border.size() <= 1)
|
||||
continue;
|
||||
assert(border.front() == border.back());
|
||||
int start_idx = -1;
|
||||
|
||||
// First calculate angles at all the vertices.
|
||||
angles.clear();
|
||||
lengths.clear();
|
||||
for (int i=0; i<int(border.size()); ++i) {
|
||||
const Vec3d& v2 = (i == 0 ? border[0] - border[border.size()-1]
|
||||
: border[i] - border[i-1]);
|
||||
const Vec3d& v1 = i == (int)border.size()-1 ? border[0] - border.back()
|
||||
for (int i=0; i<int(border.size()); ++i) { // front is the same as back, hence the weird indexing
|
||||
const Vec3d& v2 = (i == 0 ? border[0] - border[border.size()-2]
|
||||
: border[i] - border[i-1]);
|
||||
const Vec3d& v1 = i == (int)border.size()-1 ? border[1] - border.back()
|
||||
: border[i+1] - border[i];
|
||||
double angle = atan2(-normal.dot(v1.cross(v2)), -v1.dot(v2)) + M_PI;
|
||||
if (angle > M_PI)
|
||||
@ -268,10 +272,24 @@ void MeasuringImpl::extract_features()
|
||||
}
|
||||
} else {
|
||||
if (circle) {
|
||||
// Add the circle and remember indices into borders.
|
||||
const auto& [center, radius] = get_center_and_radius(border, start_idx, i, trafo);
|
||||
circles_idxs.emplace_back(start_idx, i);
|
||||
circles.emplace_back(SurfaceFeature(SurfaceFeatureType::Circle, center, plane.normal, std::nullopt, radius));
|
||||
// Anything made up of less than 4 points shall not be considered a circle.
|
||||
if (i-start_idx > 3) {
|
||||
// This may be just a partial circle, maybe a small one generated by two short edges.
|
||||
// To qualify as a circle, it should cover at least one quadrant. Check this now.
|
||||
const auto& [center, radius] = get_center_and_radius(border, start_idx, i, trafo);
|
||||
const Vec3d& p1 = border[start_idx];
|
||||
const Vec3d& p2 = border[i];
|
||||
const Vec3d& p3 = border[size_t(start_idx+i)/2];
|
||||
|
||||
// Measure angle between the first and the second radiuses. If smaller than 90 deg, measure angle
|
||||
// between first radius and one corresponding to the middle of the circle.
|
||||
if ((p1-center).normalized().dot((p2-center).normalized()) < 0.05 // exactly 90 deg might get rejected
|
||||
|| (p1-center).normalized().dot((p3-center).normalized()) < 0.) {
|
||||
// Add the circle and remember indices into borders.
|
||||
circles_idxs.emplace_back(start_idx, i);
|
||||
circles.emplace_back(SurfaceFeature(SurfaceFeatureType::Circle, center, plane.normal, std::nullopt, radius));
|
||||
}
|
||||
}
|
||||
circle = false;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user