- Published: 2025-06-25
- Updated: 2025-06-25
- MeshLib Team
Fill Holes in Meshes
Filling holes in a mesh is a function that lets you correct topological defects, predictably known as holes. These defects are essentially missing regions where a continuous surface should exist. In triangle-based meshes represented by MeshLib, they appear as boundary loops of edges that belong to only one triangle.
The problem with holes is that they, obviously, undermine the watertightness and structural coherence of a mesh. These two are the properties that virtually every 3D workflow depends on. When it comes to 3D mesh processing and computational geometry, an open surface breaks many algorithms that assume a closed two-manifold surface (e.g., remeshing, Boolean operations, volume calculation). Also, in computer graphics and CAD/CAM pipelines, simulation errors, and failed 3D-print jobs.
As long as these gaps are often tiny and hard to spot, automated hole-filling is now a staple feature in 3D programming for modeling, reverse-engineering, and inspection tools. As such, it ensures:
- Accurate analysis and simulation;
- Clean manufacturing output;
- Predictable rendering;
- Robust downstream editing.
And all these professional domains face issues with mesh hole filling quite often. Typical reasons include:
- 3D scanning gaps. Occlusions, reflective surfaces, or fine details can elude scanners. Hence, holes emerge. They must be sealed to get a complete model.
- Tears related to mesh simplification. With some libraries, removing vertices or faces during decimation can disrupt edge connectivity and leave holes that require patching before subsequent steps. MeshLib preserves topology.
- Format-conversion losses. Exporting or importing across file types can drop polygons or scramble index order. As a result, missing faces and disconnected edges that require repair can be produced.
Code to Fill Holes in 3D Meshes (Python & C++)
The MeshLib library will not leave you alone with hole filling tasks. Thanks to our modern code base, our library streamlines surface repair flows by automating hole filling. We do so in a powerful, flexible way—adaptable to a wide array of use cases. Fill holes with Python and C++ available.
import meshlib.mrmeshpy as mrmeshpy
# Load mesh
mesh = mrmeshpy.loadMesh("mesh.stl")
# Find single edge for each hole in mesh
hole_edges = mesh.topology.findHoleRepresentiveEdges()
for e in hole_edges:
# Setup filling parameters
params = mrmeshpy.FillHoleParams()
params.metric = mrmeshpy.getUniversalMetric(mesh)
# Fill hole represented by `e`
mrmeshpy.fillHole(mesh, e, params)
# Save result
mrmeshpy.saveMesh(mesh, "filledMesh.stl")
#include
#include
#include
#include
int main()
{
// Load mesh
MR::Mesh mesh = *MR::MeshLoad::fromAnySupportedFormat( "mesh.stl" );
// Find single edge for each hole in mesh
std::vector holeEdges = mesh.topology.findHoleRepresentiveEdges();
for ( MR::EdgeId e : holeEdges )
{
// Setup filling parameters
MR::FillHoleParams params;
params.metric = MR::getUniversalMetric( mesh );
// Fill hole represented by `e`
MR::fillHole( mesh, e, params );
}
// Save result
auto saveRes = MR::MeshSave::toAnySupportedFormat( mesh, "filledMesh.stl" );
}


- Your mesh gets loaded.
- Automated hole discovery for filling.
- Parametric control to fine-tune the hole filling process.
- Each hole becomes filled.
- The result is saved.
Supported Programming Languages and Versions
In addition to Python and C++, we also go with C and C#. The following versions are supported:
Language | OS | Version |
---|---|---|
C++ | Windows, macOS, Linux, WebAssembly | Any modern C++ |
Python | Windows | 3.8 – 3.13 |
macOS | 3.9 – 3.13 (the only exception
os 3.8 on macOS x64) | |
Linux | Python 3.8–3.13 (distributions that support manylinux_2_31+ |
Quick-start resources
Python installation guide
C++ installation guide
Grab the full MeshLib package on GitHub
3D Algorithm to Fill Holes in Meshes
Generally speaking, we allow the following approaches to fill holes:
- Fully automatic, metric-optimized triangulation that seals one opening in a single step. Duplicate edge handling is user-configurable. If none of the selected strategies can close the gap without breaking manifoldness, the toolbox automatically falls back to a centroid-fan patch to guarantee a watertight result.
- Batch repair of multiple openings by supplying their representative edges all at once.
- Ultra-fast ‘centroid-fan’ patch that inserts a central vertex and radiates triangles outward. This can be useful for tiny holes or quick prototypes.
- A two-phase workflow that first generates a triangulation plan for inspection. Then the plan is applied to the mesh, as soon as you approve it.
Hole Filling Parameters
The MeshLib library lets you fine-tune every fill operation instead of accepting a one-size-fits-all patch. Key dimensions you can adjust are:
- Pick the quality yardstick aka metric to minimize edge length, dihedral jumps, circumcircle radii, or supply your own metric.
- Say how strictly the patch should avoid duplicate edges, from ‘let it slide’ to ‘re-plan until none remain’.
- Cap the number of times a large rim may be split before triangulation for the purpose of balancing smoothness against speed.
- Optionally, grow a zero-area collar so the seam renders with a crisp crease.
- Flip a safety flag that aborts—or, alternatively, auto-switches to a quick fan—when the patch would flunk your quality threshold.
- Gather the IDs of every new triangle for downstream colouring, smoothing, or analytics.
Metric to Fill Holes
Above, we started the parameter list with the metric for a reason. The latter is the cost function that ranks each candidate triangle or edge while the patch is assembled. Alter the metric and you redefine what ‘best’ means to the algorithm in terms of shape, smoothness, even added surface area.
- Prioritise low dihedral angles and avoid skinny triangles with our Universal Metric. It tends to give balanced and smooth patches in most common cases;
- CircumscribedMetric minimizes circumcircle radii to create a Delaunay-style patch as a simple yet balanced match for filling basic holes;
- Keep the patch flush with a known flat plane, which is ideal for lids and machined parts or just any planar holes via PlaneFillMetric;
- Shrink the total length of new edges when triangle count through the EdgeLengthFillMetric;
- Blend triangle shape, edge length and curvature change for the cleanest patch on organic scans via ComplexFillMetric;
- When bridging between two holes, use the stitch-oriented ComplexStitchMetric for a smooth cylindrical connection;
- Constrain every new face to stay parallel to a chosen axis with VerticalStitchMetric, another stitch-oriented metric;
- Employ getMinTriAngleMetric to maximise the smallest interior angle;
- Limit the largest dihedral angle to keep shading gradients silky smooth with MaxDihedralAngleMetric;
- Cut added area to the bone via MinAreaMetric, accepting possible degeneracies, when surface growth must be minimal;
- Or plug in your own triangle/edge/combine lambdas for any niche quality rule you can imagine through FillHoleMetric. This makes MeshLib a flexible choice for anyone building or customizing a fill hole algorithm grid tailored to specific design constraints.
Our Algorithm Under the Hood
If you feel curious about how our fill hole algorithm grid operates internally, here is a simplified overview of the key steps
- Tracing the rim. The flow starts at the edge you pass in and walks the boundary loop to collect every vertex that borders the opening.
- Polygon handling within the limits you set. At each stage, the algorithm considers up to maxPolygonSubdivisionscandidate diagonals, scores them, and repeats the same search on the two sub-polygons created. This iterative process helps balance quality and performance. Higher values allow deeper candidate analysis, which may improve triangulation quality according to the selected metric.
- Score candidate patches. It sketches many possible diagonals and triangles and rates each one with your chosen metric. That metric—edge length, dihedral smoothness, area, or any custom formula—defines what ‘best; means.
- Picking the global best layout. A dynamic search assembles the full triangulation that has the lowest total cost, rather than choosing triangles one-by-one.
- Polishing. When you enable strong duplicate-edge mode, MeshLib adds a quality sweep. Namely, it attempts to avoid duplicate edges, even if that means slightly lowering the triangulation metric. If a duplicate is unavoidable, MeshLib switches to a simple fan fill (or aborts, if you asked it to).
- Committing. New faces, edges, and any extra vertices are written straight into the mesh arrays, so you get a watertight, manifold model with zero copying.
Real-world Capabilities
To highlight what our library can do for you in the terms of hole filling operations, here is a brief summary with illustrations:
- When it comes to flat surfaces, this is what can be accomplished:
- Minimal flat fill. A quick, no-frills triangulation that patches planar gaps while keeping the geometry lean.
- Enhanced flat fill. Adding a few extra vertices for a tidier edge flow when a flat area still needs higher accuracy.
- As for curved surfaces, our library is good at:
- Smooth filling. Laying down curvature-aware triangles that blend cleanly into surrounding faces, hiding the repair (smooth).
- Natural filling. Going further by gently relaxing the patch and its immediate neighbourhood, making the fix virtually invisible on intricate shapes.
- Finally, when you deal with linking or splitting gaps:
- Stitching unifies two holes into one continuous, watertight surface (connecting holes).
- Bridging inserts a controlled strip of faces to join two selected rims—or to split one hole into two—giving precise control over model topology (make bridge).
Filling hole example
Stitching example
Before


After


Smoothed


Pros of MeshLib for Hole Filling
- Fast and reliable flat-surface repair. Our 3D processing library handles planar holes with ease, offering quick, minimal triangulation that preserves structural integrity without overcomplicating the mesh.
- Smart handling of complex gaps. For more irregular or detailed holes, our toolbox generates smoother, better-shaped patches that follow the model’s natural flow—ensuring both geometry and function are maintained.
- Curvature-aware filling. When working with curved or organic surfaces, the library adapts to local geometry, producing fills that blend seamlessly with the surrounding area.
Video Guide
What our customers say
Thomas Tong
Founder, Polyga

Gal Cohen
CTO, customed.ai

Mariusz Hermansdorfer
Head of Computational Design at Henning Larsen Architechts

HeonJae Cho, DDS, MSD, PhD
Chief Executive Officer, 3DONS INC

Ruedger Rubbert
Chief Technology Officer, Brius Technologies Inc








Start Your Journey with MeshLib
MeshLib SDK offers multiple ways to dive in — from live technical demos to full application trials and hands-on SDK access. No complicated setups or hidden steps. Just the tools you need to start building smarter, faster, and better.
