Consider these two simple Polyhedrons which share a sub-face:
p1 = Polyhedron[
{{0, 0, 0}, {2, 0, 0}, {2, 1, 0}, {0, 1, 0}, {0, 0, 1}, {2, 0, 1}, {2, 1, 1}, {0, 1, 1}},
{{1, 2, 3, 4}, {5, 6, 7, 8}, {1, 2, 6, 5}, {2, 3, 7, 6}, {3, 4, 8, 7}, {4, 1, 5, 8}}];
p2 = TransformedRegion[p1, TranslationTransform[{1, 0, 1}]];
I wish to produce a third Polyhedron which describes the union of these shapes, as suggested by the Region
admitted by RegionUnion
:
Unfortunately the Polyhedron produced by RegionUnion
has not merged the 'side faces' but has actually split up previous individual faces!
It seems like MeshCells[]
is unable to return a single Polyhedron describing the full volume.
MeshCells[RegionUnion[p1, p2], 3]
>>> MeshCells: There is no simple cell representation for the specified cells of the BoundaryMeshRegion
My issues with the generated polyhedron do not appear to constitute mesh defects:
In principle, I can obtain a list of all the individual faces admitted by RegionUnion
...
p3 = RegionUnion[p1, p2];
coords = First[p3];
faces = MeshCells[p3, 2] /. i_Integer :> coords[[i]];
and attempt to stitch them myself into "clean" polyhedron faces by unifying co-planar edge-intersecting faces (using e.g. Not @ RegionDisjoint[faces[[i]], faces[[j]]
). This appears to require rotating co-planar faces into 2D Polygon, merging them and rotating back - quite a pain for one might expect as a basic Mathematica function!
Is there a way to achieve a simple unified Polyhedron like the one I have constructed below by hand:
p3 = Polyhedron[{
{0, 0, 0}, {2, 0, 0}, {2, 0, 1}, {3, 0, 1}, {3, 0, 2}, {1, 0, 2}, {1, 0, 1}, {0, 0, 1},
{0, 1, 0}, {2, 1, 0}, {2, 1, 1}, {3, 1, 1}, {3, 1, 2}, {1, 1, 2}, {1, 1, 1}, {0, 1, 1}
}, {
Range[8], 8 + Range[8],
{1, 8, 16 , 9},
Sequence @@ Table[i + {0, 1, 9, 8}, {i, 7}]
}]
Adverserial example for cvgmt's solution
The proposed solution of
BoundaryDiscretizeRegion @ RegionUnion[{p1,p2}] // Region`Mesh`MergeCells
has some issues for longer lists of more complicated Polyhedron.
For example:
vols = {Polyhedron[{{202., 277.22222222222223`, 40}, {300., 250.,
40}, {300., 296., 40}, {202., 296., 40}, {202.,
277.22222222222223`, 52}, {300., 250., 52}, {300., 296.,
52}, {202., 296., 52}}, {{1, 2, 3, 4}, {5, 6, 7, 8}, {1, 2, 6,
5}, {2, 3, 7, 6}, {3, 4, 8, 7}, {4, 1, 5, 8}}],
Polyhedron[{{400., 257.77777777777777`, 40}, {400.,
222.22222222222223`, 40}, {480., 200., 40}, {400.,
257.77777777777777`, 52}, {400., 222.22222222222223`,
52}, {480., 200., 52}}, {{1, 2, 3}, {4, 5, 6}, {1, 2, 5, 4}, {2,
3, 6, 5}, {3, 1, 4, 6}}],
Polyhedron[{{400., 257.77777777777777`, 0}, {300., 330., 0}, {150.,
350., 0}, {120., 300., 0}, {202., 277.22222222222223`,
0}, {202., 296., 0}, {300., 296., 0}, {300., 250., 0}, {400.,
222.22222222222223`, 0}, {400., 257.77777777777777`, 12}, {300.,
330., 12}, {150., 350., 12}, {120., 300., 12}, {202.,
277.22222222222223`, 12}, {202., 296., 12}, {300., 296.,
12}, {300., 250., 12}, {400., 222.22222222222223`, 12}}, {{1, 2,
3, 4, 5, 6, 7, 8, 9}, {10, 11, 12, 13, 14, 15, 16, 17, 18}, {1,
2, 11, 10}, {2, 3, 12, 11}, {3, 4, 13, 12}, {4, 5, 14, 13}, {5,
6, 15, 14}, {6, 7, 16, 15}, {7, 8, 17, 16}, {8, 9, 18, 17}, {9,
1, 10, 18}}],
Polyhedron[{{312., 246.66667169012294`, 12}, {312., 308.,
12}, {190., 308., 12}, {190., 280.55554604499355`, 12}, {202.,
277.22222222222223`, 12}, {202., 296., 12}, {300., 296.,
12}, {300., 250., 12}, {312., 246.66667169012294`, 52}, {312.,
308., 52}, {190., 308., 52}, {190., 280.55554604499355`,
52}, {202., 277.22222222222223`, 52}, {202., 296., 52}, {300.,
296., 52}, {300., 250., 52}}, {{1, 2, 3, 4, 5, 6, 7, 8}, {9, 10,
11, 12, 13, 14, 15, 16}, {1, 2, 10, 9}, {2, 3, 11, 10}, {3, 4,
12, 11}, {4, 5, 13, 12}, {5, 6, 14, 13}, {6, 7, 15, 14}, {7, 8,
16, 15}, {8, 1, 9, 16}}],
Polyhedron[{{388., 266.444472098731, 12}, {388.,
225.55554579605914`, 12}, {400., 222.22222222222223`,
12}, {400., 257.77777777777777`, 12}, {388., 266.444472098731,
52}, {388., 225.55554579605914`, 52}, {400.,
222.22222222222223`, 52}, {400., 257.77777777777777`, 52}}, {{1,
2, 3, 4}, {5, 6, 7, 8}, {1, 2, 6, 5}, {2, 3, 7, 6}, {3, 4, 8,
7}, {4, 1, 5, 8}}]};
(* doesn't evaluate *)
BoundaryDiscretizeRegion @ RegionUnion[vols]
>>> BoundaryDiscretizeRegion[BooleanRegion[#1 || #2 || #3 || #4 || #5 &, {vols}]]
% // Region`Mesh`MergeCells
>>> Region`Mesh`MergeCells[ BoundaryDiscretizeRegion[ ... ] ]
We could discretise first to avoid BooleanRegion
as per this question...
(* evaluates to a BoundaryMeshRegion *)
reg = RegionUnion[BoundaryDiscretizeRegion /@ testvols]
Alas, now calling MergeCells[reg]
throws an error:
>>> BoundaryMeshRegion::bsuncl: The boundary surface is not closed because the edges Line[{{34,36},{37,35},{36,37},{35,34}}] only come from a single face.
It is also not clear to me how to extract a Polyhedron
from the resulting BoundaryMeshRegion
when this technique does work.
Another strange adverserial example
Consider the list of polyhedrons:
vols = {InputForm[
Polyhedron[{{300., 164.53571428571428`, 10}, {202.,
163.36904761904762`, 10}, {202., -44.66666666666667,
10}, {249., -76., 10}, {300., -44.125, 10}, {300.,
164.53571428571428`, 20}, {202., 163.36904761904762`,
20}, {202., -44.66666666666667, 20}, {249., -76.,
20}, {300., -44.125, 20}}, {{1, 2, 3, 4, 5}, {6, 7, 8, 9, 10}, {
1, 2, 7, 6}, {2, 3, 8, 7}, {3, 4, 9, 8}, {4, 5, 10, 9}, {5, 1, 6,
10}}]], InputForm[
Polyhedron[{{300., -44.125, 0}, {249., -76.,
0}, {202., -44.66666666666667, 0}, {202., -200.,
0}, {300., -200., 0}, {300., -44.125, 10}, {249., -76.,
10}, {202., -44.66666666666667, 10}, {202., -200.,
10}, {300., -200., 10}}, {{1, 2, 3, 4, 5}, {6, 7, 8, 9, 10}, {1,
2, 7, 6}, {2, 3, 8, 7}, {3, 4, 9, 8}, {4, 5, 10, 9}, {5, 1, 6,
10}}]], InputForm[
Polyhedron[{{202., 296., 0}, {202., 163.36904761904762`, 0}, {300.,
164.53571428571428`, 0}, {300., 296., 0}, {202., 296.,
10}, {202., 163.36904761904762`, 10}, {300.,
164.53571428571428`, 10}, {300., 296., 10}}, {{1, 2, 3, 4}, {5,
6, 7, 8}, {1, 2, 6, 5}, {2, 3, 7, 6}, {3, 4, 8, 7}, {4, 1, 5,
8}}]], InputForm[
Polyhedron[{{300.00000220959214`, -55.91747503407568,
10}, {300., -44.125, 10}, {249., -76.,
10}, {202., -44.66666666666667,
10}, {202.00000237873843`, -56.68517250403892,
10}, {248.82501070724447`, -87.90184472304296,
10}, {300.00000220959214`, -55.91747503407568,
20}, {300., -44.125, 20}, {249., -76.,
20}, {202., -44.66666666666667,
20}, {202.00000237873843`, -56.68517250403892,
20}, {248.82501070724447`, -87.90184472304296, 20}}, {{1, 2, 3,
4, 5, 6}, {7, 8, 9, 10, 11, 12}, {1, 2, 8, 7}, {2, 3, 9, 8}, {3,
4, 10, 9}, {4, 5, 11, 10}, {5, 6, 12, 11}, {6, 1, 7, 12}}]],
InputForm[
Polyhedron[{{300., 174.5364228773892, 10}, {202., 173.36975621072256`,
10}, {202., 163.36904761904762`, 10}, {300.,
164.53571428571428`, 10}, {300., 174.5364228773892, 20}, {202.,
173.36975621072256`, 20}, {202., 163.36904761904762`,
20}, {300., 164.53571428571428`, 20}}, {{1, 2, 3, 4}, {5, 6, 7,
8}, {1, 2, 6, 5}, {2, 3, 7, 6}, {3, 4, 8, 7}, {4, 1, 5, 8}}]]}
Attempting to merge these volumes by the same technique above makes two of the faces (and the bounded volume in-between) disappear!
Polyhedron
. What's your game here? $\endgroup$