コード例 #1
0
 def test_TopoDS_byref_arguments(self):
     '''
     Test byref pass arguments to TopoDS
     '''
     cyl1 = BRepPrimAPI_MakeCylinder(10., 10.).Shape()
     cyl2 = BRepPrimAPI_MakeCylinder(100., 50.).Shape()
     c = TopoDS_Compound()
     self.assertTrue(c.IsNull())
     bb = TopoDS_Builder()
     bb.MakeCompound(c)
     for child in [cyl1, cyl2]:
         bb.Add(c, child)
     self.assertFalse(c.IsNull())
コード例 #2
0
def occ_triangle_mesh(event=None):
    #
    # Mesh the shape
    #
    BRepMesh_IncrementalMesh(aShape, 0.1)
    builder = BRep_Builder()
    Comp = TopoDS_Compound()
    builder.MakeCompound(Comp)

    ex = TopExp_Explorer(aShape, TopAbs_FACE)
    while ex.More():
        F = topods_Face(ex.Current())
        L = TopLoc_Location()
        facing = (BRep_Tool().Triangulation(F, L))
        tab = facing.Nodes()
        tri = facing.Triangles()
        for i in range(1, facing.NbTriangles() + 1):
            trian = tri.Value(i)
            #print trian
            index1, index2, index3 = trian.Get()
            for j in range(1, 4):
                if j == 1:
                    M = index1
                    N = index2
                elif j == 2:
                    N = index3
                elif j == 3:
                    M = index2
                ME = BRepBuilderAPI_MakeEdge(tab.Value(M), tab.Value(N))
                if ME.IsDone():
                    builder.Add(Comp, ME.Edge())
        ex.Next()
    display.DisplayShape(Comp, update=True)
コード例 #3
0
def _unify_compound(proto):
    builder = BRep_Builder()
    comp = TopoDS_Compound()

    builder.MakeCompound(comp)

    explorer = TopExp_Explorer()

    explorer.Init(proto.Shape(), TopAbs_SOLID)
    while explorer.More():
        builder.Add(comp, _unify_solid(Shape(explorer.Current())).Solid())
        explorer.Next()

    explorer.Init(proto.Shape(), TopAbs_SHELL, TopAbs_SOLID)
    while explorer.More():
        builder.Add(comp, _unify_shell(Shape(explorer.Current())).Shell())
        explorer.Next()

    faces = []
    explorer.Init(proto.Shape(), TopAbs_FACE, TopAbs_SHELL)
    while explorer.More():
        faces.append(Shape(explorer.Current()))
        explorer.Next()

    faces_new = _unify_faces_array(faces)
    for f in faces_new:
        builder.Add(comp, f.Shape())

    return Shape(comp)
コード例 #4
0
    def prop_soild(self, sol=TopoDS_Solid()):
        self.sol_builder = TopoDS_Builder()

        sol_exp = TopExp_Explorer(sol, TopAbs_FACE)
        sol_top = TopologyExplorer(sol)
        #print(self.cal_vol(sol), self.base_vol)
        print(sol_top.number_of_faces())

        self.face_lst = TopTools_ListOfShape()
        self.face_cnt = []
        self.face_num = 0
        self.face_init(sol_exp.Current())
        #self.sol_builder.Add(sol, sol_exp.Current())
        sol_exp.Next()

        while sol_exp.More():
            face = sol_exp.Current()
            self.face_expand(face)
            sol_exp.Next()

        if self.file == True:
            stp_file = "./shp/shp_{:04d}.stp".format(self.sol_num)
            write_step_file(sol, stp_file)

            stp_file = "./shp/shp_{:04d}_exp.stp".format(self.sol_num)
            new_shpe = TopoDS_Compound()
            self.sol_builder.Add(gp_Pnt())
            # self.sol_builder.MakeCompSolid(new_shpe)
            #write_step_file(new_shpe, stp_file)

        # if self.show == True:
        #    self.display.DisplayShape(self.face_cnt)
        """self.face_init(face)
コード例 #5
0
    def AddVerticesToScene(self, pnt_list, vertex_color, vertex_width=5):
        """ shp is a list of gp_Pnt
        """
        vertices_list = []  # will be passed to pythreejs
        BB = BRep_Builder()
        compound = TopoDS_Compound()
        BB.MakeCompound(compound)

        for vertex in pnt_list:
            vertex_to_add = BRepBuilderAPI_MakeVertex(vertex).Shape()
            BB.Add(compound, vertex_to_add)
            vertices_list.append([vertex.X(), vertex.Y(), vertex.Z()])

        # map the Points and the AIS_PointCloud
        # and to the dict of shapes, to have a mapping between meshes and shapes
        point_cloud_id = "%s" % uuid.uuid4().hex
        self._shapes[point_cloud_id] = compound

        vertices_list = np.array(vertices_list, dtype=np.float32)
        attributes = {
            "position": BufferAttribute(vertices_list, normalized=False)
        }
        mat = PointsMaterial(color=vertex_color,
                             sizeAttenuation=True,
                             size=vertex_width)
        geom = BufferGeometry(attributes=attributes)
        points = Points(geometry=geom, material=mat, name=point_cloud_id)
        return points
コード例 #6
0
 def write_target_edges(self,filename):
   comp = TopoDS_Compound()
   builder = BRep_Builder()
   builder.MakeCompound(comp)
   for shape in self.target_edges:
     builder.Add(comp, shape)
   breptools_Write(comp,filename)
コード例 #7
0
ファイル: base_occ.py プロジェクト: tnakaicode/OCCGO
def face_mesh_triangle(comp=TopoDS_Shape(), isR=0.1, thA=0.1):
    # Mesh the shape
    BRepMesh_IncrementalMesh(comp, isR, True, thA, True)
    bild1 = BRep_Builder()
    comp1 = TopoDS_Compound()
    bild1.MakeCompound(comp1)
    bt = BRep_Tool()
    ex = TopExp_Explorer(comp, TopAbs_FACE)
    while ex.More():
        face = topods_Face(ex.Current())
        location = TopLoc_Location()
        facing = bt.Triangulation(face, location)
        tab = facing.Nodes()
        tri = facing.Triangles()
        print(facing.NbTriangles(), facing.NbNodes())
        for i in range(1, facing.NbTriangles() + 1):
            trian = tri.Value(i)
            index1, index2, index3 = trian.Get()
            for j in range(1, 4):
                if j == 1:
                    m = index1
                    n = index2
                elif j == 2:
                    n = index3
                elif j == 3:
                    m = index2
                me = BRepBuilderAPI_MakeEdge(tab.Value(m), tab.Value(n))
                if me.IsDone():
                    bild1.Add(comp1, me.Edge())
        ex.Next()
    return comp1
コード例 #8
0
ファイル: base_occ.py プロジェクト: tnakaicode/OCCGO
 def make_comp_selcted(self):
     bild = BRep_Builder()
     comp = TopoDS_Compound()
     bild.MakeCompound(comp)
     for shp in self.selected_shape:
         print(shp)
         bild.Add(comp, shp)
     return comp
コード例 #9
0
ファイル: CoreBall.py プロジェクト: tnakaicode/GeomSurf
 def export_file(self):
     builder = BRep_Builder()
     compound = TopoDS_Compound()
     builder.MakeCompound(compound)
     builder.Add(compound, self.b1)
     builder.Add(compound, self.b2)
     builder.Add(compound, make_polygon(self.pts))
     write_step_file(compound, "./tmp/test.stp")
コード例 #10
0
ファイル: DoubleBall.py プロジェクト: tnakaicode/GeomSurf
 def export_file(self):
     builder = BRep_Builder()
     compound = TopoDS_Compound()
     builder.MakeCompound(compound)
     builder.Add(compound, self.b1)
     builder.Add(compound, self.b2)
     builder.Add(compound, make_polygon(self.pts))
     self.export_stp(compound)
コード例 #11
0
ファイル: base.py プロジェクト: tnakaicode/Motion
 def export_stp_selected(self):
     if self.touch == True:
         builder = BRep_Builder()
         compound = TopoDS_Compound()
         builder.MakeCompound(compound)
         for shp in self.selected_shape:
             print(shp)
             builder.Add(compound, shp)
         self.export_stp(compound)
コード例 #12
0
 def __init__(self, shapes):
     topods_compound = TopoDS_Compound()
     builder = BRep_Builder()
     builder.MakeCompound(topods_compound)
     for shape in shapes:
         shape = Shape.to_shape(shape)
         if isinstance(shape, Shape):
             builder.Add(topods_compound, shape.object)
     self._cp = Compound(topods_compound)
コード例 #13
0
ファイル: step.py プロジェクト: khabya/aoc-xchange
 def compound(self):
     """ Create and returns a compound from the _shapes list"""
     # Create a compound
     compound = TopoDS_Compound()
     brep_builder = BRep_Builder()
     brep_builder.MakeCompound(compound)
     # Populate the compound
     for shape in self._shapes:
         brep_builder.Add(compound, shape)
     return compound
コード例 #14
0
 def __init__(self,name,wire=False) :
     from OCC.Core.BRep import BRep_Builder
     from OCC.Core.TopoDS import TopoDS_Compound
     self.Name = name
     self.Wire = wire
     self.Objects = []
     self.SubVols = []
     #Combined shape of objects
     self.Compound = TopoDS_Compound() 
     self.Builder = BRep_Builder()
     self.Builder.MakeCompound(self.Compound)
コード例 #15
0
def compound(topo):
    '''
    accumulate a bunch of TopoDS_* in list `topo` to a TopoDS_Compound
    @param topo: list of TopoDS_* instances
    '''
    bd = TopoDS_Builder()
    comp = TopoDS_Compound()
    bd.MakeCompound(comp)
    for i in topo:
        bd.Add(comp, i)
    return comp
コード例 #16
0
def read_iges_file(filename,
                   return_as_shapes=False,
                   verbosity=False,
                   visible_only=False):
    """ read the IGES file and returns a compound
    filename: the file path
    return_as_shapes: optional, False by default. If True returns a list of shapes,
                      else returns a single compound
    verbosity: optionl, False by default.
    """
    if not os.path.isfile(filename):
        raise FileNotFoundError("%s not found." % filename)

    iges_reader = IGESControl_Reader()
    iges_reader.SetReadVisible(visible_only)
    status = iges_reader.ReadFile(filename)

    _shapes = []

    if status == IFSelect_RetDone:  # check status
        if verbosity:
            failsonly = False
            iges_reader.PrintCheckLoad(failsonly, IFSelect_ItemsByEntity)
            iges_reader.PrintCheckTransfer(failsonly, IFSelect_ItemsByEntity)
        iges_reader.TransferRoots()
        nbr = iges_reader.NbRootsForTransfer()
        for n in range(1, nbr + 1):
            nbs = iges_reader.NbShapes()
            if nbs == 0:
                print("At least one shape in IGES cannot be transfered")
            elif nbr == 1 and nbs == 1:
                a_res_shape = iges_reader.Shape(1)
                if a_res_shape.IsNull():
                    print("At least one shape in IGES cannot be transferred")
                else:
                    _shapes.append(a_res_shape)
            else:
                for i in range(1, nbs + 1):
                    a_shape = iges_reader.Shape(i)
                    if a_shape.IsNull():
                        print(
                            "At least one shape in STEP cannot be transferred")
                    else:
                        _shapes.append(a_shape)
    # if not return as shapes
    # create a compound and store all shapes
    if not return_as_shapes:
        builder = BRep_Builder()
        compound = TopoDS_Compound()
        builder.MakeCompound(compound)
        for s in _shapes:
            builder.Add(compound, s)
        _shapes = compound
    return _shapes
コード例 #17
0
    def __init__(self):
        plotocc.__init__(self)
        self.compound = TopoDS_Compound()
        self.builder = BRep_Builder()
        self.builder.MakeCompound(self.compound)

        mmat = math_Matrix(1, 4, 1, 3, 0.0)
        mmat.SetDiag(1.0)
        print(mmat.Determinant())
        print(mmat.DumpToString())
        mvec = math_Vector(1, 3)
        print(mvec.Norm())
        print(mvec.DumpToString())
コード例 #18
0
def move_to_box(iname, cname, wname, visualize=False):
    """Move foam to periodic box.

    Works on BREP files. Information about physical volumes is lost.

    Args:
        iname (str): input filename
        cname (str): output filename with cells
        wname (str): output filename with walls
        visualize (bool): show picture of foam morphology in box if True
    """
    cells = TopoDS_Shape()
    builder = BRep_Builder()
    breptools_Read(cells, iname, builder)
    texp = TopologyExplorer(cells)
    solids = list(texp.solids())

    cells = TopoDS_Compound()
    builder.MakeCompound(cells)

    box = BRepPrimAPI_MakeBox(gp_Pnt(1, -1, -1), 3, 3, 3).Shape()
    vec = gp_Vec(-1, 0, 0)
    solids = slice_and_move(solids, box, vec)
    box = BRepPrimAPI_MakeBox(gp_Pnt(-3, -1, -1), 3, 3, 3).Shape()
    vec = gp_Vec(1, 0, 0)
    solids = slice_and_move(solids, box, vec)
    box = BRepPrimAPI_MakeBox(gp_Pnt(-1, 1, -1), 3, 3, 3).Shape()
    vec = gp_Vec(0, -1, 0)
    solids = slice_and_move(solids, box, vec)
    box = BRepPrimAPI_MakeBox(gp_Pnt(-1, -3, -1), 3, 3, 3).Shape()
    vec = gp_Vec(0, 1, 0)
    solids = slice_and_move(solids, box, vec)
    box = BRepPrimAPI_MakeBox(gp_Pnt(-1, -1, 1), 3, 3, 3).Shape()
    vec = gp_Vec(0, 0, -1)
    solids = slice_and_move(solids, box, vec)
    box = BRepPrimAPI_MakeBox(gp_Pnt(-1, -1, -3), 3, 3, 3).Shape()
    vec = gp_Vec(0, 0, 1)
    solids = slice_and_move(solids, box, vec)
    create_compound(solids, cells, builder)
    breptools_Write(cells, cname)
    if visualize:
        display, start_display, _, _ = init_display()
        display.DisplayShape(cells, update=True)
        start_display()
    box = BRepPrimAPI_MakeBox(gp_Pnt(0, 0, 0), 1, 1, 1).Shape()
    walls = BRepAlgoAPI_Cut(box, cells).Shape()
    breptools_Write(walls, wname)
    if visualize:
        display, start_display, _, _ = init_display()
        display.DisplayShape(walls, update=True)
        start_display()
コード例 #19
0
def make_compound(parts):
    """
    Takes a list of parts and returns a TopoDS_Compound
    from the parts' shapes.

    :param parts: A list of Part instances

    :return: a TopoDS_Compound from all of the parts' shapes
    """
    compound = TopoDS_Compound()
    builder = BRep_Builder()
    builder.MakeCompound(compound)
    for part in parts:
        builder.Add(compound, part._shape)
    return compound
コード例 #20
0
    def __init__(self):
        super().__init__()

        self.builder = BRep_Builder()
        self.compound = TopoDS_Compound()
        self.builder.MakeCompound(self.compound)

        schema = 'AP203'
        assembly_mode = 1

        self.writer = STEPControl_Writer()
        self.fp = self.writer.WS().TransferWriter().FinderProcess()
        Interface_Static_SetCVal('write.step.schema', schema)
        Interface_Static_SetCVal('write.step.unit', 'M')
        Interface_Static_SetCVal('write.step.assembly', str(assembly_mode))
コード例 #21
0
def read_step_file(filename, return_as_shapes=False, verbosity=True):
    """ read the STEP file and returns a compound
    filename: the file path
    return_as_shapes: optional, False by default. If True returns a list of shapes,
                      else returns a single compound
    verbosity: optional, False by default.
    """
    if not os.path.isfile(filename):
        raise FileNotFoundError("%s not found." % filename)

    step_reader = STEPControl_Reader()
    status = step_reader.ReadFile(filename)

    if status == IFSelect_RetDone:  # check status
        if verbosity:
            failsonly = False
            step_reader.PrintCheckLoad(failsonly, IFSelect_ItemsByEntity)
            step_reader.PrintCheckTransfer(failsonly, IFSelect_ItemsByEntity)

        shapes_to_return = []

        for root_num in range(1, step_reader.NbRootsForTransfer() + 1):
            transfer_result = step_reader.TransferRoot(root_num)

            if not transfer_result:
                raise AssertionError("Transfer failed.")

            shape = step_reader.Shape(root_num)

            if shape.IsNull():
                raise AssertionError("Shape is null.")

            shapes_to_return.append(shape)

        if return_as_shapes:
            return shapes_to_return

        builder = BRep_Builder()
        compound_shape = TopoDS_Compound()
        builder.MakeCompound(compound_shape)

        for shape in shapes_to_return:
            builder.Add(compound_shape, shape)

        return compound_shape

    else:
        raise AssertionError("Error: can't read file.")
コード例 #22
0
ファイル: OCC-Camera.py プロジェクト: tnakaicode/GeomSurf
    def __init__(self):
        plotocc.__init__(self)
        self.compound = TopoDS_Compound()
        self.builder = BRep_Builder()
        self.builder.MakeCompound(self.compound)

        box = BRepPrimAPI_MakeBox(100, 200, 300).Shape()
        self.display.DisplayShape(box)

        con = BRepPrimAPI_MakeCone(gp_Ax2(gp_Pnt(500, 0, 0), gp_Dir(0, 0, 1)),
                                   100, 200, 300).Shape()
        self.display.DisplayShape(con)

        # https://www.opencascade.com/doc/occt-7.4.0/refman/html/class_graphic3d___camera.html
        self.camera = self.display.View.Camera()
        print(self.camera.Scale(), dir_to_vec(self.camera.OrthogonalizedUp()))
        print(self.camera.ViewDimensions())
コード例 #23
0
def list_of_shapes_to_compound(list_of_shapes):
    """ takes a list of shape in input, gather all shapes into one compound
    returns the compund and a boolean, True if all shapes were added to the compund,
    False otherwise
    """
    all_shapes_converted = True
    the_compound = TopoDS_Compound()
    the_builder = BRep_Builder()
    the_builder.MakeCompound(the_compound)
    for shp in list_of_shapes:
        # first ensure the shape is not Null
        if shp.IsNull():
            all_shapes_converted = False
            continue
        else:
            the_builder.Add(the_compound, shp)
    return the_compound, all_shapes_converted
コード例 #24
0
ファイル: entities.py プロジェクト: tnakaicode/AFEM-OCC
    def by_shapes(shapes):
        """
        Create a new compound from a collection of shapes.

        :param collections.Sequence(afem.topology.entities.Shape) shapes: The
            shapes.

        :return: The new compound.
        :rtype: afem.topology.entities.Compound
        """
        topods_compound = TopoDS_Compound()
        builder = BRep_Builder()
        builder.MakeCompound(topods_compound)
        for shape in shapes:
            if isinstance(shape, Shape):
                builder.Add(topods_compound, shape.object)
        return Compound(topods_compound)
コード例 #25
0
def voxel_to_TopoDS(model, voxel_length, voxel_width, voxel_height):
    (position_x, position_y, position_z) = np.where(model.data)
    voxel = TopoDS_Compound()
    counter = TopoDS_Builder()
    counter.MakeCompound(voxel)

    for i in range(position_x.size):
        voxel1 = TopoDS_Shape(
            BRepPrimAPI_MakeBox(voxel_length, voxel_width,
                                voxel_height).Shape())
        transmat = gp_Trsf()
        x, y, z = position_x[i] * voxel_length, position_y[
            i] * voxel_width, position_z[i] * voxel_height
        transmat.SetTranslation(gp_Vec(float(x), float(y), float(z)))
        location = TopLoc_Location(transmat)
        voxel1.Location(location)
        counter.Add(voxel, voxel1)

    return voxel
コード例 #26
0
def simple_mesh():
    #
    # Create the shape
    #
    theBox = BRepPrimAPI_MakeBox(200, 60, 60).Shape()
    theSphere = BRepPrimAPI_MakeSphere(gp_Pnt(100, 20, 20), 80).Shape()
    shape = BRepAlgoAPI_Fuse(theSphere, theBox).Shape()
    #
    # Mesh the shape
    #
    BRepMesh_IncrementalMesh(shape, 0.8)
    builder = BRep_Builder()
    comp = TopoDS_Compound()
    builder.MakeCompound(comp)

    bt = BRep_Tool()
    ex = TopExp_Explorer(shape, TopAbs_FACE)
    while ex.More():
        face = topods_Face(ex.Current())
        location = TopLoc_Location()
        facing = (bt.Triangulation(face, location)).GetObject()
        tab = facing.Nodes()
        tri = facing.Triangles()
        for i in range(1, facing.NbTriangles() + 1):
            trian = tri.Value(i)
            index1, index2, index3 = trian.Get()
            for j in range(1, 4):
                if j == 1:
                    m = index1
                    n = index2
                elif j == 2:
                    n = index3
                elif j == 3:
                    m = index2
                me = BRepBuilderAPI_MakeEdge(tab.Value(m), tab.Value(n))
                if me.IsDone():
                    builder.Add(comp, me.Edge())
        ex.Next()
    display.EraseAll()
    display.DisplayShape(shape)
    display.DisplayShape(comp, update=True)
コード例 #27
0
ファイル: iges.py プロジェクト: khabya/aoc-xchange
    def compound(self):
        """ Create and returns a compound from the _shapes list

        Returns
        -------
        TopoDS_Compound

        Notes
        -----
        Importing an iges box results in:
        0 solid
        0 shell
        6 faces
        24 edges

        """
        # Create a compound
        compound = TopoDS_Compound()
        brep_builder = BRep_Builder()
        brep_builder.MakeCompound(compound)
        # Populate the compound
        for shape in self._shapes:
            brep_builder.Add(compound, shape)
        return compound
コード例 #28
0
def startBottle(startOnly=True):  # minus the neck fillet, shelling & threads
    partName = "Bottle-start"
    # The points we'll use to create the profile of the bottle's body
    aPnt1 = gp_Pnt(-width / 2.0, 0, 0)
    aPnt2 = gp_Pnt(-width / 2.0, -thickness / 4.0, 0)
    aPnt3 = gp_Pnt(0, -thickness / 2.0, 0)
    aPnt4 = gp_Pnt(width / 2.0, -thickness / 4.0, 0)
    aPnt5 = gp_Pnt(width / 2.0, 0, 0)

    aArcOfCircle = GC_MakeArcOfCircle(aPnt2, aPnt3, aPnt4)
    aSegment1 = GC_MakeSegment(aPnt1, aPnt2)
    aSegment2 = GC_MakeSegment(aPnt4, aPnt5)

    # Could also construct the line edges directly using the points
    # instead of the resulting line.
    aEdge1 = BRepBuilderAPI_MakeEdge(aSegment1.Value())
    aEdge2 = BRepBuilderAPI_MakeEdge(aArcOfCircle.Value())
    aEdge3 = BRepBuilderAPI_MakeEdge(aSegment2.Value())

    # Create a wire out of the edges
    aWire = BRepBuilderAPI_MakeWire(aEdge1.Edge(), aEdge2.Edge(),
                                    aEdge3.Edge())

    # Quick way to specify the X axis
    xAxis = gp_OX()

    # Set up the mirror
    aTrsf = gp_Trsf()
    aTrsf.SetMirror(xAxis)

    # Apply the mirror transformation
    aBRespTrsf = BRepBuilderAPI_Transform(aWire.Wire(), aTrsf)

    # Get the mirrored shape back out of the transformation
    # and convert back to a wire
    aMirroredShape = aBRespTrsf.Shape()

    # A wire instead of a generic shape now
    aMirroredWire = topods.Wire(aMirroredShape)

    # Combine the two constituent wires
    mkWire = BRepBuilderAPI_MakeWire()
    mkWire.Add(aWire.Wire())
    mkWire.Add(aMirroredWire)
    myWireProfile = mkWire.Wire()

    # The face that we'll sweep to make the prism
    myFaceProfile = BRepBuilderAPI_MakeFace(myWireProfile)

    # We want to sweep the face along the Z axis to the height
    aPrismVec = gp_Vec(0, 0, height)
    myBody = BRepPrimAPI_MakePrism(myFaceProfile.Face(), aPrismVec)

    # Add fillets to all edges through the explorer
    mkFillet = BRepFilletAPI_MakeFillet(myBody.Shape())
    anEdgeExplorer = TopExp_Explorer(myBody.Shape(), TopAbs_EDGE)

    while anEdgeExplorer.More():
        anEdge = topods.Edge(anEdgeExplorer.Current())
        mkFillet.Add(thickness / 12.0, anEdge)

        anEdgeExplorer.Next()

    myBody = mkFillet.Shape()

    # Create the neck of the bottle
    neckLocation = gp_Pnt(0, 0, height)
    neckAxis = gp_DZ()
    neckAx2 = gp_Ax2(neckLocation, neckAxis)

    myNeckRadius = thickness / 4.0
    myNeckHeight = height / 10.0

    mkCylinder = BRepPrimAPI_MakeCylinder(neckAx2, myNeckRadius, myNeckHeight)
    myBody = BRepAlgoAPI_Fuse(myBody, mkCylinder.Shape())
    if startOnly:  # quit here
        uid = win.getNewPartUID(myBody.Shape(), name=partName)
        win.redraw()
        return

    partName = "Bottle-complete"
    # Our goal is to find the highest Z face and remove it
    faceToRemove = None
    zMax = -1

    # We have to work our way through all the faces to find the highest Z face
    aFaceExplorer = TopExp_Explorer(myBody.Shape(), TopAbs_FACE)
    while aFaceExplorer.More():
        aFace = topods.Face(aFaceExplorer.Current())

        if face_is_plane(aFace):
            aPlane = geom_plane_from_face(aFace)

            # We want the highest Z face, so compare this to the previous faces
            aPnt = aPlane.Location()
            aZ = aPnt.Z()
            if aZ > zMax:
                zMax = aZ
                faceToRemove = aFace

        aFaceExplorer.Next()

    facesToRemove = TopTools_ListOfShape()
    facesToRemove.Append(faceToRemove)

    myBody = BRepOffsetAPI_MakeThickSolid(myBody.Shape(), facesToRemove,
                                          -thickness / 50.0, 0.001)

    # Set up our surfaces for the threading on the neck
    neckAx2_Ax3 = gp_Ax3(neckLocation, gp_DZ())
    aCyl1 = Geom_CylindricalSurface(neckAx2_Ax3, myNeckRadius * 0.99)
    aCyl2 = Geom_CylindricalSurface(neckAx2_Ax3, myNeckRadius * 1.05)

    # Set up the curves for the threads on the bottle's neck
    aPnt = gp_Pnt2d(2.0 * math.pi, myNeckHeight / 2.0)
    aDir = gp_Dir2d(2.0 * math.pi, myNeckHeight / 4.0)
    anAx2d = gp_Ax2d(aPnt, aDir)

    aMajor = 2.0 * math.pi
    aMinor = myNeckHeight / 10.0

    anEllipse1 = Geom2d_Ellipse(anAx2d, aMajor, aMinor)
    anEllipse2 = Geom2d_Ellipse(anAx2d, aMajor, aMinor / 4.0)

    anArc1 = Geom2d_TrimmedCurve(anEllipse1, 0, math.pi)
    anArc2 = Geom2d_TrimmedCurve(anEllipse2, 0, math.pi)

    anEllipsePnt1 = anEllipse1.Value(0)
    anEllipsePnt2 = anEllipse1.Value(math.pi)

    aSegment = GCE2d_MakeSegment(anEllipsePnt1, anEllipsePnt2)

    # Build edges and wires for threading
    anEdge1OnSurf1 = BRepBuilderAPI_MakeEdge(anArc1, aCyl1)
    anEdge2OnSurf1 = BRepBuilderAPI_MakeEdge(aSegment.Value(), aCyl1)
    anEdge1OnSurf2 = BRepBuilderAPI_MakeEdge(anArc2, aCyl2)
    anEdge2OnSurf2 = BRepBuilderAPI_MakeEdge(aSegment.Value(), aCyl2)

    threadingWire1 = BRepBuilderAPI_MakeWire(anEdge1OnSurf1.Edge(),
                                             anEdge2OnSurf1.Edge())
    threadingWire2 = BRepBuilderAPI_MakeWire(anEdge1OnSurf2.Edge(),
                                             anEdge2OnSurf2.Edge())

    # Compute the 3D representations of the edges/wires
    breplib.BuildCurves3d(threadingWire1.Shape())
    breplib.BuildCurves3d(threadingWire2.Shape())

    # Create the surfaces of the threading
    aTool = BRepOffsetAPI_ThruSections(True)
    aTool.AddWire(threadingWire1.Wire())
    aTool.AddWire(threadingWire2.Wire())
    aTool.CheckCompatibility(False)
    myThreading = aTool.Shape()

    # Build the resulting compound
    aRes = TopoDS_Compound()
    aBuilder = BRep_Builder()
    aBuilder.MakeCompound(aRes)
    aBuilder.Add(aRes, myBody.Shape())
    aBuilder.Add(aRes, myThreading)
    uid = win.getNewPartUID(aRes, name=partName)
    win.redraw()
コード例 #29
0
def construct_fitter(input_file):
    print("fitting", input_file)
    obj_mesh = trimesh.load(input_file)

    print(len(obj_mesh.faces))
    if len(obj_mesh.faces) > 15000:
        sobj_mesh = obj_mesh.simplify_quadratic_decimation(
            len(obj_mesh.faces) // 20)
    else:
        sobj_mesh = obj_mesh
    print(len(sobj_mesh.faces))
    print(sobj_mesh.scale)
    sobj_mesh.apply_scale(286 / sobj_mesh.scale)
    print(sobj_mesh.scale)
    trimesh.repair.fix_inversion(sobj_mesh)

    def get_simplified_slice(sobj_mesh):
        nice_slice = sobj_mesh.section(plane_origin=sobj_mesh.centroid +
                                       np.array([0, 0, 30]),
                                       plane_normal=[0.55, 0, 1])
        sobj_mesh.visual.face_colors = [255, 170, 120, 255]

        simp_slice = nice_slice.to_planar()[0].simplify_spline()
        return simp_slice, nice_slice

    simp_slice, nice_slice = get_simplified_slice(sobj_mesh)

    total_y_rotation = 0
    rotation_deg_interval = 5
    from scipy.spatial.transform import Rotation as R
    r = R.from_euler('xyz', [[0, rotation_deg_interval, 0]], degrees=True)
    trans_mat = r.as_matrix()

    full_trans_mat = np.eye(4)
    full_trans_mat[:3, :3] = trans_mat

    # if not working, try rotating the image
    while len(simp_slice.entities) != 1 or len(nice_slice.entities) != 1:
        sobj_mesh.apply_transform(full_trans_mat)

        simp_slice, nice_slice = get_simplified_slice(sobj_mesh)

        total_y_rotation += rotation_deg_interval

    if total_y_rotation != 0:
        # add one more for good measure
        r = R.from_euler('xyz', [[0, rotation_deg_interval / 2, 0]],
                         degrees=True)
        trans_mat = r.as_matrix()

        full_trans_mat = np.eye(4)
        full_trans_mat[:3, :3] = trans_mat
        sobj_mesh.apply_transform(full_trans_mat)

        simp_slice, nice_slice = get_simplified_slice(sobj_mesh)

        total_y_rotation += rotation_deg_interval

    node_list = simp_slice.entities[0].nodes

    ordered_vertices = np.array(
        [simp_slice.vertices[p] for p in simp_slice.entities[0].points])

    ordered_vertices *= 1.15

    print('total y rotation:', total_y_rotation)

    RADIUS = 1.2

    def filletEdges(ed1, ed2):
        f = ChFi2d_AnaFilletAlgo()
        f.Init(ed1, ed2, gp_Pln())
        f.Perform(RADIUS - 0.4)
        return f.Result(ed1, ed2)

    def make_vertices(vertices, close_loop=False, smooth_vertices=False):
        if smooth_vertices:
            filter_vec = np.array([0.2, 0.6, 0.2])
        else:
            filter_vec = np.array([0, 1, 0])
        pnts = []
        prev_coords = None
        for i in range(len(vertices)):
            if i == 0:
                if close_loop:
                    row = np.array(
                        [vertices[-1], vertices[i], vertices[i + 1]])
                    coords_list = row.T.dot(filter_vec)
                else:
                    edge_filter_vec = filter_vec[1:]
                    edge_filter_vec[0] += filter_vec[0]
                    coords_list = vertices[i:i + 2].T.dot(edge_filter_vec)
            elif i == len(vertices) - 1:
                if close_loop:
                    row = np.array([vertices[i - 1], vertices[i], vertices[0]])
                    coords_list = row.T.dot(filter_vec)
                else:
                    edge_filter_vec = filter_vec[:-1]
                    edge_filter_vec[-1] += filter_vec[-1]
                    coords_list = vertices[i - 1:i + 1].T.dot(edge_filter_vec)
            else:
                coords_list = vertices[i - 1:i + 2].T.dot(filter_vec)
            # print(coords_list)
            coords_list = list(coords_list)
            # raise Exception
            if prev_coords is None or coords_list != prev_coords:
                # print(coords_list)
                pnts.append(gp_Pnt(coords_list[0], coords_list[1], 0))
                prev_coords = coords_list
        return pnts

    def vertices_to_edges(pnts):
        edges = [
            BRepBuilderAPI_MakeEdge(pnts[i - 1], pnts[i]).Edge()
            for i in range(1, len(pnts))
        ]
        return edges

    def edges_to_fillets(edges):
        fillets = []
        for i in range(1, len(edges)):
            try:
                fillets.append(filletEdges(edges[i - 1], edges[i]))
            except Exception:
                print(i - 1)
                print(edges[i - 1])
                print(edges[i])
                raise Exception
        return fillets

    def make_wire(edges, fillets=None):
        # the wire
        # print("adding wire")
        makeWire = BRepBuilderAPI_MakeWire()
        makeWire.Add(edges[0])
        if fillets is None:
            for edge in edges[1:]:
                makeWire.Add(edge)
        else:
            for fillet, edge in zip(fillets, edges[1:]):
                makeWire.Add(fillet)
                makeWire.Add(edge)
        # print("build wire")
        makeWire.Build()
        # print("make wire")
        try:
            wire = makeWire.Wire()
        except RuntimeError as e:
            print(type(makeWire))
            raise e
        return wire

    def make_pipe(wire, p1, p2):
        # the pipe
        if p2 is not None:
            direction_coords = np.array(p2.XYZ().Coord()) - np.array(
                p1.XYZ().Coord())
            direction_coords /= np.linalg.norm(direction_coords)
            direction = gp_Dir(*list(direction_coords))
        else:
            direction = gp_Dir(1, 0, 0)
        # print(p1.XYZ().Coord(), p2.XYZ().Coord())
        circle = gp_Circ(gp_Ax2(p1, direction), RADIUS)
        profile_edge = BRepBuilderAPI_MakeEdge(circle).Edge()
        profile_wire = BRepBuilderAPI_MakeWire(profile_edge).Wire()
        profile_face = BRepBuilderAPI_MakeFace(profile_wire).Face()
        pipe = BRepOffsetAPI_MakePipe(wire, profile_face).Shape()
        return pipe

    def filter_vertices(pnts, close_loop):
        good_pnts = []
        if close_loop:
            pnts.extend(pnts[:2])
        else:
            good_pnts = pnts[:2]
        for i in range(2, len(pnts)):
            # print("testing vertices:", pnts[i-2].XYZ().Coord(), pnts[i-1].XYZ().Coord(), pnts[i].XYZ().Coord())
            good_pnts.append(pnts[i])
            continue

            matrix = np.array([
                pnts[i - 2].XYZ().Coord(), pnts[i - 1].XYZ().Coord(),
                pnts[i].XYZ().Coord()
            ])
            np.savetxt('filter_vertices.txt', matrix)
            import subprocess

            cmd = subprocess.run(
                ["python", "test_point.py", "filter_vertices.txt"],
                capture_output=True)
            stdout = cmd.stdout.decode()  # bytes => str
            if 'good' in stdout:
                print("good point", i)
                good_pnts.append(pnts[i])
            else:
                print(stdout)
        return good_pnts

    def compose_wire(pnts,
                     close_loop=False,
                     smooth_vertices=False,
                     add_fillets=True):
        # print("makevert")
        pnts = make_vertices(pnts, close_loop, smooth_vertices)
        print("filtvert")
        pnts = filter_vertices(pnts, close_loop)
        # close the loop
        if close_loop:
            pnts.append(pnts[0])
        # the edges
        print("makeedge with", len(pnts), "vertices")
        edges = vertices_to_edges(pnts)  # [:len(pnts)//4])

        if add_fillets:
            print("makefillets")
            fillets = edges_to_fillets(edges)

        print("makewire")
        if add_fillets:
            wire = make_wire(edges, fillets)
        else:
            wire = make_wire(edges, fillets=None)
        return wire, pnts

    def compose_pipe(vertices,
                     close_loop=False,
                     smooth_vertices=False,
                     add_fillets=True):
        wire, pnts = compose_wire(vertices, close_loop, smooth_vertices,
                                  add_fillets)
        pipe = make_pipe(wire, pnts[0], pnts[1])
        return pipe

    def render_pipe(pipe):
        my_renderer = JupyterRenderer(compute_normals_mode=NORMAL.CLIENT_SIDE)
        my_renderer.DisplayShape(pipe,
                                 shape_color="blue",
                                 topo_level="Face",
                                 quality=1.)  # default quality
        print(my_renderer)

    from OCC.Core.BRepPrimAPI import BRepPrimAPI_MakeSphere

    def make_sphere(centre, radius):
        pnt = gp_Pnt(*list(centre))
        sphere = BRepPrimAPI_MakeSphere(pnt, radius).Shape()
        return sphere

    # In[7]:

    wire, pnts = compose_wire(ordered_vertices,
                              close_loop=False,
                              smooth_vertices=True)
    pipe = make_pipe(wire, pnts[0], pnts[1])

    recovered_vertices = np.array([pnt.XYZ().Coord() for pnt in pnts])
    recovered_vertices.mean(axis=0), recovered_vertices.max(
        axis=0), recovered_vertices.min(axis=0)

    # In[8]:

    # def create_handles
    """
    make new ring that is scaled up version of original
    atan2(3/4), -atan2(3/4)
    atan(3/-2) + pi, -(atan(3/-2) + pi)

    find vertex with greatest normalized dot product with [3,4,0] in +y, use as cutoffs
    with above and below zero

    then add even vertices from cutoffs to max x and min x points in bigger
    """
    y_axis_flip = np.array([1, -1, 1])
    ur_angle = np.array([7, 3, 0])
    dr_angle = ur_angle * y_axis_flip
    angle_prods = recovered_vertices.dot(ur_angle) / np.linalg.norm(
        recovered_vertices, axis=1)
    ur_vertex = recovered_vertices[angle_prods.argmax()]

    angle_prods = recovered_vertices.dot(dr_angle) / np.linalg.norm(
        recovered_vertices, axis=1)
    dr_vertex = recovered_vertices[angle_prods.argmax()]

    ul_angle = np.array([-3, 3, 0])
    dr_angle = ul_angle * y_axis_flip
    angle_prods = recovered_vertices.dot(ul_angle) / np.linalg.norm(
        recovered_vertices, axis=1)
    ul_vertex = recovered_vertices[angle_prods.argmax()]

    angle_prods = recovered_vertices.dot(dr_angle) / np.linalg.norm(
        recovered_vertices, axis=1)
    dl_vertex = recovered_vertices[angle_prods.argmax()]
    print(ur_vertex, ul_vertex)

    exp_vertices = recovered_vertices * 1.15

    upper_verts = exp_vertices[exp_vertices[:, 1] > 0]
    upper_verts = upper_verts[upper_verts[:, 0] >= ul_vertex[0]]
    upper_verts = upper_verts[upper_verts[:, 0] <= ur_vertex[0]]
    upper_verts = upper_verts[upper_verts[:, 0].argsort()]

    lower_verts = exp_vertices[exp_vertices[:, 1] < 0]
    lower_verts = lower_verts[lower_verts[:, 0] >= ul_vertex[0]]
    lower_verts = lower_verts[lower_verts[:, 0] <= ur_vertex[0]]
    lower_verts = lower_verts[lower_verts[:, 0].argsort()]

    ul_verts = np.array([ul_vertex, upper_verts[0]])
    ur_verts = np.array([ur_vertex, upper_verts[-1]])[::-1]
    dl_verts = np.array([dl_vertex, lower_verts[0]])
    dr_verts = np.array([dr_vertex, lower_verts[-1]])[::-1]

    u_pipe = compose_pipe(upper_verts, close_loop=False, smooth_vertices=False)
    l_pipe = compose_pipe(lower_verts, close_loop=False, smooth_vertices=False)
    ul_pipe = compose_pipe(ul_verts,
                           close_loop=False,
                           smooth_vertices=False,
                           add_fillets=False)
    ur_pipe = compose_pipe(ur_verts,
                           close_loop=False,
                           smooth_vertices=False,
                           add_fillets=False)
    dl_pipe = compose_pipe(dl_verts,
                           close_loop=False,
                           smooth_vertices=False,
                           add_fillets=False)
    dr_pipe = compose_pipe(dr_verts,
                           close_loop=False,
                           smooth_vertices=False,
                           add_fillets=False)

    ul_sphere = make_sphere(upper_verts[0], RADIUS)
    ur_sphere = make_sphere(upper_verts[-1], RADIUS)
    dl_sphere = make_sphere(lower_verts[0], RADIUS)
    dr_sphere = make_sphere(lower_verts[-1], RADIUS)

    from OCC.Core.TopoDS import TopoDS_Compound
    from OCC.Core.BRep import BRep_Builder

    aCompound = TopoDS_Compound()
    aBuilder = BRep_Builder()
    aBuilder.MakeCompound(aCompound)
    aBuilder.Add(aCompound, pipe)
    aBuilder.Add(aCompound, u_pipe)
    aBuilder.Add(aCompound, l_pipe)
    aBuilder.Add(aCompound, ul_pipe)
    aBuilder.Add(aCompound, ur_pipe)
    aBuilder.Add(aCompound, dl_pipe)
    aBuilder.Add(aCompound, dr_pipe)
    aBuilder.Add(aCompound, ul_sphere)
    aBuilder.Add(aCompound, ur_sphere)
    aBuilder.Add(aCompound, dl_sphere)
    aBuilder.Add(aCompound, dr_sphere)

    from OCC.Extend.DataExchange import write_stl_file
    output_file = '.'.join(input_file.split('.')[:-1]) + '_fitter'
    output_stl = output_file + '.stl'
    output_obj = output_file + '_bracket.obj'

    write_stl_file(aCompound, output_stl)
    print("Written to", output_stl)

    output_mesh = trimesh.load_mesh(output_stl)
    output_mesh = output_mesh.simplify_quadratic_decimation(
        len(output_mesh.faces) // 25)
    trimesh.repair.fix_inversion(output_mesh)

    def create_trans_mat(x, y, z):
        r = R.from_euler('xyz', [[x, y, z]], degrees=True)
        trans_mat = r.as_matrix()

        full_trans_mat = np.eye(4)
        full_trans_mat[:3, :3] = trans_mat
        return full_trans_mat

    full_trans_mat = create_trans_mat(0, 0, -90)
    output_mesh.apply_transform(full_trans_mat)

    # add bracket
    brac_mesh = trimesh.load_mesh('3d_files/bracket_insert_bent.STL')
    brac_mesh = brac_mesh.simplify_quadratic_decimation(
        len(brac_mesh.faces) // 2)
    print(len(brac_mesh.faces))
    trimesh.repair.fix_inversion(brac_mesh)
    full_trans_mat = create_trans_mat(-90, 10, 180)
    brac_mesh.apply_transform(full_trans_mat)
    brac_mesh.vertices = brac_mesh.vertices * 0.86 + np.array([35, 10, 35])
    brac_fitter = trimesh.util.concatenate([brac_mesh, output_mesh])
    brac_fitter.apply_transform(np.diag(np.array([-1, 1, 1, 1])))

    brac_fitter.export(output_obj)
    print("Written to", output_obj)

    return output_obj
コード例 #30
0
ファイル: blade.py プロジェクト: o4fr/BladeX
    def generate_stl(self, min_length=None, max_length=None, outfile_stl=None):
        """
        Generate and export the .STL surface mesh for the blade as a whole,
        including the upper face, lower face and tip. The method utilizes
        modules from OCC SMESH which is standalone mesh framework based on
        SALOME mesher project. Please refer to https://github.com/tpaviot
        and http://docs.salome-platform.org/7/gui/SMESH/index.html for
        further details.

        This method requires PythonOCC and SMESH to be installed.

        :param double min_length: smallest distance between two nodes. Default
            value is None
        :param double max_length: largest distance between two nodes. Default
            value is None
        :param string outfile_stl: if string is passed then the method exports
            the generated 2D surface mesh into .stl file holding the name
            <outfile_stl>.stl. Default value is None

        We note that since the current implementation performs triangulation
        based on a topological compound that combines the blade 3 generated
        shapes without "fusion", it may happen that the generated triangulation
        of the upper and lower blade faces do not share the same exact nodes
        on the joint edge/wire resulting from the faces intersection. The
        current implementation can be enough for visualization purpose. However
        if the generated mesh is intended for computational analysis then a
        manual mesh healing is recommended by the user (e.g. see
        "Repair > Sewing" in SALOME GUI) for a proper mesh closure.
        """
        from OCC.Core.SMESH import SMESH_Gen
        from OCC.Core.StdMeshers import (StdMeshers_Arithmetic1D,
                                         StdMeshers_TrianglePreference,
                                         StdMeshers_Regular_1D,
                                         StdMeshers_MEFISTO_2D)
        from OCC.Core.BRep import BRep_Builder
        from OCC.Core.TopoDS import TopoDS_Shape, TopoDS_Compound

        if min_length <= 0 or max_length <= 0:
            raise ValueError('min_length and max_length must be positive.')
        if min_length >= max_length:
            raise ValueError('min_length can not be greater than max_length')

        # First we check that blade shapes are generated, otherwise we generate
        # them. After that we combine the generated_upper_face,
        # generated_lower_face, and generated_tip into a topological compound
        # that we use to compute the surface mesh
        if (self.generated_upper_face is None) or not isinstance(
                self.generated_upper_face, TopoDS_Shape):
            # Upper face is generated with a maximal U degree = 1
            self._generate_upper_face(maxDeg=1)
        if (self.generated_lower_face is None) or not isinstance(
                self.generated_lower_face, TopoDS_Shape):
            # Upper face is generated with a maximal U degree = 1
            self._generate_lower_face(maxDeg=1)
        if (self.generated_tip is None) or not isinstance(
                self.generated_tip, TopoDS_Shape):
            # Upper face is generated with a maximal U degree = 1
            self._generate_tip(maxDeg=1)

        # Now we regroup all the shapes into a TopoDS_Compound
        aCompound = TopoDS_Compound()
        aBuilder = BRep_Builder()
        aBuilder.MakeCompound(aCompound)
        # Add shapes
        aBuilder.Add(aCompound, self.generated_upper_face)
        aBuilder.Add(aCompound, self.generated_lower_face)
        aBuilder.Add(aCompound, self.generated_tip)

        # In the following we build the surface mesh according to the given
        # hypotheses
        aMeshGen = SMESH_Gen()
        aMesh = aMeshGen.CreateMesh(0, True)
        # Adding 1D hypothesis and algorithms
        # Wire discretization. Nodes are distributed based on Arithmetic1D
        # hypothesis which allows to split edges into segments with a length
        # that changes in arithmetic progression (Lk = Lk-1 + d) beginning
        # from a given min length and up to a given max length. More about
        # 1D hypotheses can be viewed through:
        # http://docs.salome-platform.org/7/gui/SMESH/a1d_meshing_hypo_page.html
        an1DHypothesis = StdMeshers_Arithmetic1D(0, 0, aMeshGen)
        # Smallest distance between 2 points
        an1DHypothesis.SetLength(min_length, False)
        # Longest distance between 2 points
        an1DHypothesis.SetLength(max_length, True)
        # Regular Interpolation
        an1DAlgo = StdMeshers_Regular_1D(1, 0, aMeshGen)
        # Adding 2D hypothesis and algorithms
        # 2D surface mesh -- Triangulations
        a2dHypothseis = StdMeshers_TrianglePreference(2, 0, aMeshGen)
        a2dAlgo = StdMeshers_MEFISTO_2D(3, 0, aMeshGen)

        #Calculate mesh for the topological compound containing the 3 shapes
        aMesh.ShapeToMesh(aCompound)

        #Assign hyptothesis to mesh
        aMesh.AddHypothesis(aCompound, 0)
        aMesh.AddHypothesis(aCompound, 1)
        aMesh.AddHypothesis(aCompound, 2)
        aMesh.AddHypothesis(aCompound, 3)

        if outfile_stl is not None:
            if not isinstance(outfile_stl, str):
                raise ValueError('outfile_stl must be a valid string.')

            #Compute the data
            aMeshGen.Compute(aMesh, aMesh.GetShapeToMesh())
            # Export STL
            aMesh.ExportSTL(outfile_stl + '.stl', False)