Open Edwaerd opened 2 years ago
What is a fragment operation?
@Edwaerd If you mean tessellation of a CadQuery object into a mesh, see here.
For example, I have a cylindrical object and also I have smaller other objects inside the cylindrical object(let's say spheres).I want to generate conformal mesh
https://gmsh.info/doc/texinfo/gmsh.html#Boolean-operations https://wiki.freecadweb.org/Part_BooleanFragments
Something like boolean fragments (BRepAlgoAPI_BuilderAlgo
to be specific) is not exposed.
Some time ago I had written an implementation of fragment
by adding a Workplane
method fragment
in cq.py
:
def fragment(
self,
toFragment: Optional[Union["Workplane", Solid, Compound]] = None,
clean: bool = True,
glue: bool = False,
tol: Optional[float] = None,
) -> "Workplane":
"""
Fragment all of the items on the stack of toFragment with the current tool.
If there is no current solid, the items in toFragment are fragmented together.
:param toFragment:
:type toFragment: a solid object, or a CQ object having a solid,
:param boolean clean: call :py:meth:`clean` afterwards to have a clean shape (default True)
:param boolean glue: use a faster gluing mode for non-overlapping shapes (default False)
:param float tol: tolerance value for fuzzy bool operation mode (default None)
:raises: ValueError if there is no solid to add to in the chain
:return: a CQ object with the resulting object selected
"""
# first collect all of the items together
newS: List[Shape]
if isinstance(toFragment, CQ):
newS = cast(List[Shape], toFragment.solids().vals())
if len(newS) < 1:
raise ValueError(
"CQ object must have at least one solid on the stack to union!"
)
elif isinstance(toFragment, (Solid, Compound)):
newS = [toFragment]
else:
raise ValueError("Cannot fragment type '{}'".format(type(toFragment)))
# now combine with existing solid, if there is one
solidRef = self._findType(
(Solid, Compound), searchStack=True, searchParents=True
)
if solidRef is not None:
r = solidRef.fragment(*newS, glue=glue, tol=tol)
elif len(newS) > 1:
r = newS.pop(0).fragment(*newS, glue=glue, tol=tol)
else:
r = newS[0]
if clean:
r = r.clean()
return r
and a Compound
method fragment
in shapes.py
def fragment(
self, *toFragment: "Shape", glue: bool = False, tol: Optional[float] = None
) -> "Shape":
"""
Fragment the positional arguments with this Shape.
:param glue: Sets the glue option for the algorithm, which allows
increasing performance of the intersection of the input shapes
:param tol: Additional tolerance
"""
fragment_op = BRepAlgoAPI_BuilderAlgo()
toFragment = tuple(self) + toFragment
arg = TopTools_ListOfShape()
for obj in toFragment:
arg.Append(obj.wrapped)
fragment_op.SetArguments(arg)
if glue:
fragment_op.SetGlue(BOPAlgo_GlueEnum.BOPAlgo_GlueShift)
if tol:
fragment_op.SetFuzzyValue(tol)
fragment_op.SetRunParallel(True)
fragment_op.Build()
if not fragment_op.IsDone():
print("Fragment Error : ", fragment_op.IsDone())
it = TopoDS_Iterator(fragment_op.Shape())
los = tuple()
while it.More():
los = los + (Shape.cast(it.Value()),)
it.Next()
return Compound.makeCompound(los)
It returns a compound containing the fragments.
@bragostin If you have the time, you can contribute it as a plugin to https://github.com/CadQuery/cadquery-plugins (README of that repository has detailed instructions on how to do it)
@fedorkotov absolutely, I have never written a plugin but I will look at it.
I think fragment
probably does not deserve a PR (I have not found a compelling use case for it yet) but a plugin would make sense.
@fedorkotov done in https://github.com/CadQuery/cadquery-plugins/pull/27#issue-1137766265
Hi, I’ve just started to discover open source modeling programs (Gmsh,FreeCad,Cadquery).I wonder , does cadquery has capability of fragment operation like Gmsh and FreeCad ?
thx