1a84f81acd745710407a1134c318e70b9fa56d82
[occt.git] / src / IntTools / IntTools_Context.cxx
1 // Created on: 2002-04-03
2 // Created by: Peter KURNEV
3 // Copyright (c) 2002-2012 OPEN CASCADE SAS
4 //
5 // The content of this file is subject to the Open CASCADE Technology Public
6 // License Version 6.5 (the "License"). You may not use the content of this file
7 // except in compliance with the License. Please obtain a copy of the License
8 // at http://www.opencascade.org and read it completely before using this file.
9 //
10 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
11 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
12 //
13 // The Original Code and all software distributed under the License is
14 // distributed on an "AS IS" basis, without warranty of any kind, and the
15 // Initial Developer hereby disclaims all such warranties, including without
16 // limitation, any warranties of merchantability, fitness for a particular
17 // purpose or non-infringement. Please see the License for the specific terms
18 // and conditions governing the rights and limitations under the License.
19
20
21
22 #include <IntTools_Context.ixx>
23
24 #include <Precision.hxx>
25
26 #include <Geom_Curve.hxx>
27 #include <Geom_BoundedCurve.hxx>
28 #include <GeomAPI_ProjectPointOnCurve.hxx>
29 #include <GeomAPI_ProjectPointOnSurf.hxx>
30 #include <GeomAdaptor_Curve.hxx>
31
32 #include <TopAbs_State.hxx>
33 #include <TopoDS.hxx>
34 #include <TopExp_Explorer.hxx>
35
36 #include <BRep_Tool.hxx>
37 #include <BRepAdaptor_Surface.hxx>
38
39 #include <IntTools_Tools.hxx>
40 #include <IntTools_FClass2d.hxx>
41 #include <Extrema_LocateExtPC.hxx>
42
43 #include <Geom2d_Curve.hxx>
44
45 //=======================================================================
46 //function : 
47 //purpose  : 
48 //=======================================================================
49 IntTools_Context::IntTools_Context()
50 {
51 }
52 //=======================================================================
53 //function : ~
54 //purpose  : 
55 //=======================================================================
56 IntTools_Context::~IntTools_Context()
57 {
58   Standard_Address anAdr;
59   Standard_Integer i, aNb;
60   //
61   IntTools_FClass2d* pFClass2d;
62   aNb=myFClass2dMap.Extent();
63   for (i=1; i<=aNb; ++i) {
64     anAdr=myFClass2dMap(i);
65     pFClass2d=(IntTools_FClass2d*)anAdr;
66     delete pFClass2d;
67   }
68   myFClass2dMap.Clear();
69   //
70   GeomAPI_ProjectPointOnSurf* pProjPS;
71   aNb=myProjPSMap.Extent();
72   for (i=1; i<=aNb; ++i) {
73     anAdr=myProjPSMap(i);
74     pProjPS=(GeomAPI_ProjectPointOnSurf*)anAdr;
75     delete pProjPS;
76   }
77   myProjPSMap.Clear();
78   //
79   GeomAPI_ProjectPointOnCurve* pProjPC;
80   aNb=myProjPCMap.Extent();
81   for (i=1; i<=aNb; ++i) {
82     anAdr=myProjPCMap(i);
83     pProjPC=(GeomAPI_ProjectPointOnCurve*)anAdr;
84     delete pProjPC;
85   }
86   myProjPCMap.Clear();
87   //
88   GeomAPI_ProjectPointOnCurve* pProjPT;
89   aNb=myProjPTMap.Extent();
90   for (i=1; i<=aNb; ++i) {
91     anAdr=myProjPTMap(i);
92     pProjPT=(GeomAPI_ProjectPointOnCurve*)anAdr;
93     delete pProjPT;
94   }
95   myProjPTMap.Clear();
96   //
97   BRepClass3d_SolidClassifier* pSC;
98   aNb=mySClassMap.Extent();
99   for (i=1; i<=aNb; ++i) {
100     anAdr=mySClassMap(i);
101     pSC=(BRepClass3d_SolidClassifier*)anAdr;
102     delete pSC;
103   }
104   mySClassMap.Clear();
105   //
106   IntTools_SurfaceRangeLocalizeData* pSData = NULL;
107   aNb = myProjSDataMap.Extent();
108   for (i=1; i<=aNb; ++i) {
109     anAdr=myProjSDataMap(i);
110     pSData = (IntTools_SurfaceRangeLocalizeData*)anAdr;
111     if(pSData)
112       delete pSData;
113     pSData = NULL;
114   }
115   myProjSDataMap.Clear();
116 }
117 //=======================================================================
118 //function : FClass2d
119 //purpose  : 
120 //=======================================================================
121   IntTools_FClass2d& IntTools_Context::FClass2d(const TopoDS_Face& aF)
122 {
123   Standard_Address anAdr;
124   IntTools_FClass2d* pFClass2d;
125   //
126   anAdr=myFClass2dMap.FindFromKey1(aF);
127   if (!anAdr) {
128     Standard_Real aTolF;
129     TopoDS_Face aFF=aF;
130     aFF.Orientation(TopAbs_FORWARD);
131     aTolF=BRep_Tool::Tolerance(aFF);
132     //
133     pFClass2d=new IntTools_FClass2d(aFF, aTolF);
134     //
135     anAdr=(Standard_Address)pFClass2d;
136     myFClass2dMap.Add(aFF, anAdr);
137   }
138
139   else {
140     Standard_Address *pAdr=(Standard_Address *)anAdr;
141     pFClass2d=(IntTools_FClass2d*)*pAdr;
142   }
143
144   return *pFClass2d;
145 }
146 //=======================================================================
147 //function : ProjPS
148 //purpose  : 
149 //=======================================================================
150   GeomAPI_ProjectPointOnSurf& IntTools_Context::ProjPS(const TopoDS_Face& aF)
151 {
152   Standard_Address anAdr;
153   GeomAPI_ProjectPointOnSurf* pProjPS;
154   //
155   anAdr=myProjPSMap.FindFromKey1(aF);
156   if (!anAdr) {
157     Standard_Real Umin, Usup, Vmin, Vsup;
158     Standard_Real anEpsT = Precision::PConfusion(); //1.e-12;
159     BRepAdaptor_Surface aBAS;
160     //
161     const Handle(Geom_Surface)& aS=BRep_Tool::Surface(aF);
162     aBAS.Initialize (aF, Standard_True);
163     //
164     Umin=aBAS.FirstUParameter();
165     Usup=aBAS.LastUParameter ();
166     Vmin=aBAS.FirstVParameter();
167     Vsup=aBAS.LastVParameter ();
168     //
169     pProjPS=new GeomAPI_ProjectPointOnSurf;
170     pProjPS->Init(aS ,Umin, Usup, Vmin, Vsup, anEpsT);
171     //
172     anAdr=(Standard_Address)pProjPS;
173     myProjPSMap.Add(aF, anAdr);
174   }
175   
176   else {
177     Standard_Address *pAdr=(Standard_Address *)anAdr;
178     pProjPS=(GeomAPI_ProjectPointOnSurf*)*pAdr;
179   }
180   return *pProjPS;
181 }
182 //=======================================================================
183 //function : ProjPC
184 //purpose  : 
185 //=======================================================================
186   GeomAPI_ProjectPointOnCurve& IntTools_Context::ProjPC(const TopoDS_Edge& aE)
187 {
188   Standard_Address anAdr;
189   GeomAPI_ProjectPointOnCurve* pProjPC;
190   //
191   anAdr=myProjPCMap.FindFromKey1(aE);
192   if (!anAdr) {
193     Standard_Real f, l;
194     //
195     Handle(Geom_Curve)aC3D=BRep_Tool::Curve (aE, f, l);
196     //
197     pProjPC=new GeomAPI_ProjectPointOnCurve;
198     pProjPC->Init(aC3D, f, l);
199     //
200     anAdr=(Standard_Address)pProjPC;
201     myProjPCMap.Add(aE, anAdr);
202   }
203   else {
204     Standard_Address *pAdr=(Standard_Address *)anAdr;
205     pProjPC=(GeomAPI_ProjectPointOnCurve*)*pAdr;
206   }
207   return *pProjPC;
208 }
209 //=======================================================================
210 //function : ProjPT
211 //purpose  : 
212 //=======================================================================
213   GeomAPI_ProjectPointOnCurve& IntTools_Context::ProjPT(const Handle(Geom_Curve)& aC3D)
214                                                         
215 {
216   Standard_Address anAdr;
217   GeomAPI_ProjectPointOnCurve* pProjPT;
218   //
219   anAdr=myProjPTMap.FindFromKey1(aC3D);
220   if (!anAdr) {
221     Standard_Real f, l;
222     f=aC3D->FirstParameter();
223     l=aC3D->LastParameter();
224     //
225     pProjPT=new GeomAPI_ProjectPointOnCurve;
226     pProjPT->Init(aC3D, f, l);
227     //
228     anAdr=(Standard_Address)pProjPT;
229     myProjPTMap.Add(aC3D, anAdr);
230   }
231   
232   else {
233     Standard_Address *pAdr=(Standard_Address *)anAdr;
234     pProjPT=(GeomAPI_ProjectPointOnCurve*)*pAdr;
235   }
236   return *pProjPT;
237 }
238 //=======================================================================
239 //function : SurfaceData
240 //purpose  : 
241 //=======================================================================
242   IntTools_SurfaceRangeLocalizeData& IntTools_Context::SurfaceData(const TopoDS_Face& aF) 
243 {
244   Standard_Address anAdr;
245   IntTools_SurfaceRangeLocalizeData* pSData;
246   //
247   anAdr=myProjSDataMap.FindFromKey1(aF);
248   if (!anAdr) {
249     //
250     pSData=new IntTools_SurfaceRangeLocalizeData(3, 
251                                                  3, 
252                                                  10. * Precision::PConfusion(), 
253                                                  10. * Precision::PConfusion());
254     //
255     anAdr=(Standard_Address)pSData;
256     myProjSDataMap.Add(aF, anAdr);
257   }
258   
259   else {
260     Standard_Address *pAdr=(Standard_Address *)anAdr;
261     pSData=(IntTools_SurfaceRangeLocalizeData*)*pAdr;
262   }
263   return *pSData;
264
265 }
266 //=======================================================================
267 //function : SolidClassifier
268 //purpose  : 
269 //=======================================================================
270   BRepClass3d_SolidClassifier& IntTools_Context::SolidClassifier(const TopoDS_Solid& aSolid)
271 {
272   Standard_Address anAdr;
273   BRepClass3d_SolidClassifier* pSC;
274   //
275   anAdr=mySClassMap.FindFromKey1(aSolid);
276   if (!anAdr) {
277     //
278     pSC=new BRepClass3d_SolidClassifier(aSolid);
279     //
280     anAdr=(Standard_Address)pSC;
281     mySClassMap.Add(aSolid, anAdr);
282   }
283   else {
284     Standard_Address *pAdr=(Standard_Address *)anAdr;
285     pSC =(BRepClass3d_SolidClassifier*)*pAdr;
286   }
287   return *pSC;
288 }
289 //=======================================================================
290 //function : ComputeVE
291 //purpose  : 
292 //=======================================================================
293   Standard_Integer IntTools_Context::ComputeVE(const TopoDS_Vertex& aV1, 
294                                                const TopoDS_Edge&   aE2,
295                                                Standard_Real& aT)
296 {
297   Standard_Boolean bToUpdate;
298   Standard_Integer iFlag;
299   Standard_Real aDist;
300   //
301   iFlag= IntTools_Context::ComputeVE(aV1, aE2, aT, bToUpdate, aDist);
302   //
303   return iFlag;
304 }
305 //=======================================================================
306 //function : ComputeVE
307 //purpose  : 
308 //=======================================================================
309   Standard_Integer IntTools_Context::ComputeVE(const TopoDS_Vertex& aV1, 
310                                                const TopoDS_Edge&   aE2,
311                                                Standard_Real& aT,
312                                                Standard_Boolean& bToUpdateVertex, 
313                                                Standard_Real& aDist)
314 {
315   bToUpdateVertex=Standard_False;
316   aDist=0.;
317   //
318   if (BRep_Tool::Degenerated(aE2)) {
319     return -1;
320   }
321   //
322   //modified by NIZNHY-PKV Wed Jul 13 08:30:08 2011f
323   //if (!BRep_Tool::IsGeometric(aE2)) { 
324   //  return -2;
325   //}
326   //modified by NIZNHY-PKV Wed Jul 13 08:30:13 2011t
327   //
328   Standard_Real aTolV1, aTolE2, aTolSum, aTolVx;
329   Standard_Integer aNbProj;
330   gp_Pnt aP;
331   //
332   aP=BRep_Tool::Pnt(aV1);
333   //
334   GeomAPI_ProjectPointOnCurve& aProjector=ProjPC(aE2);
335   aProjector.Perform(aP);
336   aNbProj=aProjector.NbPoints();
337   if (!aNbProj) {
338     return -3;
339   }
340   //
341   aDist=aProjector.LowerDistance();
342   aTolV1=BRep_Tool::Tolerance(aV1);
343   aTolE2=BRep_Tool::Tolerance(aE2);
344   aTolSum=aTolV1+aTolE2;
345   //
346   aT=aProjector.LowerDistanceParameter();
347   if (aDist > aTolSum) {
348     return -4;
349   }
350   //
351   aTolVx=aDist+aTolE2;
352   if (aTolVx>aTolV1) {
353     bToUpdateVertex=!bToUpdateVertex;
354     aDist=aTolVx;
355   }
356   //
357   return 0;
358 }
359 //=======================================================================
360 //function : ComputeVS
361 //purpose  : 
362 //=======================================================================
363   Standard_Integer IntTools_Context::ComputeVS(const TopoDS_Vertex& aV1, 
364                                                const TopoDS_Face&   aF2,
365                                                Standard_Real& U,
366                                                Standard_Real& V)
367 {
368   Standard_Real aTolV1, aTolF2, aTolSum, aDist;
369   gp_Pnt aP;
370
371   aP=BRep_Tool::Pnt(aV1);
372   //
373   // 1. Check if the point is projectable on the surface
374   GeomAPI_ProjectPointOnSurf& aProjector=ProjPS(aF2);
375   aProjector.Perform(aP);
376   //
377   if (!aProjector.IsDone()) {
378     // the point is not  projectable on the surface
379     return -1;
380   }
381   //
382   // 2. Check the distance between the projection point and 
383   //    the original point
384   aDist=aProjector.LowerDistance();
385
386   aTolV1=BRep_Tool::Tolerance(aV1);
387   aTolF2=BRep_Tool::Tolerance(aF2);
388   aTolSum=aTolV1+aTolF2;
389   if (aDist > aTolSum) {
390     // the distance is too large
391     return -2;
392   }
393   aProjector.LowerDistanceParameters(U, V);
394   //
395   gp_Pnt2d aP2d(U, V);
396   Standard_Boolean pri=IsPointInFace (aF2, aP2d);
397   if (!pri) {
398     //  the point lays on the surface but out of the face 
399     return -3;
400   }
401   return 0;
402 }
403 //=======================================================================
404 //function : StatePointFace
405 //purpose  : 
406 //=======================================================================
407   TopAbs_State IntTools_Context::StatePointFace(const TopoDS_Face& aF,
408                                                 const gp_Pnt2d& aP2d)
409 {
410   TopAbs_State aState;
411   IntTools_FClass2d& aClass2d=FClass2d(aF);
412   aState=aClass2d.Perform(aP2d);
413   return aState;
414 }
415 //=======================================================================
416 //function : IsPointInFace
417 //purpose  : 
418 //=======================================================================
419   Standard_Boolean IntTools_Context::IsPointInFace(const TopoDS_Face& aF,
420                                                    const gp_Pnt2d& aP2d)
421 {
422   TopAbs_State aState=StatePointFace(aF, aP2d);
423   if (aState==TopAbs_OUT || aState==TopAbs_ON) {
424     return Standard_False;
425   }
426   return Standard_True;
427 }
428 //=======================================================================
429 //function : IsPointInOnFace
430 //purpose  : 
431 //=======================================================================
432   Standard_Boolean IntTools_Context::IsPointInOnFace(const TopoDS_Face& aF,
433                                                      const gp_Pnt2d& aP2d)
434
435   TopAbs_State aState=StatePointFace(aF, aP2d);
436   if (aState==TopAbs_OUT) {
437     return Standard_False;
438   }
439   return Standard_True;
440 }
441 //=======================================================================
442 //function : IsValidPointForFace
443 //purpose  : 
444 //=======================================================================
445   Standard_Boolean IntTools_Context::IsValidPointForFace(const gp_Pnt& aP,
446                                                          const TopoDS_Face& aF,
447                                                          const Standard_Real aTol) 
448 {
449   Standard_Boolean bFlag;
450   Standard_Real Umin, myEpsT, U, V;
451   myEpsT=1.e-12;
452
453   GeomAPI_ProjectPointOnSurf& aProjector=ProjPS(aF);
454   aProjector.Perform(aP);
455   
456   bFlag=aProjector.IsDone();
457   if (bFlag) {
458     
459     Umin=aProjector.LowerDistance();
460     //if (Umin > 1.e-3) { // it was 
461     if (Umin > aTol) {
462       return !bFlag; 
463     }
464     //
465     aProjector.LowerDistanceParameters(U, V);
466     gp_Pnt2d aP2D(U, V);
467     bFlag=IsPointInOnFace (aF, aP2D);
468   }
469   return bFlag;
470 }
471 //=======================================================================
472 //function : IsValidPointForFaces
473 //purpose  : 
474 //=======================================================================
475   Standard_Boolean IntTools_Context::IsValidPointForFaces (const gp_Pnt& aP,
476                                                            const TopoDS_Face& aF1,
477                                                            const TopoDS_Face& aF2,
478                                                            const Standard_Real aTol) 
479 {
480   Standard_Boolean bFlag1, bFlag2;
481
482   bFlag1=IsValidPointForFace(aP, aF1, aTol);
483   if (!bFlag1) {
484     return bFlag1;
485   }
486   bFlag2=IsValidPointForFace(aP, aF2, aTol);  
487   return  bFlag2;
488 }
489 //=======================================================================
490 //function : IsValidBlockForFace
491 //purpose  : 
492 //=======================================================================
493   Standard_Boolean IntTools_Context::IsValidBlockForFace (const Standard_Real aT1,
494                                                           const Standard_Real aT2,
495                                                           const IntTools_Curve& aC, 
496                                                           const TopoDS_Face& aF,
497                                                           const Standard_Real aTol) 
498 {
499   Standard_Boolean bFlag;
500   Standard_Real aTInterm, aFirst, aLast;
501   gp_Pnt aPInterm;
502
503   aTInterm=IntTools_Tools::IntermediatePoint(aT1, aT2);
504
505   Handle(Geom_Curve) aC3D=aC.Curve();
506   aFirst=aC3D->FirstParameter();
507   aLast =aC3D->LastParameter();
508   // point 3D
509   aC3D->D0(aTInterm, aPInterm);
510   //
511   bFlag=IsValidPointForFace (aPInterm, aF, aTol);
512   return bFlag;
513 }
514 //=======================================================================
515 //function : IsValidBlockForFaces
516 //purpose  : 
517 //=======================================================================
518   Standard_Boolean IntTools_Context::IsValidBlockForFaces (const Standard_Real aT1,
519                                                            const Standard_Real aT2,
520                                                            const IntTools_Curve& aC, 
521                                                            const TopoDS_Face& aF1,
522                                                            const TopoDS_Face& aF2,
523                                                            const Standard_Real aTol) 
524 {
525   Standard_Boolean bFlag1, bFlag2;
526   //
527   Handle(Geom2d_Curve) aPC1 = aC.FirstCurve2d();
528   Handle(Geom2d_Curve) aPC2 = aC.SecondCurve2d();
529   if( !aPC1.IsNull() && !aPC2.IsNull() ) {
530     Standard_Real aMidPar = IntTools_Tools::IntermediatePoint(aT1, aT2);
531     gp_Pnt2d aPnt2D;
532
533
534     aPC1->D0(aMidPar, aPnt2D);
535     bFlag1 = IsPointInOnFace(aF1, aPnt2D);
536
537     if( !bFlag1 )
538       return bFlag1;
539
540     aPC2->D0(aMidPar, aPnt2D);
541     bFlag2 = IsPointInOnFace(aF2, aPnt2D);
542     return bFlag2;
543   }
544   //
545
546   bFlag1=IsValidBlockForFace (aT1, aT2, aC, aF1, aTol);
547   if (!bFlag1) {
548     return bFlag1;
549   }
550   bFlag2=IsValidBlockForFace (aT1, aT2, aC, aF2, aTol);
551   return bFlag2;
552 }
553 //=======================================================================
554 //function : IsVertexOnLine
555 //purpose  : 
556 //=======================================================================
557   Standard_Boolean IntTools_Context::IsVertexOnLine (const TopoDS_Vertex& aV,
558                                                      const IntTools_Curve& aC, 
559                                                      const Standard_Real aTolC,
560                                                      Standard_Real& aT)
561 {
562   Standard_Boolean bRet;
563   Standard_Real aTolV;
564   //
565   aTolV=BRep_Tool::Tolerance(aV);
566   bRet=IntTools_Context::IsVertexOnLine(aV, aTolV, aC, aTolC , aT);
567   //
568   return bRet;
569 }
570 //=======================================================================
571 //function : IsVertexOnLine
572 //purpose  : 
573 //=======================================================================
574   Standard_Boolean IntTools_Context::IsVertexOnLine (const TopoDS_Vertex& aV,
575                                                      const Standard_Real aTolV,
576                                                      const IntTools_Curve& aC, 
577                                                      const Standard_Real aTolC,
578                                                      Standard_Real& aT)
579 {
580   Standard_Real aFirst, aLast, aDist, aTolSum;
581   Standard_Integer aNbProj;
582   gp_Pnt aPv; 
583   
584   aPv=BRep_Tool::Pnt(aV);
585
586   Handle(Geom_Curve) aC3D=aC.Curve();
587   
588   
589   aTolSum=aTolV+aTolC;
590   //
591   GeomAdaptor_Curve aGAC(aC3D);
592   GeomAbs_CurveType aType=aGAC.GetType();
593   if (aType==GeomAbs_BSplineCurve ||
594       aType==GeomAbs_BezierCurve) {
595     aTolSum=2.*aTolSum;
596     if (aTolSum<1.e-5) {
597       aTolSum=1.e-5;
598     }
599   }
600   else {
601     aTolSum=2.*aTolSum;//xft
602     if(aTolSum < 1.e-6)
603       aTolSum = 1.e-6;
604   }
605   //
606   aFirst=aC3D->FirstParameter();
607   aLast =aC3D->LastParameter();
608   //
609   //Checking extermities first
610   if (!Precision::IsInfinite(aFirst)) {
611     gp_Pnt aPCFirst=aC3D->Value(aFirst);
612     aDist=aPv.Distance(aPCFirst);
613     if (aDist < aTolSum) {
614       aT=aFirst;
615       //
616       if(aDist > aTolV) {
617         Extrema_LocateExtPC anExt(aPv, aGAC, aFirst, 1.e-10);
618
619         if(anExt.IsDone()) {
620           Extrema_POnCurv aPOncurve = anExt.Point();
621           aT = aPOncurve.Parameter();
622
623           if((aT > (aLast + aFirst) * 0.5) ||
624              (aPv.Distance(aPOncurve.Value()) > aTolSum) ||
625              (aPCFirst.Distance(aPOncurve.Value()) < Precision::Confusion()))
626             aT = aFirst;
627         }
628       }
629       //
630       return Standard_True;
631     }
632   }
633   //
634   if (!Precision::IsInfinite(aLast)) {
635     gp_Pnt aPCLast=aC3D->Value(aLast);
636     aDist=aPv.Distance(aPCLast);
637     if (aDist < aTolSum) {
638       aT=aLast;
639       //
640       if(aDist > aTolV) {
641         Extrema_LocateExtPC anExt(aPv, aGAC, aLast, 1.e-10);
642
643         if(anExt.IsDone()) {
644           Extrema_POnCurv aPOncurve = anExt.Point();
645           aT = aPOncurve.Parameter();
646
647           if((aT < (aLast + aFirst) * 0.5) ||
648              (aPv.Distance(aPOncurve.Value()) > aTolSum) ||
649              (aPCLast.Distance(aPOncurve.Value()) < Precision::Confusion()))
650             aT = aLast;
651         }
652       }
653       //
654       return Standard_True;
655     }
656   }
657   //
658   GeomAPI_ProjectPointOnCurve& aProjector=ProjPT(aC3D);
659   aProjector.Perform(aPv);
660   
661   aNbProj=aProjector.NbPoints();
662   if (!aNbProj) {
663     Handle(Geom_BoundedCurve) aBC=
664       Handle(Geom_BoundedCurve)::DownCast(aC3D);
665     if (!aBC.IsNull()) {
666       gp_Pnt aPStart=aBC->StartPoint();
667       gp_Pnt aPEnd  =aBC->EndPoint();
668       
669       aDist=aPv.Distance(aPStart);
670       if (aDist < aTolSum) {
671         aT=aFirst;
672         return Standard_True;
673       }
674       
675       aDist=aPv.Distance(aPEnd);
676       if (aDist < aTolSum) {
677         aT=aLast;
678         return Standard_True;
679       }
680     }
681     
682     return Standard_False;
683   }
684   
685   aDist=aProjector.LowerDistance();
686   
687   if (aDist > aTolSum) {
688     return Standard_False;
689   }
690
691   aT=aProjector.LowerDistanceParameter();
692
693   return Standard_True; 
694 }
695 //=======================================================================
696 //function : ProjectPointOnEdge
697 //purpose  : 
698 //=======================================================================
699   Standard_Boolean IntTools_Context::ProjectPointOnEdge(const gp_Pnt& aP,
700                                                         const TopoDS_Edge& anEdge,
701                                                         Standard_Real& aT)
702 {
703   Standard_Integer aNbPoints;
704
705   GeomAPI_ProjectPointOnCurve& aProjector=ProjPC(anEdge);
706   aProjector.Perform(aP);
707
708   aNbPoints=aProjector.NbPoints();
709   if (aNbPoints) {
710     aT=aProjector.LowerDistanceParameter();
711     return Standard_True;
712   }
713   return Standard_False;
714 }
715