MCPcopy Create free account
hub / github.com/MeshInspector/MeshLib / alignContoursToMesh

Function alignContoursToMesh

source/MRMesh/MRAlignContoursToMesh.cpp:44–112  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

42}
43
44Expected<Mesh> alignContoursToMesh( const Mesh& mesh, const Contours2f& contours, const ContoursMeshAlignParams& params )
45{
46 MR_TIMER;
47 auto contoursMesh = PlanarTriangulation::triangulateContours( contours );
48 auto bbox = contoursMesh.computeBoundingBox();
49 if ( !bbox.valid() )
50 return unexpected( "Contours mesh is empty" );
51
52 const float cStartDepth = bbox.diagonal() * 0.05f; // use relative depth to avoid floating errors
53 addBaseToPlanarMesh( contoursMesh, -cStartDepth );
54
55 auto diagonal = bbox.size(); diagonal.z = cStartDepth;
56 AffineXf3f transform;
57
58 const auto& vecx = params.xDirection.normalized();
59 const auto norm = params.zDirection != nullptr ? *params.zDirection : mesh.pseudonormal( params.meshPoint );
60 const auto vecy = cross( vecx, -norm ).normalized();
61
62 const Vector3f pivotCoord{ bbox.min.x + diagonal.x * params.pivotPoint.x,
63 bbox.min.y + diagonal.y * params.pivotPoint.y,
64 0.0f };
65
66 auto rotQ = Quaternionf( Vector3f::plusX(), vecx );
67 // handle degenerated case
68 auto newY = rotQ( Vector3f::plusY() );
69 auto dotY = dot( newY, vecy );
70 if ( std::abs( std::abs( dotY ) - 1.0f ) < 10.0f * std::numeric_limits<float>::epsilon() )
71 {
72 if ( dotY < 0.0f )
73 rotQ = Quaternionf( vecx, PI_F ) * rotQ;
74 }
75 else
76 rotQ = Quaternionf( newY, vecy ) * rotQ;
77 AffineXf3f rot = AffineXf3f::linear( rotQ );
78
79 auto translation = mesh.triPoint( params.meshPoint );
80
81 transform =
82 AffineXf3f::translation( translation ) *
83 rot
84 * AffineXf3f::translation( -pivotCoord );
85
86 auto& contoursMeshPoints = contoursMesh.points;
87 for ( auto& p : contoursMeshPoints )
88 p = transform( p );
89
90 auto plusOffsetDir = norm * std::abs( params.extrusion );
91 auto minusOffsetDir = norm * ( cStartDepth - std::abs( params.extrusion ) );
92 const auto maxMovement = std::max( 0.0f, params.maximumShift );
93 for ( int i = 0; i < contoursMeshPoints.size() / 2; ++i )
94 {
95 PointOnFace hit;
96 auto inter = rayMeshIntersect( mesh, Line3f{ contoursMeshPoints[VertId( i )] + norm * bbox.size().y, -norm } );
97 if ( !inter )
98 return unexpected( std::string( "Cannot align contours" ) );
99 hit = inter.proj;
100
101 auto coords = hit.point;

Callers 1

alignTextToMeshFunction · 0.85

Calls 15

triangulateContoursFunction · 0.85
addBaseToPlanarMeshFunction · 0.85
absFunction · 0.85
maxFunction · 0.85
rayMeshIntersectFunction · 0.85
pseudonormalMethod · 0.80
triPointMethod · 0.80
unexpectedFunction · 0.70
crossFunction · 0.70
dotFunction · 0.70
computeBoundingBoxMethod · 0.45
validMethod · 0.45

Tested by

no test coverage detected