Wildmeshing Toolkit
Loading...
Searching...
No Matches
Public Member Functions | Public Attributes | Private Member Functions | List of all members
wmtk::components::manifold_extraction::ManExtractTriMesh Class Reference
Inheritance diagram for wmtk::components::manifold_extraction::ManExtractTriMesh:
wmtk::components::topological_offset::TopoOffsetTriMesh wmtk::TriOptimizerMesh wmtk::TriMesh wmtk::RationalPositions

Public Member Functions

 ManExtractTriMesh (Parameters &_m_man_params, topological_offset::Parameters &_m_top_params, int _num_threads=0)
 
size_t label_non_manifold ()
 label nonmanifold simplices (edges and verts). Corresponding attributes have label set to 1
 
bool vertex_is_manifold (const Tuple &v) const
 check if a vertex is manifold. A vertex is manifold if all 'inside' and all 'outside' tets adjacent to the vertex form single face-reachable connected components, respectively. For vertices on the boundary of the mesh, external space is considered an 'outside' polyhedra that is face connected to all tets on the mesh boundary.
 
void vertex_dfs_helper (std::set< size_t > &visited_fids, const Tuple &f) const
 dfs helper for vertex manifold check
 
void extract_curve_mesh (MatrixXd &V, MatrixXi &F) const
 extract edge mesh separating 'inside' faces from 'outside' faces. Resulting curve is guaranteed to be manifold.
 
void write_curve (const std::string &path)
 write curve .obj (boundary of in_tag)
 
- Public Member Functions inherited from wmtk::components::topological_offset::TopoOffsetTriMesh
void classify_curve_edges ()
 Mark the mesh edges that lie on the input's curve group (EdgeExtra2d::on_curve).
 
void init_region_potentials (double delta, double effective_factor)
 
void assign_band_regions (bool log=true)
 
void log_front_profile (size_t vid)
 Diagnostic: the front objective of one vertex along its normal, offset term vs total.
 
int vertex_region (const size_t vid) const
 
int edge_region (const size_t va, const size_t vb) const
 
const OffsetPotential2D & potential_for_region (const int region) const
 
const OffsetPotential2D & potential_for (const size_t vid) const
 
std::shared_ptr< const OffsetPotential2D > potential_ptr_for (const size_t vid) const
 
const OffsetPotential2D & potential_for_edge (const size_t va, const size_t vb) const
 
const OffsetPotential2D & potential_for_face (const size_t fid) const
 
std::shared_ptr< SampleEnvelope > containment_for (uint64_t region_mask, bool on_offset) const
 The containment a simplex with this region mask, on/off the offset front, must satisfy – the intersection of everything that holds it, or null if nothing does.
 
bool project_into_containment (size_t vid, Vector2d &x) const
 Move x back inside every region tube this vertex lies on. True if it ended up inside all of them.
 
int64_t tangent_curve_tag (size_t vid, const Vector2d &x) const
 Which tag's boundary curve a vertex slides along, or -1.
 
bool walk_along_curve (int64_t tag, const Vector2d &x, double s, Vector2d &out) const
 March s of arclength along tag tag's boundary polyline from x's foot on it.
 
bool curve_tangent (int64_t tag, const Vector2d &x, const Vector2d &prefer, Vector2d &tau) const
 The unit tangent of tag tag's curve at x's foot, or false if there is none.
 
bool phase_places_front () const
 
EnvelopeSetup envelope_setup () const
 
std::string envelope_key_name (int64_t tag) const
 The name a tag or pseudo-tag prints under.
 
bool edge_is_complex_boundary (const Tuple &e) const
 
void build_boundary_envelopes (const char *when, EnvelopeSetup setup)
 
void rebuild_offset_envelope ()
 
void check_no_vertex_on_both_surfaces (const char *when) const
 
void optimize_offset_single_phase ()
 TriWild's loop, the front placed inside its smoothing passes.
 
double phase_b_front_gradient_linf ()
 
 TopoOffsetTriMesh (Parameters &_m_offset_params, int _num_threads=0)
 
void set_vertex_position (const size_t vid, const Vector2d &p)
 Place a vertex, keeping its exact and rounded coordinates in step.
 
bool edge_is_offset (const size_t eid) const
 
bool edge_is_region (const size_t eid) const
 
EdgeSnapshot2d edge_snapshot (const size_t eid) const
 
void restore_edge (const size_t eid, const EdgeSnapshot2d &s)
 
FaceSnapshot2d face_snapshot (const size_t fid) const
 
void restore_face (const size_t fid, const FaceSnapshot2d &s)
 
void label_offset_boundary ()
 Tag the two tracked surfaces for the optimization phase.
 
bool face_in_region (const size_t fid) const
 Whether face fid belongs to the closed offset region, read from its label.
 
bool face_is_input_complex (const size_t fid) const
 
bool vertex_is_on_surface (const size_t vid) const override
 The substructure the link condition is evaluated against, derived not cached.
 
bool edge_is_on_surface (const std::array< size_t, 2 > &vids) const override
 Is an edge part of the substructure.
 
void optimize_offset (const std::filesystem::path &output_file)
 The 2D optimization phase: split / collapse / swap / smooth on the shared driver.
 
bool face_is_offset_band (const size_t fid) const
 
std::pair< double, double > compute_distance_deviation () const
 How far the offset boundary is from where it should be: {max, avg} over vertices.
 
void log_worst_dist_vertex () const
 
bool edge_is_offset_surface_live (const Tuple &e) const
 
void write_debug_pvd () const
 
bool marching_split_edge_before (const Tuple &t)
 
bool marching_split_edge_after (const Tuple &t)
 
bool edge_split_sphere_trace (const Vector2d &p_in, const Vector2d &p_out, Vector2d &p_new, size_t &steps) const
 Construction placement under sphere_trace_initialization: sphere tracing along the edge from p_in (the endpoint in the input complex, label != 0) towards p_out (the background endpoint) for the point where d(x) = target_distance, d(x) the distance to the input complex through m_input_complex_bvh. From t = 0 the trace evaluates d at the current point and steps forward by target_distance - d, the largest step that cannot cross the level set (d is 1-Lipschitz); it stops when |d - target_distance| <= sphere_trace_target_rel_tol x target_distance and returns true with p_new there. It returns false, p_new untouched, as soon as the current point reaches or passes p_out (t >= L: the level set is not on the edge) or would move behind p_in (d(p_in) already beyond the target); the caller then places the plain midpoint. Every step taken is longer than the tolerance, so the trace ends within L / (tol x target_distance) steps; steps returns how many it took. No snapping away from the endpoints: a point found arbitrarily close to p_out is used as is. Same as 3D.
 
bool collapse_edge_before (const Tuple &t) override
 Reject any collapse that violates the substructure link condition.
 
bool swap_edge_before (const Tuple &t) override
 Reject a flip whose new edge already exists.
 
bool swap_edge_after (const Tuple &t) override
 
bool collapse_before_vertex (size_t v1, size_t v2) override
 
void collapse_after_vertex (size_t v1, size_t v2) override
 
void split_after_vertex (size_t v_new) override
 
bool split_adjust_position (size_t v_new, const std::vector< Tuple > &children) override
 Carry each parent's region label onto the two children it became.
 
bool smooth_before (const Tuple &t) override
 User specified preparations and desideratas for an edge smooth.
 
bool smooth_after (const Tuple &t) override
 User specified modifications and desideras after an edge smooth.
 
bool vertex_is_on_domain_boundary (const size_t vid) const
 Identification only – no operation refuses the domain wall through these.
 
bool edge_is_on_domain_boundary (const size_t eid) const
 
void init_surfaces_and_boundaries ()
 Classify every region boundary, build the per-tag containment envelopes, and tag the domain wall – once, from the input mesh, before offset construction runs.
 
void mark_input_complex_vertices ()
 
void warn_if_offset_reaches_domain_boundary () const
 Warn if the offset band has grown into the domain boundary.
 
double ring_max_quality (size_t vid) const
 Max AMIPS over the faces incident to vid. -1 if it has none.
 
double face_flatness (size_t fid) const
 Scale-invariant flatness: 2*area / longest_edge^2.
 
void needle_forensics () const
 The full post-mortem on why nothing removes the flat faces.
 
void record_flatness (const char *op, double parent_flat, size_t child_fid) const
 Genesis: flatness transitions recorded at the operation hooks. {op, parent, child}.
 
double offset_edge_sag (size_t a, size_t b) const
 
double max_offset_edge_sag (const std::vector< std::array< size_t, 2 > > &edges) const
 
bool ops_guard_refuses_collapse (size_t v1, size_t v2) const
 
std::vector< Tuple > offset_surface_edges_live_at (size_t vid) const
 
std::vector< char > offset_surface_foldover_labels () const
 Per-vertex 0/1: has the offset curve folded back on itself at this vertex? Debug frame diagnostic; see write_vtu(). Costs one pass over the live offset edges, no field evaluation.
 
void log_smooth_trace () const
 
void log_region_edge_mask_health (const std::string &when) const
 Are the tracked region boundaries actually contained by anything?
 
void audit_surface_containment (const std::string &when) const
 Which tracked edges are outside their envelope, and by how much.
 
bool vertex_is_on_region (const size_t vid) const
 Is this vertex on a region boundary – a tag boundary, or the domain wall.
 
uint64_t tag_bits (const CellTag &tags) const
 
uint64_t vertex_boundary_mask (const size_t vid) const
 The tag boundaries this vertex lies on – the raw mask gated on the vertex still being region geometry at all.
 
uint64_t edge_mask (const std::array< size_t, 2 > &vids) const
 
uint64_t edge_boundary_bits (const Tuple &e) const
 Diagnostic only: which tag boundaries the incident faces say this edge lies on right now – the same symmetric difference init_surfaces_and_boundaries() classified by.
 
std::shared_ptr< SampleEnvelope > envelope_for_mask (uint64_t mask) const
 The envelope a simplex with this boundary mask is contained in, or null.
 
std::shared_ptr< SampleEnvelope > surface_envelope_for_edge (const std::array< size_t, 2 > &vids) const override
 Class-0 segments – every region boundary, the input complex and the domain wall included – carry a containment requirement; the offset boundary does not.
 
bool smoothing_position_is_allowed (const size_t, const Vector2d &) const override
 No per-vertex positional constraint. The per-tag envelopes close that hole structurally – the same deletion 3D made to its lower-strata point refusal.
 
std::shared_ptr< SampleEnvelope > smoothing_energy_envelope (const size_t vid) const override
 The offset boundary is the one tracked surface with no envelope, in either role.
 
std::shared_ptr< SampleEnvelope > smoothing_containment_envelope (const size_t vid) const override
 ... and it is not contained by one either, except in Phase A.
 
bool smooth_front_vertex_phase_b (const Tuple &t)
 Phase B placement of a front vertex: the shared smoother with the offset's options.
 
double front_vertex_normal_gradient (size_t vid) const
 
Vector2d front_vertex_move_direction (size_t vid) const
 
double front_move_alignment (size_t vid) const
 
bool front_vertex_alignment_traps_1d_solve (size_t vid) const
 
double front_vertex_conv_ratio (size_t vid) const
 
bool front_vertex_placed (size_t vid) const
 THE definition of "placed" for a vertex on the offset surface.
 
bool front_placed_by_ratio (const double ratio) const
 
double edge_conv_ratio (const Tuple &e) const
 The edge test divided by its bar (1 = bar), per front_conv_criterion; -1 unmeasurable.
 
double edge_conv_ratio (size_t a, size_t b) const
 
Vector2d front_vertex_normal (size_t vid) const
 The field's outward unit direction at front vertex vid (zero where grad Phi vanishes).
 
std::shared_ptr< polysolve::nonlinear::Problem > phase_b_front_objective (size_t vid, const Vector2d &x) const
 
std::shared_ptr< polysolve::nonlinear::Problem > smoothing_extra_energy (const size_t vid) const override
 
std::shared_ptr< SampleEnvelope > released_envelope () const
 
bool edge_borders_released_boundary (const Tuple &e) const
 
bool face_is_deformable (size_t fid) const
 Under deform_others the same set as face_is_plastic(): every face outside the band.
 
bool face_is_plastic (size_t fid) const
 
void stamp_plastic_rests ()
 Stamp rest := current for every plastic face; called before every operation group.
 
bool smooth_plastic_vertex (const Tuple &t)
 
bool face_is_released_band (size_t fid) const
 
void stamp_rest_face (size_t fid)
 
void release_deformable_regions ()
 
std::shared_ptr< polysolve::nonlinear::Problem > rest_energy_for_vertex (size_t vid) const
 
std::shared_ptr< polysolve::nonlinear::Problem > phase_b_front_energy (size_t vid, const std::shared_ptr< const OffsetPotential2D > &pot) const
 
std::tuple< double, double > optimization_quality_stats () override
 The loop's convergence metric, normalized so that 1.0 means "done".
 
double optimization_stop_metric () const override
 1.0 in Phase B, where the metric is normalized; the base's stop_energy in Phase A.
 
int stencil_order () const
 
double offset_residual_tolerance () const
 
double offset_gradient_tolerance () const
 The convergence tolerance: the bound on |grad (Phi - c)^2| at a band vertex.
 
double gradient_reference () const
 
void check_offset_within_support (const char *when) const
 Stop the run if any reachable band vertex has left the potential's support.
 
DistanceSplit distance_deviation_split () const
 
DistanceSplit residual_split () const
 
std::vector< bool > band_vertex_mask () const
 
double max_band_vertex_distance () const
 
double band_vertex_distance_error (const size_t vid) const
 
double band_vertex_residual (const size_t vid) const
 
EdgeSamples offset_edge_samples (const Tuple &e) const
 The Phi residual at stencil_order interior points of band edge e.
 
template<typename Visit >
void for_each_offset_edge_sample (const Tuple &e, Visit &&visit) const
 Visit the same interior sample points offset_edge_samples() measures on.
 
GradientSplit gradient_split (bool include_edge_samples=true) const
 
EnergyCriterion energy_criterion ()
 
double front_chord_target (size_t va, size_t vb, double len, double sag, double tube) const
 
size_t refine_front_from_sag (const std::vector< EnergyCriterion::Refinable > &edges)
 
size_t refine_front_by_halving (const std::vector< EnergyCriterion::Refinable > &edges)
 
void grade_sizing (double grade, const std::vector< size_t > &seeds)
 
size_t grade_sizing_by_distance (const std::vector< size_t > &seeds)
 
SmoothingProgress smoothing_progress (const std::vector< Vector2d > &before)
 Measure a pass: before holds every live vertex's position before it, indexed by vid.
 
void smooth_group_to_convergence (const char *group_name)
 
double edge_interpolation_residual (const Tuple &e) const
 The interpolation residual of front edge e, see EnergyCriterion. -1 when unmeasurable.
 
double edge_interpolation_residual (size_t a, size_t b) const
 The same on a vertex pair; the tuple form delegates here. See edge_conv_ratio(a, b).
 
Vector2d offset_vertex_normal (const size_t vid) const
 The normal at an offset vertex. Every caller that needs one goes through here, so switching the definition is a one-line edit rather than a hunt through the call sites.
 
void report_outside_support (const char *when, const DistanceSplit &s) const
 
bool band_vertex_is_reachable (const size_t vid) const
 
size_t refine_sizing_around_worst (double max_metric) override
 TriWild's stall-driven sizing refinement, verbatim.
 
void log_stuck_refine_census (double max_metric, double filter_energy)
 Why Phase A is stuck: a census of the faces stuck-refine is about to chase.
 
void log_refine_block_census (const std::string &when, double filter_energy) const
 For every element above filter_energy, why its edges cannot be split.
 
bool collapse_quality_allowed (size_t v1, size_t v2, double q, double ring_max) const override
 Instrumentation only: which operation manufactures the MAX_ENERGY needles.
 
bool swap_quality_allowed (const double after, const double before, const bool is_surface_flip) const override
 
void report_needle (const char *op, size_t fid, double parent_q) const
 Where the first needles come from – a tripwire, not a census.
 
void needle_scan (const char *when) const
 
void collapse_pass_begin () override
 
bool optimization_bare_coarsen_passes () const override
 
bool collapse_edge_after (const Tuple &t) override
 A collapse is accepted by the same criterion the smoothing minimises.
 
double face_criterion_rel (const size_t fid) const
 
void write_smoothing_debug_output (const std::string &path) const override
 Put the optimization's frames on the run's single debug timeline (see write_debug_frame()), labelled "r<round><phase><pass>_<op>" / "r<round><phase>_end". <pass> counts passes within the current phase and restarts whenever the round or the phase changes, so r1S3 reads as "round 1, single phase, third pass"; the restart is detected here, so no call site has to remember to reset anything. Renaming here rather than at the call sites keeps this out of the shared driver, whose naming is also triwild's and simwild's. Same scheme as 3D.
 
void append_frame_label (size_t idx, const std::string &label) const
 One line of <output>_frames.txt; truncates the file on the first frame.
 
void write_debug_frame (const std::string &label)
 One frame of the run's single debug timeline: <output>_NNNNN.vtu with the next sequence number, and one "NNNNN<tab>label" line in <output>_frames.txt. Every debug frame the run writes – the input as loaded, the construction stages, and the optimization's own frames through write_smoothing_debug_output() – goes through this sequence, so the numbers are consecutive and the .txt says what each one is. The only debug files outside it are the ones that are not this mesh: <output>_input_complex.vtu and the phi grid.
 
void init_from_image (const MatrixXd &V, const MatrixXi &F, const MatrixSi &F_tags, const MatrixXd &V_env, const MatrixXi &F_env, const std::vector< std::string > &tag_names, const std::string &curve_name="")
 initialize TriMesh from vertex, face, tag data
 
bool ambient_assert ()
 ensure ambient tag does not overlap any other tags in mesh.
 
void label_input_complex ()
 label input complex simplices as per boolean expression (or single body mode)
 
bool empty_input_complex ()
 check if the input complex is empty. Only valid after calling init_from_image(...). Checks if any vertices (therefore any simplices) are labelled 1, if not returns true
 
void init_input_complex_bvh ()
 Build the input complex's BVH and its smooth offset potential, from one extraction.
 
void init_offset_potential ()
 Build the smooth offset potential from the extraction init_input_complex_bvh() kept.
 
bool split_edge_before (const Tuple &t) override
 User specified preparations and desideratas for an edge split.
 
bool split_edge_after (const Tuple &t) override
 User specified modifications and desideratas after an edge split.
 
bool split_face_before (const Tuple &t) override
 User specified preparations and desideratas for a face split.
 
bool split_face_after (const Tuple &t) override
 User specified modifications and desideratas after a face split.
 
bool invariants (const std::vector< Tuple > &tris) override
 User specified invariants that can't be violated.
 
void execute_offset (const std::filesystem::path &output_file)
 
void marching_tris ()
 
bool is_simplicially_embedded () const
 check if the input complex (simplices labelled 1) are simplicially embedded w.r.t. the entire mesh
 
bool tri_is_simp_emb (const Tuple &t) const
 check if a triangle satisfies simpicial embedding criteria w.r.t. input complex (simplices labelled 1)
 
void simplicial_embedding ()
 make mesh a simplicial embedding of the input complex (simplices labelled 1)
 
void set_offset_tri_tags ()
 update 'tags' data for triangles in the offset region (tris labelled 2) based on the given offset tag values in m_offset_params.offset_tag_value
 
bool offset_is_manifold ()
 verify that the closed offset region (simplices labelled 1 or 2) form a manifold region. This should be true for any offset. This function is for verification
 
void write_phi_grid (const std::string &path, int n) const
 Sample the smooth offset potential on a dense grid and write it as <path>_phi.vtu.
 
void write_input_complex (const std::string &path)
 
void write_vtu (const std::string &path)
 
void write_msh_groups (const std::string &file)
 
size_t edge_id_from_simplex (const simplex::Edge &e) const
 get global id of edge from simplex::Edge object
 
Tuple get_tuple_from_edge (const simplex::Edge &e) const
 get Tuple simplex::Edge object
 
std::vector< Tuple > get_edge_adjacent_faces (const Tuple &f) const
 get faces (as Tuples) that are edge-adjacent to the given face (as Tuple)
 
- Public Member Functions inherited from wmtk::TriOptimizerMesh
 TriOptimizerMesh (OptimizerParameters &params)
 
size_t get_partition_id (const Tuple &loc) const
 
void partition_mesh ()
 
void partition_mesh_morton ()
 
double get_length2 (const Tuple &l) const
 
bool is_inverted (const std::array< size_t, 3 > &vs) const
 Orientation check, exact for the coordinates the vertices actually carry.
 
bool is_inverted (const Tuple &loc) const
 
bool is_inverted (const size_t fid) const
 
bool is_inverted_f (const Tuple &loc) const
 Inversion check using only the double positions.
 
bool is_inverted_f (const size_t fid) const
 
double get_quality (const std::array< size_t, 3 > &vs) const
 
double get_quality (const Tuple &loc) const
 
double get_quality (const size_t fid) const
 
std::tuple< double, double > get_max_avg_energy ()
 
virtual void update_attributes ()
 Update the attributes of the mesh after an iteration of operations.
 
void mesh_improvement (int max_its=80)
 
std::tuple< double, double > local_operations (const std::array< int, 4 > &ops, bool collapse_limit_length=true)
 
bool is_force_split_edge (const size_t v1, const size_t v2) const
 
void split_all_edges ()
 
bool split_edge_before (const Tuple &t) override
 User specified preparations and desideratas for an edge split.
 
bool split_edge_after (const Tuple &loc) override
 User specified modifications and desideratas after an edge split.
 
void collapse_all_edges (bool is_limit_length=true)
 
bool collapse_edge_before (const Tuple &t) override
 User specified preparations and desideratas for an edge collapse including the link check as collapse prerequisite.
 
bool collapse_edge_after (const Tuple &t) override
 User specified modifications and desideratas after an edge collapse.
 
size_t coarsen_mesh ()
 Coarsen the mesh without letting the max energy rise.
 
bool coarsen_collapse_edge (const Tuple &e, std::vector< Tuple > &new_tris)
 One collapse under the coarsening rules, outside a coarsening pass.
 
size_t swap_all_edges ()
 Run TriWild's quality-improving interior edge-flip pass.
 
double swap_weight (const Tuple &t) const
 
bool swap_edge_before (const Tuple &t) override
 User specified preparations and desideratas for an edge swap including 1.can't swap on boundary edge. 2. when swap edge between v1, v2, there can't exist edges between the two opposite vertices v3, v4.
 
bool swap_edge_after (const Tuple &t) override
 User specified modifications and desideras after an edge swap.
 
void smooth_all_vertices (size_t n_iters=1)
 Run TriWild's vertex-smoothing pass.
 
bool smooth_before (const Tuple &t) override
 User specified preparations and desideratas for an edge smooth.
 
bool smooth_after (const Tuple &t) override
 User specified modifications and desideras after an edge smooth.
 
Vector2d smoothing_position (size_t vid) const
 
void set_smoothing_position (size_t vid, const Vector2d &p)
 
double active_quality_threshold () const
 
virtual std::vector< size_t > active_vertices () const
 
virtual double quality_rel (const size_t fid) const
 A face's quality relative to the quality it is required to reach; <= 1 means it meets it.
 
bool round (const Tuple &v)
 Round a vertex position to floating point, if that inverts no incident face.
 
bool is_edge_on_surface (const Tuple &loc) const
 
bool is_edge_on_surface (const std::array< size_t, 2 > &vids) const
 
bool is_edge_on_bbox (const Tuple &loc) const
 
bool is_edge_on_bbox (const std::array< size_t, 2 > &vids) const
 
bool vertex_is_on_surface (const size_t vid) const override
 Is a vertex part of the substructure.
 
bool edge_is_on_surface (const std::array< size_t, 2 > &vids) const override
 Is an edge part of the substructure.
 
bool surface_segment_is_outside (const size_t a, const size_t b) const
 
std::vector< std::array< size_t, 2 > > get_edges_by_condition (std::function< bool(const EdgeAttributes &)> cond) const
 
void gradation_smooth_sizing (double grade, const std::vector< size_t > &seeds)
 Monotone (only-decreasing) gradation smoothing of the sizing field.
 
- Public Member Functions inherited from wmtk::TriMesh
void init (size_t n_vertices, const std::vector< std::array< size_t, 3 > > &tris)
 
void init (const MatrixXi &F)
 Generate the connectivity of the mesh from an IGL-style F matrix.
 
std::vector< Tuple > get_vertices () const
 
std::vector< Tuple > get_edges () const
 
std::vector< Tuple > get_faces () const
 
Tuple tuple_from_edge (size_t vid1, size_t vid2, size_t fid) const
 
Tuple tuple_from_vids (size_t vid0, size_t vid1, size_t vid2) const
 
simplex::Vertex simplex_from_vertex (const Tuple &t) const
 
simplex::Edge simplex_from_edge (const Tuple &t) const
 
simplex::Face simplex_from_face (const Tuple &t) const
 
simplex::Face simplex_from_face (const size_t fid) const
 
Tuple tuple_from_simplex (const simplex::Face &s) const
 
simplex::SimplexCollection simplex_incident_triangles (const simplex::Vertex &v) const
 
simplex::SimplexCollection simplex_incident_triangles (const simplex::Edge &e) const
 
simplex::SimplexCollection simplex_link_vertices (const simplex::Vertex &v) const
 
simplex::SimplexCollection simplex_link_vertices (const simplex::Edge &e) const
 
simplex::SimplexCollection simplex_link_edges (const simplex::Vertex &v) const
 
void set_preallocation_factor (double factor)
 Preallocation factor: init/consolidate reserve capacity = max(floor, ceil(factor * live_count)) so operations can grab fresh slots without resizing the storage. When a pass exhausts the reserved capacity the affected operations fail (retried later after a consolidate). Values < 1 are clamped to 1.
 
double preallocation_factor () const
 
bool slots_exhausted () const
 
void clear_slots_exhausted ()
 
size_t request_tri_slots (size_t n)
 
size_t request_vert_slots (size_t n)
 
size_t tri_capacity () const
 get the current largest global fid
 
size_t vert_capacity () const
 get the current largest global vid
 
void consolidate_mesh ()
 removing the elements that are removed
 
void remove_tris_by_ids (const std::vector< size_t > &fids)
 Mark the given triangles, and any vertex left without an incident triangle, as removed.
 
Tuple switch_vertex (const Tuple &t) const
 a duplicate of Tuple::switch_vertex funciton
 
Tuple switch_edge (const Tuple &t) const
 a duplicate of Tuple::switch_edge funciton
 
std::optional< Tuple > switch_face (const Tuple &t) const
 a duplicate of Tuple::switch_face funciton
 
bool check_link_condition (const Tuple &t) const
 prerequisite for collapse
 
void set_use_link_condition (bool use_it)
 Should collapse_edge_before enforce the link condition?
 
bool use_link_condition () const
 
bool check_mesh_connectivity_validity () const
 verify the connectivity validity of the mesh
 
bool check_edge_manifold () const
 verify the edge manifoldness of the mesh
 
size_t edge_valence (const TriMesh::Tuple &t) const
 Number of triangles incident to the edge the Tuple points at.
 
bool is_boundary_edge (const TriMesh::Tuple &t) const
 Does exactly one triangle share this edge?
 
bool is_manifold_edge (const TriMesh::Tuple &t) const
 Do exactly two triangles share this edge?
 
size_t vertex_component_count (const size_t vid) const
 Number of edge-connected components in the fan of a vertex.
 
size_t vertex_component_count (const TriMesh::Tuple &t) const
 
bool is_manifold_vertex (const size_t vid) const
 
std::optional< Tuple > switch_component (const TriMesh::Tuple &t) const
 Jump to the next edge-connected component of the fan of the Tuple's vertex.
 
bool is_boundary_vertex (const TriMesh::Tuple &t) const
 check if the vertex that's represented by a Tuple is at the boundary of the mesh
 
bool split_edge (const Tuple &t, std::vector< Tuple > &new_t)
 
virtual bool collapse_edge (const Tuple &t, std::vector< Tuple > &new_t)
 
void collapse_edge_conn (const Tuple &loc0, std::vector< Tuple > &new_tris, Tuple &return_t, size_t &new_vid, std::vector< std::pair< size_t, TriangleConnectivity > > &old_tris, std::vector< std::pair< size_t, VertexConnectivity > > &old_vertices, std::vector< std::pair< size_t, size_t > > &same_edge_vid_fid, std::vector< size_t > &n12_intersect_fids)
 
void collapse_edge_rollback (size_t &new_vid, std::vector< std::pair< size_t, TriangleConnectivity > > &old_tris, std::vector< std::pair< size_t, VertexConnectivity > > &old_vertices, std::vector< std::pair< size_t, size_t > > &same_edge_vid_fid, std::vector< size_t > &n12_intersect_fids)
 
bool swap_edge (const Tuple &t, std::vector< Tuple > &new_t)
 
bool smooth_vertex (const Tuple &t)
 
bool split_face (const Tuple &t, std::vector< Tuple > &new_t)
 Split a face in 3 faces.
 
size_t get_valence_for_vertex (const Tuple &t) const
 Count the number of the one ring tris for a vertex.
 
size_t vertex_valence (const size_t vid) const
 Number of triangles incident to a vertex, by id.
 
std::vector< Tuple > get_one_ring_tris_for_vertex (const Tuple &t) const
 Get the one ring tris for a vertex.
 
const std::vector< size_t > & get_one_ring_fids_for_vertex (const Tuple &t) const
 
const std::vector< size_t > & get_one_ring_fids_for_vertex (const size_t vid) const
 
std::vector< size_t > get_one_ring_vids_for_vertex_duplicate (const size_t &t) const
 Get the vids of the incident one ring tris for a vertex.
 
void get_one_ring_vids_for_vertex_duplicate (const size_t &t, std::vector< size_t > &one_ring) const
 
std::vector< size_t > get_incident_fids_for_edge (const Tuple &t) const
 
std::vector< size_t > get_incident_fids_for_edge (const size_t vid0, const size_t vid1) const
 
std::vector< Tuple > get_one_ring_edges_for_vertex (const Tuple &t) const
 Get all edges that are incident to the vertex of Tuple t.
 
std::vector< Tuple > get_one_ring_edges_for_vertex (const size_t vid) const
 
std::array< Tuple, 3 > oriented_tri_vertices (const Tuple &t) const
 Get the incident vertices for a triangle.
 
std::array< size_t, 3 > oriented_tri_vids (const Tuple &t) const
 Get the incident vertices for a triangle.
 
std::array< size_t, 3 > oriented_tri_vids (const size_t i) const
 
std::array< Tuple, 2 > get_edge_vertices (const Tuple &t) const
 
std::array< size_t, 2 > get_edge_vids (const Tuple &t) const
 
Tuple tuple_from_tri (size_t fid) const
 
Tuple tuple_from_vertex (size_t vid) const
 
Tuple tuple_from_edge (size_t fid, size_t local_eid) const
 
std::tuple< Tuple, size_t > tuple_from_edge (const std::array< size_t, 2 > &vids) const
 
std::optional< std::tuple< Tuple, size_t > > try_tuple_from_edge (const std::array< size_t, 2 > &vids) const
 tuple_from_edge for callers where a missing edge is an answer, not a bug.
 
void start_protect_attributes ()
 Start the phase where the attributes that will be modified can be recorded.
 
void release_protect_attributes ()
 End the modification phase.
 
void rollback_protected_attributes ()
 rollback the attributes that are modified if any condition failed
 
int release_vertex_mutex_in_stack ()
 
int release_vertex_mutex_to (size_t mark)
 Release the mutexes taken since the release stack held mark entries.
 
bool try_set_vertex_mutex_n_ring (const Tuple &v, int threadid, int n)
 Lock every vertex within graph distance n of v, the seed included.
 
bool try_set_vertex_mutex_n_ring (size_t vid, int threadid, int n)
 
bool try_set_edge_mutex_n_ring (const Tuple &e, int threadid, int n)
 try_set_vertex_mutex_n_ring seeded from both ends of an edge.
 
bool try_set_face_mutex_one_ring (const Tuple &f, int threadid)
 try lock the one-ring neighboring triangles' incident vertices.
 
void for_each_face (const std::function< void(const Tuple &)> &)
 perform the given function for each face
 
void for_each_edge (const std::function< void(const Tuple &)> &)
 perform the given function for each edge
 
void for_each_vertex (const std::function< void(const Tuple &)> &)
 perform the given function for each vertex
 
simplex::SimplexCollection get_surface_edges_for_vertex (const size_t vid) const
 Get all edges on the surface that are incident to vid.
 
size_t get_order_of_edge (const std::array< size_t, 2 > &vids) const
 Compute the order of an edge.
 
size_t get_order_of_vertex (const size_t vid) const
 Get the order of a vertex.
 
bool substructure_link_condition (const Tuple &e_tuple) const
 Link condition that also considers substructures.
 
size_t tri_storage_capacity () const
 
size_t vert_storage_capacity () const
 
bool try_set_vertex_mutex_two_ring (const Tuple &v, int threadid)
 Lock v's one-ring and, partially, its two-ring. See the note above.
 
bool try_set_edge_mutex_two_ring (const Tuple &e, int threadid)
 Lock the edge's one-ring and, partially, its two-ring. See the note above.
 
bool try_set_vertex_mutex_one_ring (const Tuple &v, int threadid)
 Lock v and its one-ring. Complete, unlike the two-ring pair.
 
size_t cell_capacity () const
 
Tuple tuple_from_cell (size_t cid) const
 
- Public Member Functions inherited from wmtk::RationalPositions
size_t round_all_vertices ()
 Try to round every un-rounded vertex; returns the number reclaimed.
 
bool round_and_check_all_rounded ()
 Run the sweep, then report whether the mesh is now fully rounded.
 

Public Attributes

int m_vtu_counter = 0
 
int m_surfvtu_counter = 0
 
Parameters & m_man_params
 
- Public Attributes inherited from wmtk::components::topological_offset::TopoOffsetTriMesh
std::array< size_t, 3 > m_init_counts = {{0, 0, 0}}
 
size_t m_tags_count
 
int64_t m_curve_tag = -1
 
MatrixXd m_curve_V
 The curve group as loaded, kept because the classification below is redone on demand.
 
MatrixXi m_curve_E
 
std::shared_ptr< SimplicialComplexBVH > m_input_complex_bvh
 The input complex as loaded. Built once, never rebuilt.
 
std::shared_ptr< OffsetPotential2D > m_offset_potential
 The smooth offset potential, and with it the definition of the offset itself.
 
int m_n_regions = 0
 One field per connected piece of the input complex, and which one each band vertex is placed on.
 
std::vector< std::shared_ptr< OffsetPotential2D > > m_region_potentials
 one per piece
 
std::vector< int64_t > m_phi_vert_region
 per m_phi_V row: region index
 
std::vector< int64_t > m_phi_seg_region
 per m_phi_E row: region index, -1 unknown
 
std::vector< int64_t > m_phi_face_region
 per m_phi_F row: region index, -1 unknown
 
std::vector< int64_t > m_phi_point_region
 per m_phi_P entry: region index, -1 unknown
 
std::vector< int > m_face_region
 per face: band's region, -1 none, -2 reached from two
 
std::vector< int > m_vertex_region
 per vertex: region of its band faces, -1 / -2 as above
 
std::map< int64_t, std::shared_ptr< SampleEnvelope > > m_tag_envelopes
 One containment envelope per input tag, ambient included. Both phases.
 
std::vector< Eigen::Vector2d > m_env_polyline_V
 
std::map< int64_t, TagPolyline2d > m_tag_polyline
 
std::map< int64_t, int > m_tag_bit
 
std::map< uint64_t, std::shared_ptr< SampleEnvelope > > m_isect_cache
 
std::mutex m_isect_mutex
 
std::map< uint64_t, std::shared_ptr< SampleEnvelope > > m_offset_isect_cache
 Memoized "region tubes AND the offset envelope", keyed by the region mask.
 
OptPhase m_phase = OptPhase::A
 Which phase is running. Read by every hook that differs between them; see OptPhase.
 
bool m_freeze_front = false
 The final Phase A: front vertices are not smoothed (see smooth_before()).
 
std::shared_ptr< SampleEnvelope > m_offset_envelope
 The tube the offset boundary may not leave during Phase A, of half-width offset_envelope. Rebuilt at the end of every Phase B from the boundary as that phase left it, which is what lets the boundary travel across rounds. Non-null once the offset exists; whether it constrains is containment_for()'s phase test, not the pointer. Unlike m_tag_envelopes, which must never be rebuilt.
 
double m_front_gradient_reference = 0.
 
EdgeSplitMode m_edge_split_mode = EdgeSplitMode::Midpoint
 
std::map< std::string, int64_t > m_tag_name_to_id
 
std::map< int64_t, std::string > m_tag_id_to_name
 
CellTag m_offset_output_tag_ids
 
bool m_singlebody = false
 
int64_t m_single_tag
 
bool m_has_envelope = false
 
MatrixXd m_V_envelope
 
MatrixXi m_F_envelope
 
Parameters & m_offset_params
 The base holds only wmtk::OptimizerParameters; this is the same object, typed.
 
VertexExtraCol m_vertex_extra
 
EdgeExtraCol m_edge_extra
 
FaceExtraCol m_face_extra
 
size_t m_worst_dist_vid = static_cast<size_t>(-1)
 
std::vector< std::array< double, 8 > > optimization_metrics
 
std::vector< std::array< int, 3 > > churn_counts
 
std::vector< std::array< int, 3 > > op_counts
 
int m_ab_round = 0
 
size_t m_debug_seq = 0
 Monotonic frame counter for the debug timeline. Mutable because the write hook is const.
 
std::vector< std::string > m_debug_frame_labels
 
std::map< std::string, std::vector< size_t > > m_debug_pvd_series
 
int m_debug_pass = 0
 
int m_debug_last_round = -1
 
char m_debug_last_phase = '?'
 
double m_gradient_reference = 0.
 See offset_gradient_tolerance(). Nothing sets it on the single-phase path; it stays 0.
 
bool m_converged = false
 
bool m_quality_converged = true
 
double m_quality_max_amips = 0.
 
std::atomic< int > iter_cnt_split_born {0}
 
std::atomic< int > iter_cnt_recollapsed {0}
 
std::atomic< int > iter_cnt_recollapsed_same_pass {0}
 
std::atomic< int > iter_cnt_split = 0
 
std::atomic< int > iter_cnt_collapse = 0
 
std::atomic< int > iter_cnt_swap = 0
 
std::atomic< int > iter_cnt_collapse_offset_removed {0}
 
std::atomic< int > iter_cnt_collapse_offset_reject {0}
 Operations refused because they would have left an offset-boundary face over tolerance.
 
std::atomic< int > iter_cnt_swap_offset_reject {0}
 
std::atomic< int > iter_cnt_collapse_guard_reject {0}
 
std::atomic< int > iter_cnt_split_offset_before {0}
 Splits of an offset-boundary edge: offered, accepted.
 
std::atomic< int > iter_cnt_split_offset {0}
 
wmtk::threading::enumerable_thread_specific< OptSplitCache2d > m_opt_split_cache
 
size_t m_marching_root_splits = 0
 
size_t m_marching_midpoint_splits = 0
 
size_t m_marching_trace_steps = 0
 
size_t m_marching_trace_steps_max = 0
 
SmoothTrace m_smooth_trace
 
wmtk::threading::enumerable_thread_specific< std::pair< double, Vector2d > > m_needle_pre
 Why smoothing does not lift a sliver's apex off its opposite edge.
 
std::atomic< size_t > m_needle_smooth_offered {0}
 
std::atomic< size_t > m_needle_smooth_reached {0}
 
std::atomic< size_t > m_needle_smooth_fixed {0}
 
std::atomic< size_t > m_needle_smooth_stationary {0}
 
std::atomic< size_t > m_needle_smooth_reports {0}
 Worst-case record: the best (lowest) ring max any needle-adjacent smooth achieved.
 
std::atomic< size_t > m_flat_created_split {0}
 
std::atomic< size_t > m_flat_created_collapse {0}
 
std::atomic< size_t > m_flat_worsened_split {0}
 
std::atomic< size_t > m_flat_genesis_reports {0}
 
wmtk::threading::enumerable_thread_specific< double > m_collapse_parent_flatness
 The flattest face in the collapse's ring before it ran, for record_flatness().
 
wmtk::threading::enumerable_thread_specific< double > m_collapse_survivor_sizing
 
std::atomic< int > m_placement_env_entry_outside {0}
 
std::atomic< int > m_placement_projected {0}
 
std::atomic< int > m_placement_tangential {0}
 
size_t m_front_gradient_worst_vid
 
std::set< int64_t > m_deform_tags
 The released tags. Filled by release_deformable_regions(); empty = feature inactive.
 
std::set< int64_t > m_source_tags
 
std::shared_ptr< SampleEnvelope > m_released_envelope
 
std::atomic< bool > m_released_tube_dirty {false}
 
std::mutex m_released_mutex
 
bool m_plastic_active = false
 set in optimize_offset() when deform_others
 
std::optional< EnergyCriterion > m_energy_verdict
 
std::atomic< size_t > m_deg_split_created {0}
 
std::atomic< size_t > m_deg_collapse_offered {0}
 
std::atomic< size_t > m_deg_collapse_allowed {0}
 
std::atomic< size_t > m_deg_collapse_by_ringmax {0}
 
std::atomic< size_t > m_deg_collapse_by_stop {0}
 
std::atomic< size_t > m_deg_collapse_by_unrounded {0}
 
std::array< size_t, 6 > m_deg_prev_counts {{0, 0, 0, 0, 0, 0}}
 Values at the previous census, so each census can report deltas rather than totals.
 
std::atomic< size_t > m_needle_reports {0}
 
std::set< std::pair< long, long > > m_stuck_prev_cells
 
size_t m_stuck_calls = 0
 
MatrixXd m_phi_V
 
MatrixXi m_phi_E
 
MatrixXi m_phi_F
 the complex faces, in the same vertex index space (for per-region BVHs)
 
std::vector< int > m_phi_P
 
- Public Attributes inherited from wmtk::TriOptimizerMesh
VertAttCol m_vertex_attribute
 
EdgeAttCol m_edge_attribute
 
FaceAttCol m_face_attribute
 
AttributeContainerGroup m_vertex_attr_group
 What p_vertex_attrs points at, so a derived class can register more.
 
AttributeContainerGroup m_edge_attr_group
 What p_edge_attrs points at, so a derived class can register more.
 
AttributeContainerGroup m_face_attr_group
 What p_face_attrs points at, so a derived class can register more.
 
OptimizerParameters & m_params
 
std::shared_ptr< SampleEnvelope > m_envelope
 
double m_envelope_eps = -1
 
double m_s_amips = -1
 
double m_s_envelope = -1
 
wmtk::threading::enumerable_thread_specific< std::unique_ptr< polysolve::nonlinear::Solver > > m_solver
 
optimization::SmoothRejectCounters m_smooth_rejects
 Why smoothing attempts were refused, reported once per pass.
 
bool m_collapse_limit_length = true
 
int m_debug_print_counter = 0
 
std::string m_debug_pass_name
 
size_t m_tags_count = 0
 
std::map< int64_t, std::string > m_tag_id_to_name
 
std::map< std::string, int64_t > m_tag_name_to_id
 
int m_iterations_used = 0
 Shared TriWild/SimWild outer optimization schedule.
 
std::set< simplex::Edge > m_force_split_edges
 
size_t m_force_split_count = 0
 
std::unique_ptr< std::atomic< int >[]> m_high_valence_claim
 
size_t m_high_valence_claim_size = 0
 
std::atomic< size_t > m_high_valence_rejects = 0
 
CoarsenStats m_coarsen_stats
 
- Public Attributes inherited from wmtk::TriMesh
AbstractAttributeContainer * p_vertex_attrs = nullptr
 
AbstractAttributeContainer * p_edge_attrs = nullptr
 
AbstractAttributeContainer * p_face_attrs = nullptr
 
wmtk::threading::enumerable_thread_specific< std::vector< size_t > > mutex_release_stack
 
int NUM_THREADS = 0
 

Private Member Functions

bool is_curve_vertex (const Tuple &v) const
 
bool is_curve_edge (const Tuple &e) const
 
bool is_interior_face (const Tuple &f) const
 
bool is_interior_face (size_t f_id) const
 

Additional Inherited Members

- Public Types inherited from wmtk::components::topological_offset::TopoOffsetTriMesh
enum class  EdgeSplitMode { Midpoint = 0 , SphereTrace = 1 , Optimization = 2 }
 
enum class  OptPhase { A , B , Single }
 Which mode the hooks are running in. The 2D twin of TopoOffsetTetMesh::OptPhase. More...
 
enum class  EnvelopeSetup { PerTag , WallComplex }
 Which boundaries the region-class envelopes hold, and how they are built. More...
 
using VertexExtraCol = wmtk::AttributeCollection< VertexExtra2d >
 
using EdgeExtraCol = wmtk::AttributeCollection< EdgeExtra2d >
 
using FaceExtraCol = wmtk::AttributeCollection< FaceExtra2d >
 
- Public Types inherited from wmtk::TriOptimizerMesh
using EdgeAttributes = wmtk::SurfaceTagAttributes
 
using VertAttCol = AttributeCollection< VertexAttributes >
 
using EdgeAttCol = AttributeCollection< EdgeAttributes >
 
using FaceAttCol = AttributeCollection< FaceAttributes >
 
- Public Types inherited from wmtk::TriMesh
template<typename T >
using vector = std::vector< T >
 
using VertexMutex = wmtk::threading::VertexMutex
 
- Static Public Attributes inherited from wmtk::components::topological_offset::TopoOffsetTriMesh
static constexpr int64_t m_wall_tag = -2
 pseudo-tag: the domain wall's tube
 
static constexpr int64_t m_complex_tag = -3
 
static constexpr int INPUT_SURFACE_CLASS = 0
 SurfaceTagAttributes::m_surface_class: which of the two tracked surfaces an edge belongs to. Same scheme as 3D.
 
static constexpr int OFFSET_SURFACE_CLASS = 1
 
static constexpr double kFlatThreshold = 1e-3
 
static constexpr size_t kNeedleReports = 12
 
static constexpr double kNeedleQuality = 1e6
 What counts as a needle for the tripwire – deliberately far below MAX_ENERGY.
 
- Static Public Attributes inherited from wmtk::TriOptimizerMesh
static constexpr double MAX_ENERGY = 1e50
 The sentinel get_quality returns for a face AMIPS2D cannot score.
 
- Static Public Attributes inherited from wmtk::TriMesh
static constexpr int EDGES_PER_CELL = 3
 
- Protected Member Functions inherited from wmtk::TriOptimizerMesh
virtual bool optimization_stop_at_float () const
 
virtual bool optimization_stalled (double prev, double cur)
 Whether an iteration that moved the metric from prev to cur is stalled, and the sizing refinement should therefore fire.
 
virtual void optimization_debug_checkpoint ()
 Called at every pass boundary, whether or not debug output is on.
 
virtual void collapse_pass_end (size_t)
 
std::vector< size_t > all_vertex_ids () const override
 Every live vertex, in the mesh's own iteration order.
 
bool vertex_is_rounded (const size_t vid) const override
 Whether this vertex's double position is currently trusted.
 
bool round_vertex (const size_t vid) override
 
- Protected Member Functions inherited from wmtk::TriMesh
void vertex_fan_components (size_t vid, std::vector< size_t > &component_of, std::vector< size_t > &representatives) const
 
void resize_mutex (size_t v)
 
- Protected Attributes inherited from wmtk::TriOptimizerMesh
uint32_t m_op_epoch = 0
 
wmtk::threading::enumerable_thread_specific< SplitInfoCache > split_cache
 
wmtk::threading::enumerable_thread_specific< CollapseInfoCache > collapse_cache
 
bool m_coarsen_mode = false
 Set for the duration of coarsen_mesh(); read-only while a pass is running.
 
- Protected Attributes inherited from wmtk::RationalPositions
std::atomic< bool > m_all_rounded = false
 True when every vertex is known to be rounded.
 

The documentation for this class was generated from the following files: