def is_anticlockwise(pyptlist, pyref_vec): total = [0, 0, 0] npts = len(pyptlist) for i in range(npts): pt1 = pyptlist[i] if i == npts - 1: pt2 = pyptlist[0] else: pt2 = pyptlist[i + 1] #cross the two pts vec1 = gp_Vec(pt1[0], pt1[1], pt1[2]) vec2 = gp_Vec(pt2[0], pt2[1], pt2[2]) prod = vec1.Crossed(vec2) total[0] += prod.X() total[1] += prod.Y() total[2] += prod.Z() gp_total = gp_Vec(total[0], total[1], total[2]) gp_ref_vec = gp_Vec(pyref_vec[0], pyref_vec[1], pyref_vec[2]) result = gp_total.Dot(gp_ref_vec) if result < 0: return False else: return True
def display_vector(self, origin, direction): r"""Display a vector starting at origin and going in direction Parameters ---------- origin : tuple(float) The origin coordinates (x, y, z) of the vector to display direction : tuple(float) The direction coordinates (x, y, z) of the vector to display """ xo, yo, zo = origin xd, yd, zd = direction end = (xo + xd, yo + xd, zo + zd) xe, ye, ze = end # self.glarea.d3d.DisplayVector(gp_Vec(xd, yd, zd), gp_Pnt(xo, yo, zo)) presentation = Prs3d_Presentation(self.glarea.occ_context.MainPrsMgr(). GetObject().StructureManager()) arrow = Prs3d_Arrow() arrow.Draw(presentation.GetHandle(), gp_Pnt(xe, ye, ze), gp_Dir(gp_Vec(xd, yd, zd)), _math.radians(20), gp_Vec(xd, yd, zd).Magnitude() / 4.) presentation.Display() e1 = BRepBuilderAPI_MakeEdge(gp_Pnt(xo, yo, zo), gp_Pnt(xe, ye, ze)).\ Edge() self.display(e1, line_width=4)
def get_boundingbox(shape, tol=1e-6, as_vec=False): """ return the bounding box of the TopoDS_Shape `shape` Parameters ---------- shape : TopoDS_Shape or a subclass such as TopoDS_Face the shape to compute the bounding box from tol: float tolerance of the computed boundingbox as_vec : bool wether to return the lower and upper point of the bounding box as gp_Vec instances Returns ------- if `as_vec` is True, return a tuple of gp_Vec instances for the lower and another for the upper X,Y,Z values representing the bounding box if `as_vec` is False, return a tuple of lower and then upper X,Y,Z values representing the bounding box """ bbox = Bnd_Box() bbox.SetGap(tol) brepbndlib_Add(shape, bbox) xmin, ymin, zmin, xmax, ymax, zmax = bbox.Get() if as_vec is False: return xmin, ymin, zmin, xmax, ymax, zmax else: return gp_Vec(xmin, ymin, zmin), gp_Vec(xmax, ymax, zmax)
def angle_bw_2_vecs_w_ref(pyvec1, pyvec2, ref_pyvec): """ This function measures the angle between two vectors regards to a reference vector. The reference vector must be perpendicular to both the vectors. The angle is measured in counter-clockwise direction. Parameters ---------- pyvec1 : tuple of floats The first vector to be measured. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) pyvec2 : tuple of floats The second vector to be measured. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) ref_pyvec : tuple of floats The reference vector must be perpendicular to pyvec1 and pyvec2. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) Returns ------- angle : float The measured angle between pyvec1 and pyvec2 regards to ref_pyvec, the angle is measured in counter-clockwise direction. """ vec1 = gp_Vec(pyvec1[0], pyvec1[1], pyvec1[2]) vec2 = gp_Vec(pyvec2[0], pyvec2[1], pyvec2[2]) ref_vec = gp_Vec(ref_pyvec[0], ref_pyvec[1], ref_pyvec[2]) radangle = vec1.AngleWithRef(vec2, ref_vec) angle = radangle * (180.0 / math.pi) if angle < 0: angle = 360 + angle #the angle is measured in counter-clockwise direction return angle
def angle_bw_2_vecs_w_ref(pyvec1, pyvec2, ref_pyvec): """ This function measures the angle between two vectors regards to a reference vector. The reference vector must be perpendicular to both the vectors. The angle is measured in counter-clockwise direction. Parameters ---------- pyvec1 : tuple of floats The first vector to be measured. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) pyvec2 : tuple of floats The second vector to be measured. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) ref_pyvec : tuple of floats The reference vector must be perpendicular to pyvec1 and pyvec2. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) Returns ------- angle : float The measured angle between pyvec1 and pyvec2 regards to ref_pyvec, the angle is measured in counter-clockwise direction. """ vec1 = gp_Vec(pyvec1[0], pyvec1[1], pyvec1[2]) vec2 = gp_Vec(pyvec2[0], pyvec2[1], pyvec2[2]) ref_vec = gp_Vec(ref_pyvec[0], ref_pyvec[1], ref_pyvec[2]) radangle = vec1.AngleWithRef(vec2, ref_vec) angle = radangle * (180.0/math.pi) if angle <0: angle = 360+angle #the angle is measured in counter-clockwise direction return angle
def test_gp_Quaternion(self): ''' Test Interpolate method of qp_QuaternionSLerp. This method takes a by ref parameter q. ''' vX = gp_Vec(12, 0, 0) vY = gp_Vec(0, 12, 0) v45 = (gp_Vec(1, 1, 1).Normalized() * 12) q = gp_Quaternion() q1 = gp_Quaternion(vX, vX) q2 = gp_Quaternion(vX, vY) interp = gp_QuaternionSLerp(q1, q2) interp.Init(q1, q2) for i in range(10): i__ = i / 10. interp.Interpolate(i__, q) if i == 0: self.assertEqual(q.X(), 0.) self.assertEqual(q.Y(), 0.) self.assertEqual(q.Z(), 0.) self.assertEqual(q.W(), 1.) else: self.assertEqual(q.X(), 0.) self.assertEqual(q.Y(), 0.) assert q.Z() > 0. assert q.W() < 1.
def normalEdgesAlongEdge(edge, length , interval): "compute an edge having length at the specified parameter on the supplied curve:" edgeList = []; ew = Wrappers.Edge(edge); zDir = gp.gp().DZ(); zVec = gp.gp_Vec(zDir); curve = ew.curve; pStart = ew.firstParameter; pEnd = ew.lastParameter; for p in Wrappers.frange6(pStart,pEnd,interval): tangent = gp.gp_Vec(); tanpoint = gp.gp_Pnt(); curve.D1(p,tanpoint,tangent ); axis = gp.gp_Ax1(tanpoint, gp.gp_Dir(tangent.Crossed(zVec) ) ); line = Geom.Geom_Line(axis ); e = BRepBuilderAPI.BRepBuilderAPI_MakeEdge(line.GetHandle(),0, length).Edge(); if e: edgeList.append(e); return edgeList;
def rotate(event=None): display.EraseAll() origin = gp_Vec(0, 0, 0) origin_pt = as_pnt(origin) vX = gp_Vec(12, 0, 0) vY = gp_Vec(0, 12, 0) vZ = gp_Vec(0, 0, 12) v45 = (gp_Vec(1, 1, 1).Normalized() * 12) q1 = gp_Quaternion(vX, vY) p1 = as_pnt(origin + vX) p2 = as_pnt(origin + vY) p3 = as_pnt(origin + (q1 * vY)) p4 = as_pnt(origin + (q1 * v45)) # RED e1 = make_edge(origin_pt, p1) e2 = make_edge(origin_pt, p2) e3 = make_edge(origin_pt, as_pnt(v45)) # GREEN -> transformed e4 = make_edge(origin_pt, p3) e5 = make_edge(origin_pt, p4) display.DisplayShape([e1, e2, e3]) display.DisplayColoredShape([e4, e5], 'GREEN') #display.DisplayMessage(p1, 'e1') #display.DisplayMessage(p2, 'e2') #display.DisplayMessage(v45.as_pnt(), 'e3') #display.DisplayMessage(p3, 'q1*vY') #display.DisplayMessage(p4, 'q1*v45') display.DisplayVector((q1 * vY).Normalized(), as_pnt(origin + q1 * vY / 2.)) display.DisplayVector((q1 * v45).Normalized(), as_pnt(origin + q1 * v45 / 2.)) display.FitAll()
def brep_feat_rib(event=None): mkw = BRepBuilderAPI_MakeWire() mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(0., 0., 0.), gp_Pnt(200., 0., 0.)).Edge()) mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(200., 0., 0.), gp_Pnt(200., 0., 50.)).Edge()) mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(200., 0., 50.), gp_Pnt(50., 0., 50.)).Edge()) mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(50., 0., 50.), gp_Pnt(50., 0., 200.)).Edge()) mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(50., 0., 200.), gp_Pnt(0., 0., 200.)).Edge()) mkw.Add(BRepBuilderAPI_MakeEdge(gp_Pnt(0., 0., 200.), gp_Pnt(0., 0., 0.)).Edge()) S = BRepPrimAPI_MakePrism(BRepBuilderAPI_MakeFace(mkw.Wire()).Face(), gp_Vec(gp_Pnt(0., 0., 0.), gp_Pnt(0., 100., 0.))) display.EraseAll() # display.DisplayShape(S.Shape()) W = BRepBuilderAPI_MakeWire(BRepBuilderAPI_MakeEdge(gp_Pnt(50., 45., 100.), gp_Pnt(100., 45., 50.)).Edge()) aplane = Geom_Plane(0., 1., 0., -45.) aform = BRepFeat_MakeLinearForm(S.Shape(), W.Wire(), aplane.GetHandle(), gp_Vec(0., 10., 0.), gp_Vec(0., 0., 0.), 1, True) aform.Perform() display.DisplayShape(aform.Shape()) display.FitAll()
def axs_line(axs): p0, dx, dy = axs.Location(), axs.XDirection(), axs.YDirection() px = gp_Pnt((gp_Vec(p0.XYZ()) + dir_to_vec(dx) * 50).XYZ()) py = gp_Pnt((gp_Vec(p0.XYZ()) + dir_to_vec(dy) * 100).XYZ()) lx = make_line(p0, px) ly = make_line(p0, py) return lx, ly
def get_shortest_vec(pntList_add, pntList_base): minVec = gp_Vec(pntList_add[0], pntList_base[0]) for pnt_base in pntList_base: for pnt_add in pntList_add: newVec = gp_Vec(pnt_add, pnt_base) if newVec.Magnitude() < minVec.Magnitude(): minVec = newVec return minVec
def midpoint(pnt1: gp_Pnt, pnt2: gp_Pnt) -> gp_Pnt: """ computes the point that lies in the middle between pntA and pntB @param pnt1: gp_Pnt @param pnt2: gp_Pnt """ vec1 = gp_Vec(pnt1.XYZ()) vec2 = gp_Vec(pnt2.XYZ()) veccie = (vec1 + vec2) / 2. return gp_Pnt(veccie.XYZ())
def axisAndAngle(vec1, alpha1, vec2, alpha2, front=False): q1 = gp_Quaternion(gp_Vec(*vec1), alpha1) if front: q = q1 else: q2 = gp_Quaternion(gp_Vec(*vec2), alpha2) q = q2 * q1 axis = gp_Vec(0.0, 0.0, 0.0) angle = gp_Quaternion.GetVectorAndAngle(q, axis) return (axis, angle)
def set_obj(meta, xyz, dx, dy, pln_set=[-200, 200, -200, 200], indx=1): vx = gp_Vec(*dx).Normalized() vy = gp_Vec(*dy).Normalized() vz = vx.Crossed(vy) meta["pnt"] = gp_Pnt(*xyz) meta["xyz"] = [vx, vy, vz] meta["pln"] = make_plane(meta["pnt"], meta["xyz"][2], *pln_set) meta["pts"] = shape_to_pts(meta["pln"]) meta["frm"] = set_wire(meta["pts"]) meta["idx"] = indx
def midpoint(pntA, pntB): ''' computes the point that lies in the middle between pntA and pntB @param pntA: gp_Pnt @param pntB: gp_Pnt ''' vec1 = gp_Vec(pntA.XYZ()) vec2 = gp_Vec(pntB.XYZ()) veccie = (vec1+vec2)/2. return gp_Pnt(veccie.XYZ())
def midpoint(pntA, pntB): ''' computes the point that lies in the middle between pntA and pntB @param pntA: gp_Pnt @param pntB: gp_Pnt ''' vec1 = gp_Vec(pntA.XYZ()) vec2 = gp_Vec(pntB.XYZ()) veccie = (vec1 + vec2) / 2. return gp_Pnt(veccie.XYZ())
def reflect(p0, v0, ax): ray = gp_Lin(p0, vec_to_dir(v0)) intersection = IntAna_IntConicQuad(ray, gp_Pln(ax), precision_Angular(), precision_Confusion()) p1 = intersection.Point(1) vx, vy = gp_Vec(1, 0, 0), gp_Vec(0, 1, 0) handle = Geom_Plane(ax) handle.D1(0.5, 0.5, gp_Pnt(), vx, vy) vz = vx.Crossed(vy) v1 = v0.Mirrored(gp_Ax2(p1, vec_to_dir(vz))) return p1, v1
def second_derivative(h_surf, u=0, v=0): p1 = gp_Pnt() pu, pv = gp_Vec(), gp_Vec() puu, pvv = gp_Vec(), gp_Vec() puv = gp_Vec() prop = GeomLProp_SLProps(h_surf, u, v, 1, 1) GeomLProp_SurfaceTool.D2(h_surf, u, v, p1, pu, pv, puu, pvv, puv) e0 = pu.Crossed(pv) pu.Normalize() pv.Normalize() e0.Normalize() puu.Normalize() pvv.Normalize() puv.Normalize() print(p1) print("pu", pu) print("pv", pv) print("e0", e0) print("puu", puu) print("pvv", pvv) print("puv", puv) first_form = np.array([[pu.Dot(pu), pu.Dot(pv)], [pv.Dot(pu), pv.Dot(pv)]]) secnd_form = np.array([[e0.Dot(puu), e0.Dot(puv)], [e0.Dot(puv), e0.Dot(pvv)]]) print(first_form) print(secnd_form) print(prop.GaussianCurvature()) print(prop.MeanCurvature()) d1, d2 = gp_Dir(), gp_Dir() prop.CurvatureDirections(d1, d2) a1 = gp_Ax3() v1 = dir_to_vec(d1) v2 = dir_to_vec(d2) if pu.IsParallel(v1, 1 / 1000): c1 = prop.MaxCurvature() c2 = prop.MinCurvature() print(v1.Dot(pu), v1.Dot(pv)) print(v2.Dot(pu), v2.Dot(pv)) else: c1 = prop.MinCurvature() c2 = prop.MaxCurvature() print(v1.Dot(pu), v1.Dot(pv)) print(v2.Dot(pu), v2.Dot(pv)) print(c1, 1 / c1) print(c2, 1 / c2) px = np.linspace(-1, 1, 100) * 100 p1_y = px**2 / c1 p2_y = px**2 / c1 curv1 = curv_spl(px, p1_y) curv2 = curv_spl(px, p2_y)
def get_closest_parallel_planePair(solid_add, solid_base=None, init_min_dist=1000.0, xyplane_z_inMM=1215.0): """ Arguments: solid_add {TopoDS_Solid} -- The solid going to be added Keyword Arguments: solid_base {TopoDS_Solid} -- By default, solid_base will be xy-plane (default: {None}) init_min_dist {float} -- [description] (default: {10.0}) Returns: {dict} -- keyValues: miniDist, topoPair, geomPair, mvVec """ min_dist = init_min_dist ang_list = find_closest_normal_pair(solid_add, solid_base) if solid_base is None: solid_base = gen_boxSolidAsTable(height=xyplane_z_inMM) axisGrp1 = group_planes_by_axis(solid_base) axisGrp2 = group_planes_by_axis(solid_add) axisPair = ang_list['minAxisKeyPair'] for axKeyPair in axisPair: for topoPln1 in axisGrp1[axKeyPair[0]]: surf1 = BRepAdaptor_Surface(topoPln1, True) pln1 = surf1.Plane() # [ToDo] A better distance evaluation, how to select a correct point which is inside the wire or centerofmass of plane plnpnt1 = pln1.Location() for topoPln2 in axisGrp2[axKeyPair[1]]: surf2 = BRepAdaptor_Surface(topoPln2, True) pln2 = surf2.Plane() # rospy.logdebug('Distance:', pln2.Distance(plnpnt1)) dist = pln2.Distance(plnpnt1) if dist < min_dist: min_dist = dist minDistTopoPair = [topoPln1, topoPln2] minDistGeomPair = [pln1, pln2] p = gp_Pnt(0, 0, 0) p1 = ais_ProjectPointOnPlane(p, minDistGeomPair[0]) p2 = ais_ProjectPointOnPlane(p, minDistGeomPair[1]) # in order to remove small digits projPln = minDistGeomPair[0] mvVec = gp_Vec(p2, p1) projPlnNormal = gp_Vec(projPln.Axis().Direction()) mag = np.sign(mvVec.Dot(projPlnNormal)) * mvVec.Magnitude() mvVec = projPlnNormal.Normalized().Multiplied(mag) return { 'minDist': dist, 'topoPair': minDistTopoPair, 'geomPair': minDistGeomPair, 'mvVec': mvVec }
def surface_from_curves(): ''' @param display: ''' # First spline array = [] array.append(gp_Pnt(-4, 0, 2)) array.append(gp_Pnt(-7, 2, 2)) array.append(gp_Pnt(-6, 3, 1)) array.append(gp_Pnt(-4, 3, -1)) array.append(gp_Pnt(-3, 5, -2)) pt_list1 = point_list_to_TColgp_Array1OfPnt(array) SPL1 = GeomAPI_PointsToBSpline(pt_list1).Curve() SPL1_c = SPL1.GetObject() # Second spline a2 = [] a2.append(gp_Pnt(-4, 0, 2)) a2.append(gp_Pnt(-2, 2, 0)) a2.append(gp_Pnt(2, 3, -1)) a2.append(gp_Pnt(3, 7, -2)) a2.append(gp_Pnt(4, 9, -1)) pt_list2 = point_list_to_TColgp_Array1OfPnt(a2) SPL2 = GeomAPI_PointsToBSpline(pt_list2).Curve() SPL2_c = SPL2.GetObject() # Fill with StretchStyle aGeomFill1 = GeomFill_BSplineCurves(SPL1, SPL2, GeomFill_StretchStyle) SPL3 = Handle_Geom_BSplineCurve_DownCast(SPL1_c.Translated(gp_Vec(10, 0, 0))) SPL4 = Handle_Geom_BSplineCurve_DownCast(SPL2_c.Translated(gp_Vec(10, 0, 0))) # Fill with CoonsStyle aGeomFill2 = GeomFill_BSplineCurves(SPL3, SPL4, GeomFill_CoonsStyle) SPL5 = Handle_Geom_BSplineCurve_DownCast(SPL1_c.Translated(gp_Vec(20, 0, 0))) SPL6 = Handle_Geom_BSplineCurve_DownCast(SPL2_c.Translated(gp_Vec(20, 0, 0))) # Fill with CurvedStyle aGeomFill3 = GeomFill_BSplineCurves(SPL5, SPL6, GeomFill_CurvedStyle) aBSplineSurface1 = aGeomFill1.Surface() aBSplineSurface2 = aGeomFill2.Surface() aBSplineSurface3 = aGeomFill3.Surface() display.DisplayShape(make_face(aBSplineSurface1, 1e-6)) display.DisplayShape(make_face(aBSplineSurface2, 1e-6)) display.DisplayShape(make_face(aBSplineSurface3, 1e-6), update=True)
def make_plane(center=gp_Pnt(0, 0, 0), vec_normal=gp_Vec(0, 0, 1), extent_x_min=-100., extent_x_max=100., extent_y_min=-100., extent_y_max=100., depth=0.): if depth != 0: center = center.add_vec(gp_Vec(0, 0, depth)) PL = gp_Pln(center, vec_normal.as_dir()) face = make_face(PL, extent_x_min, extent_x_max, extent_y_min, extent_y_max) return face
def midpoint(pntA, pntB): """ computes the point that lies in the middle between pntA and pntB Parameters ---------- pntA, pntB : gp_Pnt Returns ------- gp_Pnt """ vec1 = gp_Vec(pntA.XYZ()) vec2 = gp_Vec(pntB.XYZ()) veccie = (vec1 + vec2) * 0.5 return gp_Pnt(veccie.XYZ())
def _triangle_is_valid(self, P1,P2,P3): V1 = gp_Vec(P1,P2) V2 = gp_Vec(P2,P3) V3 = gp_Vec(P3,P1) if V1.SquareMagnitude()>1e-10 and V2.SquareMagnitude()>1e-10 and V3.SquareMagnitude()>1e-10: V1.Cross(V2) if V1.SquareMagnitude()>1e-10: return True else: return False else: return False
def __init__(self, *args): if len(args) == 3: fV = gp_Vec(*args) elif len(args) == 2: fV = gp_Vec(*args, 0) elif len(args) == 1: if isinstance(args[0], Vector): fV = gp_Vec(args[0].wrapped.XYZ()) elif isinstance(args[0], (tuple, list)): arg = args[0] if len(arg) == 3: fV = gp_Vec(*arg) elif len(arg) == 2: fV = gp_Vec(*arg, 0) elif isinstance(args[0], (gp_Vec, gp_Pnt, gp_Dir)): fV = gp_Vec(args[0].XYZ()) elif isinstance(args[0], gp_XYZ): fV = gp_Vec(args[0]) else: raise TypeError("Expected three floats, OCC gp_, or 3-tuple") elif len(args) == 0: fV = gp_Vec(0, 0, 0) else: raise TypeError("Expected three floats, OCC gp_, or 3-tuple") self._wrapped = fV
def normal(geom, d0=0, d1=0): p, v0, v1 = gp_Pnt(), gp_Vec(), gp_Vec() geom.D1(d0, d1, p, v0, v1) v0.Normalize() v1.Normalize() #v0.Reverse() #v1.Reverse() v2 = v1.Crossed(v0) v2.Normalize() print("pnt", p.X(), p.Y(), p.Z()) print("v_x", v0.X(), v0.Y(), v0.Z()) print("v_y", v1.X(), v1.Y(), v1.Z()) print("v_z", v2.X(), v2.Y(), v2.Z()) return p, v0, v1, v2
def surface_from_curves(): ''' @param display: ''' # First spline array = [] array.append(gp_Pnt(-4, 0, 2)) array.append(gp_Pnt(-7, 2, 2)) array.append(gp_Pnt(-6, 3, 1)) array.append(gp_Pnt(-4, 3, -1)) array.append(gp_Pnt(-3, 5, -2)) pt_list1 = point_list_to_TColgp_Array1OfPnt(array) SPL1 = GeomAPI_PointsToBSpline(pt_list1).Curve() SPL1_c = SPL1.GetObject() # Second spline a2 = [] a2.append(gp_Pnt(-4, 0, 2)) a2.append(gp_Pnt(-2, 2, 0)) a2.append(gp_Pnt(2, 3, -1)) a2.append(gp_Pnt(3, 7, -2)) a2.append(gp_Pnt(4, 9, -1)) pt_list2 = point_list_to_TColgp_Array1OfPnt(a2) SPL2 = GeomAPI_PointsToBSpline(pt_list2).Curve() SPL2_c = SPL2.GetObject() # Fill with StretchStyle aGeomFill1 = GeomFill_BSplineCurves(SPL1, SPL2, GeomFill_StretchStyle) SPL3 = Handle_Geom_BSplineCurve_DownCast( SPL1_c.Translated(gp_Vec(10, 0, 0))) SPL4 = Handle_Geom_BSplineCurve_DownCast( SPL2_c.Translated(gp_Vec(10, 0, 0))) # Fill with CoonsStyle aGeomFill2 = GeomFill_BSplineCurves(SPL3, SPL4, GeomFill_CoonsStyle) SPL5 = Handle_Geom_BSplineCurve_DownCast( SPL1_c.Translated(gp_Vec(20, 0, 0))) SPL6 = Handle_Geom_BSplineCurve_DownCast( SPL2_c.Translated(gp_Vec(20, 0, 0))) # Fill with CurvedStyle aGeomFill3 = GeomFill_BSplineCurves(SPL5, SPL6, GeomFill_CurvedStyle) aBSplineSurface1 = aGeomFill1.Surface() aBSplineSurface2 = aGeomFill2.Surface() aBSplineSurface3 = aGeomFill3.Surface() display.DisplayShape(make_face(aBSplineSurface1, 1e-6)) display.DisplayShape(make_face(aBSplineSurface2, 1e-6)) display.DisplayShape(make_face(aBSplineSurface3, 1e-6), update=True)
def _triangle_is_valid(self, P1, P2, P3): V1 = gp_Vec(P1, P2) V2 = gp_Vec(P2, P3) V3 = gp_Vec(P3, P1) if V1.SquareMagnitude() > 1e-10 and V2.SquareMagnitude( ) > 1e-10 and V3.SquareMagnitude() > 1e-10: V1.Cross(V2) if V1.SquareMagnitude() > 1e-10: return True else: return False else: return False
def InitDoc(self): h_shape_tool = XCAFDoc.XCAFDoc_DocumentTool().ShapeTool(doc.Main()) l_Colors = XCAFDoc.XCAFDoc_DocumentTool().ColorTool(doc.Main()) shape_tool = h_shape_tool.GetObject() colors = l_Colors.GetObject() self.shape_tool = shape_tool top_label = shape_tool.NewShape( ) #this is the "root" label for the assembly self.top_label = top_label #Add some shapes box = BRepPrimAPI.BRepPrimAPI_MakeBox(10, 20, 30).Shape() box_label = shape_tool.AddShape(box, False) cyl = BRepPrimAPI.BRepPrimAPI_MakeCylinder(25, 50).Shape() cyl_label = shape_tool.AddShape(cyl, False) #Add components as references to our shape tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(100, 100, 100)) loc = TopLoc.TopLoc_Location(tr) box_comp1 = shape_tool.AddComponent(top_label, box_label, loc) tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(-100, -100, -100)) loc = TopLoc.TopLoc_Location(tr) box_comp2 = shape_tool.AddComponent(top_label, box_label, loc) tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(10, 10, 10)) loc = TopLoc.TopLoc_Location(tr) cyl_comp = shape_tool.AddComponent(top_label, cyl_label, loc) #Add some colors red = Quantity.Quantity_Color(Quantity.Quantity_NOC_RED) green = Quantity.Quantity_Color(Quantity.Quantity_NOC_GREEN) blue = Quantity.Quantity_Color(Quantity.Quantity_NOC_BLUE1) colors.SetColor(cyl_comp, red, XCAFDoc.XCAFDoc_ColorGen) colors.SetColor(box_label, blue, XCAFDoc.XCAFDoc_ColorGen) colors.SetColor(box_comp2, green, XCAFDoc.XCAFDoc_ColorGen) self.box_label = box_label self.cyl_label = cyl_label self.box_comp1 = box_comp1 self.box_comp2 = box_comp2 self.cyl_comp = cyl_comp
def _add_stuff_changed(self, old, new): for i in xrange(20): brep = BRepPrimAPI_MakeCylinder(random.random()*50, random.random()*50).Shape() trsf = gp_Trsf() trsf.SetTranslation(gp_Vec(random.random()*100, random.random()*100, random.random()*100)) brep.Move(TopLoc_Location(trsf)) self.shapes.append(brep)
def DisplayShape(self, shape, vertex_shader=None, fragment_shader=None, export_edges=False, color=(0.65, 0.65, 0.65), specular_color=(1, 1, 1), shininess=0.9, transparency=0., line_color=(0, 0., 0.), line_width=2., mesh_quality=1.): """ Adds a shape to the rendering buffer. This class computes the x3d file """ shape_hash = hash(shape) x3d_exporter = X3DExporter(shape, vertex_shader, fragment_shader, export_edges, color, specular_color, shininess, transparency, line_color, line_width, mesh_quality) x3d_exporter.compute() x3d_filename = os.path.join(self._path, "shp%s.x3d" % shape_hash) # the x3d filename is computed from the shape hash x3d_exporter.write_to_file(x3d_filename) # get shape translation and orientation trans = shape.Location().Transformation().TranslationPart().Coord() # vector v = gp_Vec() angle = shape.Location().Transformation().GetRotation().GetVectorAndAngle(v) ori = (v.X(), v.Y(), v.Z(), angle) # angles # fill the shape dictionnary with shape hash, translation and orientation self._x3d_shapes[shape_hash] = [trans, ori]
def display_str_at_pos(stri, col, line): brepstr = text_to_brep(stri, "Arial", Font_FA_Bold, 12., True) # translate the letter to the right brepstr_translated = translate_shp(brepstr, gp_Vec(col*8, -line*10, 0)) brepstr_extruded = make_extrusion(brepstr_translated, 2.5) display.DisplayColoredShape(brepstr_extruded, 'WHITE') display.Repaint()
def transform(self, T): # to gp_Pnt to obey cq transformation convention (in OCC vectors do not translate) pnt = self.toPnt() pnt_t = pnt.Transformed(T.wrapped) return Vector(gp_Vec(pnt_t.XYZ()))
def get_mesh_precision(shape, quality_factor): bbox = Bnd_Box() BRepBndLib_Add(shape, bbox) x_min,y_min,z_min,x_max,y_max,z_max = bbox.Get() diagonal_length = gp_Vec(gp_Pnt(x_min, y_min, z_min), gp_Pnt(x_max, y_max, z_max)).Magnitude() return (diagonal_length / 20.) / quality_factor
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)
def move_pt(orig_pypt, pydir2move, magnitude): """ This function moves a point. Parameters ---------- orig_pypt : tuple of floats The original point to be moved. A pypt is a tuple that documents the xyz coordinates of a pt e.g. (x,y,z) pydir2move : tuple of floats The direction to move the point. A pydir is a tuple that documents the xyz vector of a dir e.g. (x,y,z). magnitude : float The distance of the move. Returns ------- moved point : pypt The moved point. """ gp_orig_pt = gp_Pnt(orig_pypt[0], orig_pypt[1],orig_pypt[2]) gp_direction2move = gp_Vec(pydir2move[0], pydir2move[1], pydir2move[2]) gp_moved_pt = gp_orig_pt.Translated(gp_direction2move.Multiplied(magnitude)) moved_pt = (gp_moved_pt.X(), gp_moved_pt.Y(), gp_moved_pt.Z()) return moved_pt
def boolean_cut(base): # Create a cylinder cylinder_radius = 0.25 cylinder_height = 2.0 cylinder_origin = gp_Ax2(gp_Pnt(0.0, 0.0, -cylinder_height / 2.0), gp_Dir(0.0, 0.0, 1.0)) cylinder = BRepPrimAPI_MakeCylinder(cylinder_origin, cylinder_radius, cylinder_height) # Repeatedly move and subtract it from the input shape move = gp_Trsf() boolean_result = base clone_radius = 1.0 for clone in range(8): angle = clone * pi / 4.0 # Move the cylinder move.SetTranslation( gp_Vec(cos(angle) * clone_radius, sin(angle) * clone_radius, 0.0)) moved_cylinder = BRepBuilderAPI_Transform(cylinder.Shape(), move, True).Shape() # Subtract the moved cylinder from the drilled sphere boolean_result = BRepAlgoAPI_Cut(boolean_result, moved_cylinder).Shape() return boolean_result
def translate(self, vec): tr = gp_Trsf() tr.SetTranslation(gp_Vec(*vec)) loc = TopLoc_Location(tr) self.shape.Move(loc) self.__extract_curves() return self
def get_mesh_precision(shape, quality_factor): bbox = Bnd_Box() BRepBndLib_Add(shape, bbox) x_min, y_min, z_min, x_max, y_max, z_max = bbox.Get() diagonal_length = gp_Vec(gp_Pnt(x_min, y_min, z_min), gp_Pnt(x_max, y_max, z_max)).Magnitude() return (diagonal_length / 20.) / quality_factor
def display_str_at_pos(stri, col, line): brepstr = text_to_brep(stri, "Arial", Font_FA_Bold, 12., True) # translate the letter to the right brepstr_translated = translate_shp(brepstr, gp_Vec(col * 8, -line * 10, 0)) brepstr_extruded = make_extrusion(brepstr_translated, 2.5) display.DisplayColoredShape(brepstr_extruded, 'WHITE') display.Repaint()
def get_transform(self): d = self.declaration t = gp_Trsf() #: TODO: Order matters... how to configure it??? if d.mirror: try: p,v = d.mirror except ValueError: raise ValueError("You must specify a tuple containing a (point,direction)") t.SetMirror(gp_Ax1(gp_Pnt(*p), gp_Dir(*v))) if d.scale: try: p,s = d.scale except ValueError: raise ValueError("You must specify a tuple containing a (point,scale)") t.SetScale(gp_Pnt(*p),s) if d.translate: t.SetTranslation(gp_Vec(*d.translate)) if d.rotate: try: p,v,a = d.rotate except ValueError: raise ValueError("You must specify a tuple containing a (point,direction,angle)") t.SetRotation(gp_Ax1(gp_Pnt(*p), gp_Dir(*v)),a) return t
def prism(): # the bspline profile array = TColgp_Array1OfPnt(1, 5) array.SetValue(1, gp_Pnt(0, 0, 0)) array.SetValue(2, gp_Pnt(1, 2, 0)) array.SetValue(3, gp_Pnt(2, 3, 0)) array.SetValue(4, gp_Pnt(4, 3, 0)) array.SetValue(5, gp_Pnt(5, 5, 0)) bspline = GeomAPI_PointsToBSpline(array).Curve() profile = BRepBuilderAPI_MakeEdge(bspline).Edge() # the linear path starting_point = gp_Pnt(0., 0., 0.) end_point = gp_Pnt(0., 0., 6.) vec = gp_Vec(starting_point, end_point) path = BRepBuilderAPI_MakeEdge(starting_point, end_point).Edge() # extrusion prism = BRepPrimAPI_MakePrism(profile, vec).Shape() display.DisplayShape(profile, update=False) display.DisplayShape(starting_point, update=False) display.DisplayShape(end_point, update=False) display.DisplayShape(path, update=False) display.DisplayShape(prism, update=True)
def normal_vector_from_plane(plane, vec_length=1.): ''' returns a vector normal to the plane of length vec_length @param plane: ''' trns = gp_Vec(plane.Axis().Direction()) return trns.Normalized() * vec_length
def move_pt(orig_pypt, pydir2move, magnitude): """ This function moves a point. Parameters ---------- orig_pypt : tuple of floats The original point to be moved. A pypt is a tuple that documents the xyz coordinates of a pt e.g. (x,y,z) pydir2move : tuple of floats The direction to move the point. A pydir is a tuple that documents the xyz vector of a dir e.g. (x,y,z). magnitude : float The distance of the move. Returns ------- moved point : pypt The moved point. """ gp_orig_pt = gp_Pnt(orig_pypt[0], orig_pypt[1], orig_pypt[2]) gp_direction2move = gp_Vec(pydir2move[0], pydir2move[1], pydir2move[2]) gp_moved_pt = gp_orig_pt.Translated( gp_direction2move.Multiplied(magnitude)) moved_pt = (gp_moved_pt.X(), gp_moved_pt.Y(), gp_moved_pt.Z()) return moved_pt
def init_display(backend_str=None, size=(1000, 600)): QtCore, QtGui, QtWidgets, QtOpenGL = get_qt_modules() class MainWindow(QtWidgets.QMainWindow): def __init__(self, *args): QtWidgets.QMainWindow.__init__(self, *args) self.resize(size[0], size[1]) self.Viewer = qtViewer2(self) self.setCentralWidget(self.Viewer) self.centerOnScreen() def centerOnScreen(self): '''Centers the window on the screen.''' resolution = QtWidgets.QDesktopWidget().screenGeometry() self.move((resolution.width() / 2) - (self.frameSize().width() / 2), (resolution.height() / 2) - (self.frameSize().height() / 2)) # following couple of lines is a twek to enable ipython --gui='qt' app = QtWidgets.QApplication.instance() # checks if QApplication already exists if not app: # create QApplication if it doesnt exist app = QtWidgets.QApplication(sys.argv) win = MainWindow() win.show() win.Viewer.InitDriver() display = win.Viewer._display # background gradient display.set_bg_gradient_color(206, 215, 222, 128, 128, 128) # display black trihedron display.display_trihedron() def start_display(): win.raise_() # make the application float to the top app.exec_() win.display = display win.show() win.Viewer.init2() # create and add shapes box = BRepPrimAPI.BRepPrimAPI_MakeBox(60, 30, 10).Shape() cyl = BRepPrimAPI.BRepPrimAPI_MakeCylinder(25, 40).Shape() tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(0, 50, 0)) loc = TopLoc.TopLoc_Location(tr) moved_box = box.Moved(loc) # these shapes can be deleted by selecting them and pressing 'Del': win.Viewer.doc_ctrl.add(box) win.Viewer.doc_ctrl.add(cyl) # this shape cannot be deleted in this implementation: win.Viewer.doc_ctrl.add(moved_box) win.Viewer.repaint(Update=False) display.FitAll() return display, start_display
def __init__(self,fromPoint,toPoint): if fromPoint == None: fromPoint = gp.gp_Pnt(0,0,0); self.fromPoint = fromPoint; self.toPoint = toPoint; self.dir = gp.gp_Vec(fromPoint,toPoint);
def InitDoc(self): h_shape_tool = XCAFDoc.XCAFDoc_DocumentTool().ShapeTool(doc.Main()) l_Colors = XCAFDoc.XCAFDoc_DocumentTool().ColorTool(doc.Main()) shape_tool = h_shape_tool.GetObject() colors = l_Colors.GetObject() self.shape_tool = shape_tool top_label = shape_tool.NewShape() #this is the "root" label for the assembly self.top_label = top_label #Add some shapes box = BRepPrimAPI.BRepPrimAPI_MakeBox(10,20,30).Shape() box_label = shape_tool.AddShape(box, False) cyl = BRepPrimAPI.BRepPrimAPI_MakeCylinder(25,50).Shape() cyl_label = shape_tool.AddShape(cyl, False) #Add components as references to our shape tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(100,100,100)) loc = TopLoc.TopLoc_Location(tr) box_comp1 = shape_tool.AddComponent(top_label, box_label, loc) tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(200,200,200)) loc = TopLoc.TopLoc_Location(tr) box_comp2 = shape_tool.AddComponent(top_label, box_label, loc) tr = gp.gp_Trsf() tr.SetTranslation(gp.gp_Vec(150,200,100)) loc = TopLoc.TopLoc_Location(tr) cyl_comp = shape_tool.AddComponent(top_label, cyl_label, loc) #Add some colors red = Quantity.Quantity_Color(Quantity.Quantity_NOC_RED) green = Quantity.Quantity_Color(Quantity.Quantity_NOC_GREEN) colors.SetColor(cyl_comp, red, XCAFDoc.XCAFDoc_ColorGen) colors.SetColor(box_comp2, green, XCAFDoc.XCAFDoc_ColorGen) self.box_label = box_label self.cyl_label = cyl_label self.box_comp1 = box_comp1 self.box_comp2 = box_comp2 self.cyl_comp = cyl_comp
def translate(self, target): transform = gp.gp_Trsf() transform.SetTranslation(gp.gp_Vec(*target)) for i, needle in enumerate(self.shapes): needle_transform = BRepTransform(needle, transform, False) needle_transform.Build() self.shapes[i] = needle_transform.Shape()
def translate(self, target): transform = gp.gp_Trsf() transform.SetTranslation(gp.gp_Vec(*target)) # FIXME: this needs some explanation... should it be here? needle_transform = BRepTransform(self.needle, transform, False) needle_transform.Build() self.needle = needle_transform.Shape()
def fuse(event=None): display.EraseAll() box1 = BRepPrimAPI_MakeBox(2, 1, 1).Shape() box2 = BRepPrimAPI_MakeBox(2, 1, 1).Shape() box1 = translate_topods_from_vector(box1, gp_Vec(.5, .5, 0)) fuse = BRepAlgoAPI_Fuse(box1, box2).Shape() display.DisplayShape(fuse) display.FitAll()
def CutSect(Shape, SpanStation): """ Parameters ---------- Shape : TopoDS_Shape The Shape to find planar cut section (parallel to xz plane) SpanStation : scalar in range (0, 1) y-direction location at which to cut Shape Returns ------- Section : result of OCC.BRepAlgoAPI.BRepAlgoAPI_Section (TopoDS_Shape) The cut section of shape given a cut plane parallel to xz at input Spanstation. Chord : result of OCC.GC.GC_MakeSegment.Value (Geom_TrimmedCurve) The Chord line between x direction extremeties """ (Xmin, Ymin, Zmin, Xmax, Ymax, Zmax) = ObjectsExtents([Shape]) YStation = Ymin + (Ymax - Ymin) * SpanStation OriginX = Xmin - 1 OriginZ = Zmin - 1 P = gp_Pln(gp_Pnt(OriginX, YStation, OriginZ), gp_Dir(gp_Vec(0, 1, 0))) # Note: using 2*extents here as previous +1 trimmed plane too short CutPlaneSrf = make_face(P, 0, Zmax + 2, 0, Xmax +2) I = BRepAlgoAPI_Section(Shape, CutPlaneSrf) I.ComputePCurveOn1(True) I.Approximation(True) I.Build() Section = I.Shape() (Xmin, Ymin, Zmin, Xmax, Ymax, Zmax) = ObjectsExtents([Section]) # Currently assume only one edge exists in the intersection: exp = TopExp_Explorer(Section, TopAbs_EDGE) edge = topods_Edge(exp.Current()) # Find the apparent chord of the section (that is, the line connecting the # fore most and aftmost points on the curve DivPoints = Uniform_Points_on_Curve(edge, 200) Xs = np.array([pt.X() for pt in DivPoints]) min_idx = np.argmin(Xs) LeadingPoint = gp_Pnt(Xs[min_idx], DivPoints[min_idx].Y(), DivPoints[min_idx].Z()) max_idx = np.argmax(Xs) TrailingPoint = gp_Pnt(Xs[max_idx], DivPoints[max_idx].Y(), DivPoints[max_idx].Z()) HChord = GC_MakeSegment(TrailingPoint, LeadingPoint).Value() # Chord = HChord.GetObject() return Section, HChord
def ObjectsExtents(breps, tol=1e-6, as_vec=False): """Compute the extents in the X, Y and Z direction (in the current coordinate system) of the objects listed in the argument. Parameters ---------- breps : list of TopoDS_Shape The shapes to be added for bounding box calculation tol : float (default=1e-6) Tolerance for bounding box calculation as_vec : bool (default=False) If true, returns minimum and maximum points as tuple of gp_Vec Returns ------- xmin, ymin, zmin, xmax, ymax, zmax : scalar the min and max points of bbox (returned if as_vec=False) ( gp_Vec(xmin, ymin, zmin), gp_Vec(xmax, ymax, zmax) ) : tuple of gp_Vec the min and max points of bbox (returned in as_vec=True) Notes ----- Due to the underlying OCC.Bnd.Bnd_Box functions, the bounding box is calculated via triangulation of the shapes to avoid inclusion of the control points of NURBS curves in bounding box calculation """ bbox = OCC.Bnd.Bnd_Box() bbox.SetGap(tol) try: for shape in breps: brepbndlib_Add(shape, bbox, True) except TypeError: # Assume not iterable: brepbndlib_Add(breps, bbox, True) xmin, ymin, zmin, xmax, ymax, zmax = bbox.Get() if as_vec is False: return xmin, ymin, zmin, xmax, ymax, zmax else: return gp_Vec(xmin, ymin, zmin), gp_Vec(xmax, ymax, zmax)
def midpoint(pntA, pntB): """ computes the point that lies in the middle between pntA and pntB Parameters ---------- pntA, pntB : gp_Pnt Returns ------- gp_Pnt """ vec1 = gp_Vec(pntA.XYZ()) vec2 = gp_Vec(pntB.XYZ()) veccie = (vec1 + vec2) / 2. return gp_Pnt(veccie.XYZ())
def move(self, x = None, y = None, z = None, feed=None, cmd="G01"): if x == None: x = self.currentX if y == None: y = self.currentY if z == None: z = self.currentZ if feed == None: feed = self.currentFeed; #rapids reset naive move tracking if cmd != 'G01': self.lastMove = None; #if there is no move at all, return immediately if ( close(x , self.currentX ) and close(y ,self.currentY) and close(z , self.currentZ) ): log.debug( "No move required" ); return ""; #compute direction of the move, to filter out naive moves if self.currentX != None and self.currentY != None and self.currentZ != None and self.currentFeed != None: #ok we are doing a move, and we know what our current location and feed is #so we can compute a direction currentPoint = gp.gp_Pnt(self.currentX, self.currentY, self.currentZ); newPoint = gp.gp_Pnt(x,y,z); proposedMove = gp.gp_Vec(currentPoint,newPoint); if self.lastMove: #we have a last move. compare this one to see if they are the same direction if ( proposedMove.IsParallel(self.lastMove,TOLERANCE )) and ( self.currentFeed == feed) : #caught a naive move log.debug("Caught a naive move. Adjusting to remove the extra"); #TODO this approach only works with absolute coordinates #in incremental coordinates, we have to adjust the new vector to move the same #as all of the previous moves! self.removeLastNonCommentMove(); #self.comment("Removed Move"); #remove last non-comment move #store this one as the last move self.lastMove = proposedMove; #compare the direction of this move to the previous move. cmds=[] cmds.append(cmd); if not close(x, self.currentX): cmds.append( ("X" + self.numberFormat) % (x) ); self.currentX = x if not close(y , self.currentY): cmds.append( ("Y" + self.numberFormat) % (y) ); self.currentY = y if not close( z, self.currentZ): cmds.append( ("Z" + self.numberFormat) % (z) ); self.currentZ = z if feed != self.currentFeed: cmds.append(("F" + self.numberFormat) % (feed) ); self.currentFeed = feed; self.addCommand( " ".join(cmds));
def make_extrusion(face, length, vector=gp_Vec(0., 0., 1.)): ''' creates a extrusion from a face, along the vector vector. with a distance legnth. Note that the normal vector does not necessary be normalized. By default, the extrusion is along the z axis. ''' vector.Normalize() vector.Scale(length) return BRepPrimAPI_MakePrism(face, vector).Shape()
def is_anticlockwise(pyptlist, ref_pyvec): """ This function checks if the list of points are arranged anticlockwise in regards to the ref_pyvec. The ref_pyvec must be perpendicular to the points. Parameters ---------- pyptlist : a list of tuples The list of points to be checked. List of points to be converted. A pypt is a tuple that documents the xyz coordinates of a pt e.g. (x,y,z), thus a pyptlist is a list of tuples e.g. [(x1,y1,z1), (x2,y2,z2), ...] ref_pyvec : tuple of floats The reference vector must be perpendicular to the list of points. A pyvec is a tuple that documents the xyz direction of a vector e.g. (x,y,z) Returns ------- True or False : bool If True the list of points are arranged in anticlockwise manner, if False they are not. """ total = [0,0,0] npts = len(pyptlist) for i in range(npts): pt1 = pyptlist[i] if i == npts-1: pt2 = pyptlist[0] else: pt2 = pyptlist[i+1] #cross the two pts vec1 = gp_Vec(pt1[0],pt1[1],pt1[2]) vec2 = gp_Vec(pt2[0],pt2[1],pt2[2]) prod = vec1.Crossed(vec2) total[0] += prod.X() total[1] += prod.Y() total[2] += prod.Z() gp_total = gp_Vec(total[0],total[1],total[2]) gp_ref_vec = gp_Vec(ref_pyvec[0],ref_pyvec[1],ref_pyvec[2]) result = gp_total.Dot(gp_ref_vec) if result < 0: return False else: return True