コード例 #1
0
ファイル: shapes.py プロジェクト: zhukandrey/cadquery
 def makeCone(cls, radius1, radius2, height, pnt=Vector(0, 0, 0), dir=Vector(0, 0, 1), angleDegrees=360):
     """
     Make a cone with given radii and height
     By default pnt=Vector(0,0,0),
     dir=Vector(0,0,1) and angle=360'
     """
     return Shape.cast(FreeCADPart.makeCone(radius1, radius2, height, pnt.wrapped, dir.wrapped, angleDegrees))
コード例 #2
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def revolve(cls, outerWire, innerWires, angleDegrees, axisStart, axisEnd):
        """
        Attempt to revolve the list of wires into a solid in the provided direction

        :param outerWire: the outermost wire
        :param innerWires: a list of inner wires
        :param angleDegrees: the angle to revolve through.
        :type angleDegrees: float, anything less than 360 degrees will leave the shape open
        :param axisStart: the start point of the axis of rotation
        :type axisStart: tuple, a two tuple
        :param axisEnd: the end point of the axis of rotation
        :type axisEnd: tuple, a two tuple
        :return: a Solid object

        The wires must not intersect

        * all wires must be closed
        * there cannot be any intersecting or self-intersecting wires
        * wires must be listed from outside in
        * more than one levels of nesting is not supported reliably
        * the wire(s) that you're revolving cannot be centered

        This method will attempt to sort the wires, but there is much work remaining to make this method
        reliable.
        """
        face = Face.makeFromWires(outerWire, innerWires)

        v1 = Vector(axisStart)
        v2 = Vector(axisEnd)
        v2 = v2 - v1
        revol_builder = BRepPrimAPI_MakeRevol(face.wrapped,
                                              gp_Ax1(v1.toPnt(), v2.toDir()),
                                              angleDegrees * DEG2RAD, True)

        return cls(revol_builder.Shape())
コード例 #3
0
ファイル: shapes.py プロジェクト: zhukandrey/cadquery
 def makeCylinder(cls, radius, height, pnt=Vector(0, 0, 0), dir=Vector(0, 0, 1), angleDegrees=360):
     """
     makeCylinder(radius,height,[pnt,dir,angle]) --
     Make a cylinder with a given radius and height
     By default pnt=Vector(0,0,0),dir=Vector(0,0,1) and angle=360'
     """
     return Shape.cast(FreeCADPart.makeCylinder(radius, height, pnt.wrapped, dir.wrapped, angleDegrees))
コード例 #4
0
 def test_from_plane(self):
     plane = Plane(origin=(1,2,3), xDir=(0,1,0), normal=(1,0,0))
     cs = CoordSystem.from_plane(plane)
     self.assertEqual(cs.origin, Vector(1,2,3))
     self.assertEqual(cs.xDir, Vector(0,1,0))
     self.assertEqual(cs.yDir, Vector(0,0,1))
     self.assertEqual(cs.zDir, Vector(1,0,0))
コード例 #5
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def makePlane(cls, length, width, basePnt=(0, 0, 0), dir=(0, 0, 1)):
        basePnt = Vector(basePnt)
        dir = Vector(dir)

        pln_geom = gp_Pln(basePnt.toPnt(), dir.toDir())

        return cls(
            BRepBuilderAPI_MakeFace(pln_geom, -width * 0.5, width * 0.5,
                                    -length * 0.5, length * 0.5).Face())
コード例 #6
0
 def makeCircle(cls,
                radius,
                pnt=(0, 0, 0),
                dir=(0, 0, 1),
                angle1=360.0,
                angle2=360):
     center = Vector(pnt)
     normal = Vector(dir)
     return Edge(
         FreeCADPart.makeCircle(radius, center.wrapped, normal.wrapped,
                                angle1, angle2))
コード例 #7
0
    def __init__(self, *args):
        def sub(v1, v2):
            if isinstance(v1, Vertex):
                v1 = Vector(v1.X, v1.Y, v1.Z)
            if isinstance(v2, Vertex):
                v2 = Vector(v2.X, v2.Y, v2.Z)
            return (v1 - v2).normalized()

        if len(args) == 1 and isinstance(args[0], Shape):
            val = args[0]

            self.origin = val.Center()

            if val.geomType() in ["CIRCLE", "ELLIPSE"]:
                self.z_dir = val.normal()

                vertices = val.Vertices()
                if len(vertices) == 1:  # full circle or ellipse
                    # Use the vector defined by the circle's/ellipse's vertex and the origin as x direction
                    self.x_dir = sub(vertices[0], self.origin)
                else:  # arc
                    # Use the vector defined by start and end of the arc as x direction
                    self.x_dir = sub(vertices[1], vertices[0])

            elif isinstance(val, Wire):
                self.z_dir = val.normal()

                vertices = val.Vertices()
                if len(vertices) == 1:  # e.g. a single closed spline
                    # Use the vector defined by the vertex and the origin as x direction
                    self.x_dir = sub(vertices[0], self.origin)
                else:
                    # Use the vector defined by the first two vertices as x direction
                    self.x_dir = sub(vertices[1], vertices[0])

            elif isinstance(val, Face):
                self.z_dir = val.normalAt(val.Center())

                # x_dir will be derived from the local coord system of the underlying plane
                xd = val._geomAdaptor().Position().XDirection()
                self.x_dir = Vector(xd.X(), xd.Y(), xd.Z())

            else:
                raise ValueError("Needs a Face, Wire, Circle or an Ellipse")

        else:
            c = lambda v: v if isinstance(v, Vector) else Vector(*v)
            self.origin = Vector(0, 0, 0) if len(args) == 0 else c(args[0])
            self.x_dir = Vector(1, 0, 0) if len(args) <= 1 else c(args[1])
            self.z_dir = Vector(0, 0, 1) if len(args) <= 2 else c(args[2])

        self.y_dir = self.z_dir.cross(self.x_dir)
コード例 #8
0
ファイル: shapes.py プロジェクト: h0st1le/cadquery
 def makeBox(cls,
             length,
             width,
             height,
             pnt=Vector(0, 0, 0),
             dir=Vector(0, 0, 1)):
     """
         makeBox(length,width,height,[pnt,dir]) -- Make a box located\nin pnt with the d
         imensions (length,width,height)\nBy default pnt=Vector(0,0,0) and dir=Vector(0,0,1)'
     """
     return Shape.cast(
         FreeCADPart.makeBox(length, width, height, pnt.wrapped,
                             dir.wrapped))
コード例 #9
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
 def makeBox(cls,
             length,
             width,
             height,
             pnt=Vector(0, 0, 0),
             dir=Vector(0, 0, 1)):
     """
     makeBox(length,width,height,[pnt,dir]) -- Make a box located in pnt with the dimensions (length,width,height)
     By default pnt=Vector(0,0,0) and dir=Vector(0,0,1)'
     """
     return cls(
         BRepPrimAPI_MakeBox(gp_Ax2(pnt.toPnt(), dir.toDir()), length,
                             width, height).Shape())
コード例 #10
0
 def Center(self):
     # A Part.Shape object doesn't have the CenterOfMass function, but it's wrapped Solid(s) does
     if isinstance(self.wrapped, FreeCADPart.Shape):
         # If there are no Solids, we're probably dealing with a Face or something similar
         if len(self.Solids()) == 0:
             return Vector(self.wrapped.CenterOfMass)
         else:
             # TODO: compute the weighted average instead of using the first solid
             return Vector(self.Solids()[0].wrapped.CenterOfMass)
     elif isinstance(self.wrapped, FreeCADPart.Solid):
         return Vector(self.wrapped.CenterOfMass)
     else:
         raise ValueError("Cannot find the center of %s object type" % str(type(self.Solids()[0].wrapped)))
コード例 #11
0
ファイル: shapes.py プロジェクト: zhukandrey/cadquery
 def Center(self):
     # A Part.Shape object doesn't have the CenterOfMass function, but it's wrapped Solid(s) does
     if isinstance(self.wrapped, FreeCADPart.Shape):
         # If there are no Solids, we're probably dealing with a Face or something similar
         if len(self.Solids()) == 0:
             return Vector(self.wrapped.CenterOfMass)
         elif len(self.Solids()) == 1:
             return Vector(self.Solids()[0].wrapped.CenterOfMass)
         elif len(self.Solids()) > 1:
             return self.CombinedCenter(self.Solids())
     elif isinstance(self.wrapped, FreeCADPart.Solid):
         return Vector(self.wrapped.CenterOfMass)
     else:
         raise ValueError("Cannot find the center of %s object type" % str(type(self.Solids()[0].wrapped)))
コード例 #12
0
ファイル: shapes.py プロジェクト: zhukandrey/cadquery
 def CenterOfBoundBox(self, tolerance = 0.1):
     self.wrapped.tessellate(tolerance)
     if isinstance(self.wrapped, FreeCADPart.Shape):
         # If there are no Solids, we're probably dealing with a Face or something similar
         if len(self.Solids()) == 0:
             return Vector(self.wrapped.BoundBox.Center)
         elif len(self.Solids()) == 1:
             return Vector(self.Solids()[0].wrapped.BoundBox.Center)
         elif len(self.Solids()) > 1:
             return self.CombinedCenterOfBoundBox(self.Solids())
     elif isinstance(self.wrapped, FreeCADPart.Solid):
         return Vector(self.wrapped.BoundBox.Center)
     else:
         raise ValueError("Cannot find the center(BoundBox's) of %s object type" % str(type(self.Solids()[0].wrapped)))
コード例 #13
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
 def makeCylinder(cls,
                  radius,
                  height,
                  pnt=Vector(0, 0, 0),
                  dir=Vector(0, 0, 1),
                  angleDegrees=360):
     """
     makeCylinder(radius,height,[pnt,dir,angle]) --
     Make a cylinder with a given radius and height
     By default pnt=Vector(0,0,0),dir=Vector(0,0,1) and angle=360'
     """
     return cls(
         BRepPrimAPI_MakeCylinder(gp_Ax2(pnt.toPnt(), dir.toDir()), radius,
                                  height, angleDegrees * DEG2RAD).Shape())
コード例 #14
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def normalAt(self, locationVector=None):
        """
            Computes the normal vector at the desired location on the face.

            :returns: a  vector representing the direction
            :param locationVector: the location to compute the normal at. If none, the center of the face is used.
            :type locationVector: a vector that lies on the surface.
        """
        # get the geometry
        surface = self._geomAdaptor()

        if locationVector is None:
            u0, u1, v0, v1 = self._uvBounds()
            u = 0.5 * (u0 + u1)
            v = 0.5 * (v0 + v1)
        else:
            # project point on surface
            projector = GeomAPI_ProjectPointOnSurf(locationVector.toPnt(),
                                                   surface)

            u, v = projector.LowerDistanceParameters()

        p = gp_Pnt()
        vn = gp_Vec()
        BRepGProp_Face(self.wrapped).Normal(u, v, p, vn)

        return Vector(vn)
コード例 #15
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def tangentAt(self, locationVector=None):
        """
        Compute tangent vector at the specified location.
        :param locationVector: location to use. Use the center point if None
        :return: tangent vector
        """

        curve = self._geomAdaptor()

        if locationVector:
            raise NotImplementedError
        else:
            umin, umax = curve.FirstParameter(), curve.LastParameter()
            umid = 0.5 * (umin + umax)

        # TODO what are good parameters for those?
        curve_props = BRepLProp_CLProps(curve, 2, curve.Tolerance())
        curve_props.SetParameter(umid)

        if curve_props.IsTangentDefined():
            dir_handle = gp_Dir(
            )  # this is awkward due to C++ pass by ref in the API
            curve_props.Tangent(dir_handle)

            return Vector(dir_handle)
コード例 #16
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
 def makeSphere(cls,
                radius,
                pnt=Vector(0, 0, 0),
                dir=Vector(0, 0, 1),
                angleDegrees1=0,
                angleDegrees2=90,
                angleDegrees3=360):
     """
     Make a sphere with a given radius
     By default pnt=Vector(0,0,0), dir=Vector(0,0,1), angle1=0, angle2=90 and angle3=360
     """
     return cls(
         BRepPrimAPI_MakeSphere(gp_Ax2(pnt.toPnt(), dir.toDir()), radius,
                                angleDegrees1 * DEG2RAD,
                                angleDegrees2 * DEG2RAD,
                                angleDegrees3 * DEG2RAD).Shape())
コード例 #17
0
ファイル: shapes.py プロジェクト: h0st1le/cadquery
    def translate(self, vector):

        if type(vector) == tuple:
            vector = Vector(vector)
        tmp = self.wrapped.copy()
        tmp.translate(vector.wrapped)
        return Shape.cast(tmp)
コード例 #18
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
 def makeCone(cls,
              radius1,
              radius2,
              height,
              pnt=Vector(0, 0, 0),
              dir=Vector(0, 0, 1),
              angleDegrees=360):
     """
     Make a cone with given radii and height
     By default pnt=Vector(0,0,0),
     dir=Vector(0,0,1) and angle=360'
     """
     return cls(
         BRepPrimAPI_MakeCone(gp_Ax2(pnt.toPnt(),
                                     dir.toDir()), radius1, radius2, height,
                              angleDegrees * DEG2RAD).Shape())
コード例 #19
0
ファイル: shapes.py プロジェクト: h0st1le/cadquery
    def rotate(self, startVector, endVector, angleDegrees):
        """
        Rotates a shape around an axis
        :param startVector: start point of rotation axis  either a 3-tuple or a Vector
        :param endVector:  end point of rotation axis, either a 3-tuple or a Vector
        :param angleDegrees:  angle to rotate, in degrees
        :return: a copy of the shape, rotated
        """
        if type(startVector) == tuple:
            startVector = Vector(startVector)

        if type(endVector) == tuple:
            endVector = Vector(endVector)

        tmp = self.wrapped.copy()
        tmp.rotate(startVector.wrapped, endVector.wrapped, angleDegrees)
        return Shape.cast(tmp)
コード例 #20
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def makeHelix(cls,
                  pitch,
                  height,
                  radius,
                  center=Vector(0, 0, 0),
                  dir=Vector(0, 0, 1),
                  angle=360.0,
                  lefthand=False):
        """
        Make a helix with a given pitch, height and radius
        By default a cylindrical surface is used to create the helix. If
        the fourth parameter is set (the apex given in degree) a conical surface is used instead'
        """

        # 1. build underlying cylindrical/conical surface
        if angle == 360.:
            geom_surf = Geom_CylindricalSurface(
                gp_Ax3(center.toPnt(), dir.toDir()), radius)
        else:
            geom_surf = Geom_ConicalSurface(
                gp_Ax3(center.toPnt(), dir.toDir()),
                angle * DEG2RAD,  # TODO why no orientation?
                radius)

        # 2. construct an semgent in the u,v domain
        if lefthand:
            geom_line = Geom2d_Line(gp_Pnt2d(0.0, 0.0),
                                    gp_Dir2d(-2 * pi, pitch))
        else:
            geom_line = Geom2d_Line(gp_Pnt2d(0.0, 0.0),
                                    gp_Dir2d(2 * pi, pitch))

        # 3. put it together into a wire
        n_turns = height / pitch
        u_start = geom_line.Value(0.)
        u_stop = geom_line.Value(sqrt(n_turns * ((2 * pi)**2 + pitch**2)))
        geom_seg = GCE2d_MakeSegment(u_start, u_stop).Value()

        e = BRepBuilderAPI_MakeEdge(geom_seg, geom_surf.GetHandle()).Edge()

        # 4. Convert to wire and fix building 3d geom from 2d geom
        w = BRepBuilderAPI_MakeWire(e).Wire()
        breplib_BuildCurves3d(w)

        return cls(w)
コード例 #21
0
 def _getVector(self, pr):
     """
     Translate parsed vector string into a CQ Vector
     """
     if 'vector_dir' in pr:
         vec = pr.vector_dir
         return Vector(float(vec.x), float(vec.y), float(vec.z))
     else:
         return self.axes[pr.simple_dir]
コード例 #22
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def translate(self, vector):

        if type(vector) == tuple:
            vector = Vector(vector)

        T = gp_Trsf()
        T.SetTranslation(vector.wrapped)

        return self._apply_transform(T)
コード例 #23
0
ファイル: shapes.py プロジェクト: h0st1le/cadquery
    def startPoint(self):
        """

            :return: a vector representing the start poing of this edge

            Note, circles may have the start and end points the same
        """
        # work around freecad bug where valueAt is unreliable
        curve = self.wrapped.Curve
        return Vector(curve.value(self.wrapped.ParameterRange[0]))
コード例 #24
0
ファイル: shapes.py プロジェクト: h0st1le/cadquery
    def tangentAt(self, locationVector=None):
        """
            Compute tangent vector at the specified location.
        :param locationVector: location to use. Use the center point if None
        :return: tangent vector
        """
        if locationVector is None:
            locationVector = self.Center()

        p = self.wrapped.Curve.parameter(locationVector.wrapped)
        return Vector(self.wrapped.tangentAt(p))
コード例 #25
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def rotate(self, startVector, endVector, angleDegrees):
        """
        Rotates a shape around an axis
        :param startVector: start point of rotation axis  either a 3-tuple or a Vector
        :param endVector:  end point of rotation axis, either a 3-tuple or a Vector
        :param angleDegrees:  angle to rotate, in degrees
        :return: a copy of the shape, rotated
        """
        if type(startVector) == tuple:
            startVector = Vector(startVector)

        if type(endVector) == tuple:
            endVector = Vector(endVector)

        T = gp_Trsf()
        T.SetRotation(
            gp_Ax1(startVector.toPnt(), (endVector - startVector).toDir()),
            angleDegrees)

        return self._apply_transform(T)
コード例 #26
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def makeCircle(cls,
                   radius,
                   pnt=Vector(0, 0, 0),
                   dir=Vector(0, 0, 1),
                   angle1=360.0,
                   angle2=360):
        """

        """
        pnt = Vector(pnt)
        dir = Vector(dir)

        circle_gp = gp_Circ(gp_Ax2(pnt.toPnt(), dir.toDir()), radius)

        if angle1 == angle2:  # full circle case
            return cls(BRepBuilderAPI_MakeEdge(circle_gp).Edge())
        else:  # arc case
            circle_geom = GC_MakeArcOfCircle(circle_gp, angle1 * DEG2RAD,
                                             angle2 * DEG2RAD, True).Value()
            return cls(BRepBuilderAPI_MakeEdge(circle_geom).Edge())
コード例 #27
0
ファイル: shapes.py プロジェクト: zhukandrey/cadquery
    def mirror(self, mirrorPlane="XY", basePointVector=(0, 0, 0)):
        if mirrorPlane == "XY" or mirrorPlane== "YX":
            mirrorPlaneNormalVector = FreeCAD.Base.Vector(0, 0, 1)
        elif mirrorPlane == "XZ" or mirrorPlane == "ZX":
            mirrorPlaneNormalVector = FreeCAD.Base.Vector(0, 1, 0)
        elif mirrorPlane == "YZ" or mirrorPlane == "ZY":
            mirrorPlaneNormalVector = FreeCAD.Base.Vector(1, 0, 0)

        if type(basePointVector) == tuple:
            basePointVector = Vector(basePointVector)

        return Shape.cast(self.wrapped.mirror(basePointVector.wrapped, mirrorPlaneNormalVector))
コード例 #28
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def centerOfMass(obj):
        """
        Calculates the 'mass' of an object.
        """
        Properties = GProp_GProps()
        calc_function = shape_properties_LUT[obj.wrapped.ShapeType()]

        if calc_function:
            calc_function(obj.wrapped, Properties)
            return Vector(Properties.CentreOfMass())
        else:
            raise NotImplemented
コード例 #29
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
    def startPoint(self):
        """

            :return: a vector representing the start poing of this edge

            Note, circles may have the start and end points the same
        """

        curve = self._geomAdaptor()
        umin = curve.FirstParameter()

        return Vector(curve.Value(umin))
コード例 #30
0
ファイル: shapes.py プロジェクト: fragmuffin/cadquery
 def makeWedge(cls,
               xmin,
               ymin,
               zmin,
               z2min,
               x2min,
               xmax,
               ymax,
               zmax,
               z2max,
               x2max,
               pnt=Vector(0, 0, 0),
               dir=Vector(0, 0, 1)):
     """
     Make a wedge located in pnt
     By default pnt=Vector(0,0,0) and dir=Vector(0,0,1)
     """
     return cls(
         BRepPrimAPI_MakeWedge(gp_Ax2(pnt.toPnt(), dir.toDir()), xmin, ymin,
                               zmin, z2min, x2min, xmax, ymax, zmax, z2max,
                               x2max).Solid())