Triangulate a surface given as a MeshRegion

Why not use DiscretizeRegion again but with a lower MaxCellMeasure?

mr = DiscretizeRegion[RegionBoundary[Cuboid[]], MaxCellMeasure -> ∞, 
  MeshCellStyle -> {1 -> Black}]

enter image description here

DiscretizeRegion[mr, MaxCellMeasure -> {2 -> .01}, MeshCellStyle -> {1 -> Black}]

enter image description here


After a bit of spelunking I got this:

r = DiscretizeRegion[RegionBoundary@Cuboid[], 
   MaxCellMeasure -> Infinity, MeshCellStyle -> {1 -> Black}];

Needs["TriangleLink`"]

r2 = Region`Mesh`Triangulate3DFaces[r, TriangleTriangulate[#, "pqa0.01"] &]

enter image description here

{RegionDimension[r2], RegionEmbeddingDimension[r2]}
(* {2, 3} *)

The TriangleTriangulate documentation describes how to control the triangulation.


This is a hack, but it does the trick. The problem is that you can't use TriangulateMesh on a 2D polygon embedded in 3D. One solution is to translate/rotate your polygon to the xy plane, triangulate, then reverse the transformation.

triangulate3DPolygon[Polygon[pts__], opts : OptionsPattern[]] := Module[
    {a, b, c, U, V, W, tr, trpgon, newpts, newpgns},
    (*The rotation matrix - http://math.stackexchange.com/a/856705 *)
    {a, b, c} = pts[[;; 3]];
    tr = a;
    {a, b, c} = # - a & /@ {a, b, c};
    {U, W} = {Normalize[b], Normalize[Cross[b, c]]};
    V = Cross[U, W];
    {U, V, W}.(# - tr) & /@ pts;
    trpgon = TriangulateMesh[
        DiscretizeGraphics[
            Polygon[Most /@ ({U, V, W}.(# - tr) & /@ pts)]],
            opts
            ];
    newpts = (Transpose[{U, V, W}].PadRight[#, 3] + tr) & /@  MeshCoordinates[trpgon];
    newpgns = MeshCells[trpgon, 2];
    {newpts, newpgns}
];

Options[triangulate2DMeshEmb3D] = {"OutputType" -> "MeshRegion"};
triangulate2DMeshEmb3D[mesh_,opts : OptionsPattern[
    {MeshRegion, TriangulateMesh, Graphics3D, triangulate2DMeshEmb3D}]
    ] :=Module[ {pgons, data, extracount, bag, pgonPrimitives, head, pts},
    pgons = MeshPrimitives[mesh, 2];
    data = triangulate3DPolygon[#, 
        Evaluate@FilterRules[{opts}, Options[TriangulateMesh]]] & /@ pgons;

    extracount = 0;
    bag = Internal`Bag[];
    pgonPrimitives = {};

    Do[
     pgonPrimitives = Join[
        pgonPrimitives,
        data[[n, 2]] /. Polygon[a__] :> Polygon[a + extracount]
     ];
     Do[
      extracount++;
      Internal`StuffBag[bag, pt],
      {pt, data[[n, 1]]}
      ];
     , {n, Length@data}
     ];
    head = Switch[OptionValue["OutputType"], "MeshRegion", MeshRegion, 
      "Graphics3D", Graphics3D@*GraphicsComplex];
    pts = Internal`BagPart[bag, All];
    Clear[bag];
    head[pts, pgonPrimitives, 
     Evaluate[FilterRules[{opts}, Options[head]]]]
];

If you don't tell MeshRegion to color the lines in black, then you might think it didn't work,

enter image description here

But you can see that it does work, and the triangulation is customizable,

triangulate2DMeshEmb3D[
   msh,
   MeshCellStyle -> {1 -> Black},
   MaxCellMeasure -> #] & /@ {.2, .01}
Through[{RegionEmbeddingDimension, RegionDimension}[First@%]]

enter image description here