0028567: Get rid of the unused DRAW commands based on old Boolean Operations (BRepAlgo)
[occt.git] / src / BRepTest / BRepTest_FilletCommands.cxx
1 // Created on: 1994-06-20
2 // Created by: Modeling
3 // Copyright (c) 1994-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
8 // This library is free software; you can redistribute it and/or modify it under
9 // the terms of the GNU Lesser General Public License version 2.1 as published
10 // by the Free Software Foundation, with special exception defined in the file
11 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12 // distribution for complete text of the license and disclaimer of any warranty.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 #include <BRepTest.hxx>
18 #include <TColgp_Array1OfPnt2d.hxx>
19 #include <DBRep.hxx>
20 #include <Draw_Interpretor.hxx>
21 #include <Draw_Appli.hxx>
22 #include <BRepFilletAPI_MakeFillet.hxx>
23 #include <BiTgte_Blend.hxx>
24 #include <TopOpeBRepBuild_HBuilder.hxx>
25 #include <TopTools_ListIteratorOfListOfShape.hxx>
26 #include <TopAbs_ShapeEnum.hxx>
27 #include <TopoDS_Shape.hxx>
28 #include <TopoDS_Compound.hxx>
29 #include <TopoDS_Edge.hxx>
30 #include <TopoDS_Vertex.hxx>
31 #include <TopoDS.hxx>
32 #include <TopExp.hxx>
33 #include <TopExp_Explorer.hxx>
34
35 #include <BOPAlgo_PaveFiller.hxx>
36
37 #include <BRepAlgoAPI_BooleanOperation.hxx>
38 #include <BRepAlgoAPI_Fuse.hxx>
39 #include <BRepAlgoAPI_Cut.hxx>
40 #include <BRepAlgoAPI_Section.hxx>
41
42 #include <FilletSurf_Builder.hxx>
43 #include <ChFi3d_FilletShape.hxx>
44 #include <Geom_TrimmedCurve.hxx>
45 #include <Geom_Surface.hxx>
46 #include <Geom_Curve.hxx>
47 #include <Geom2d_Curve.hxx>
48 #include <TopTools_ListOfShape.hxx>
49 #include <FilletSurf_StatusType.hxx>
50 #include <FilletSurf_ErrorTypeStatus.hxx>
51 #include <TopAbs.hxx>
52 #include <DrawTrSurf.hxx>
53
54 #include <stdio.h>
55
56
57 static Standard_Real t3d = 1.e-4;
58 static Standard_Real t2d = 1.e-5;
59 static Standard_Real ta  = 1.e-2;
60 static Standard_Real fl  = 1.e-3;
61 static Standard_Real tapp_angle = 1.e-2;
62 static GeomAbs_Shape blend_cont = GeomAbs_C1;
63
64 static BRepFilletAPI_MakeFillet* Rakk = 0;
65 static BRepFilletAPI_MakeFillet* Rake = 0;
66 static char name[100];
67
68
69 static Standard_Integer contblend(Draw_Interpretor& di, Standard_Integer narg, const char** a)
70 {
71   if(narg ==1) {
72     //cout<<"tolerance angular of approximation  : "<< tapp_angle <<endl;
73     //cout<<"internal continuity                 : ";
74     di<<"tolerance angular of approximation  : "<< tapp_angle <<"\n";
75     di<<"internal continuity                 : ";
76     switch (blend_cont) {
77       case GeomAbs_C0:
78          //cout << ""<<endl;
79          di << "C0\n";
80          break;
81       case GeomAbs_C1:
82          //cout << "C1"<<endl;
83          di << "C1\n";
84          break;
85       case GeomAbs_C2:
86          //cout << "C2"<<endl;
87          di << "C2\n";
88          break;
89        default:
90          break;
91        }
92     return 0;
93   }
94   else {
95     if (narg >3) return 1;
96     if (narg == 3) {  tapp_angle = Abs(Draw::Atof(a[2])); }
97     char c=a[1][1];
98     switch (c) {
99     case '0':
100       blend_cont = GeomAbs_C0;
101       break;
102     case '2':
103       blend_cont = GeomAbs_C2;
104       break;
105     default :
106        blend_cont = GeomAbs_C1;    
107     }
108     return 0;
109   }
110 }
111
112 static void printtolblend(Draw_Interpretor& di)
113 {
114   //cout<<"tolerance ang : "<<ta<<endl;
115   //cout<<"tolerance 3d  : "<<t3d<<endl;
116   //cout<<"tolerance 2d  : "<<t2d<<endl;
117   //cout<<"fleche        : "<<fl<<endl;
118
119   //cout<<"tolblend "<<ta<<" "<<t3d<<" "<<t2d<<" "<<fl<<endl;
120
121   di<<"tolerance ang : "<<ta<<"\n";
122   di<<"tolerance 3d  : "<<t3d<<"\n";
123   di<<"tolerance 2d  : "<<t2d<<"\n";
124   di<<"fleche        : "<<fl<<"\n";
125
126   di<<"tolblend "<<ta<<" "<<t3d<<" "<<t2d<<" "<<fl<<"\n";
127 }
128
129 static Standard_Integer tolblend(Draw_Interpretor& di, Standard_Integer narg, const char** a)
130 {
131   if(narg == 1){
132     printtolblend(di);
133     return 0;
134   }
135   else if(narg == 5){
136     ta = Draw::Atof(a[1]);
137     t3d = Draw::Atof(a[2]);
138     t2d = Draw::Atof(a[3]);
139     fl = Draw::Atof(a[4]);
140     return 0;
141   }
142   return 1;
143 }
144 static Standard_Integer BLEND(Draw_Interpretor& di, Standard_Integer narg, const char** a)
145 {
146   if(Rakk != 0) {delete Rakk; Rakk = 0;}
147   printtolblend(di);
148   if (narg<5) return 1;
149   TopoDS_Shape V = DBRep::Get(a[2]);
150   if(V.IsNull()) return 1;
151   ChFi3d_FilletShape FSh = ChFi3d_Rational;
152   if (narg%2 == 0) {
153     if (!strcasecmp(a[narg-1], "Q")) {
154       FSh = ChFi3d_QuasiAngular;
155     }
156     else if (!strcasecmp(a[narg-1], "P")) {
157       FSh = ChFi3d_Polynomial;
158     }
159   }
160   Rakk = new BRepFilletAPI_MakeFillet(V,FSh);
161   Rakk->SetParams(ta,t3d,t2d,t3d,t2d,fl);
162   Rakk->SetContinuity(blend_cont, tapp_angle);
163   Standard_Real Rad;
164   TopoDS_Edge E;
165   Standard_Integer nbedge = 0;
166   for (Standard_Integer ii = 1; ii < (narg-1)/2; ii++){
167     Rad = Draw::Atof(a[2*ii + 1]);
168     TopoDS_Shape aLocalEdge(DBRep::Get(a[(2*ii+2)],TopAbs_EDGE));
169     E = TopoDS::Edge(aLocalEdge);
170 //    E = TopoDS::Edge(DBRep::Get(a[(2*ii+2)],TopAbs_EDGE));
171     if(!E.IsNull()){
172       Rakk->Add(Rad,E);
173       nbedge++;
174     }
175   }
176   if(!nbedge) return 1;
177   Rakk->Build();
178   if(!Rakk->IsDone()) return 1;
179   TopoDS_Shape res = Rakk->Shape();
180   DBRep::Set(a[1],res);
181   return 0;
182 }
183
184 static void PrintHist(const TopoDS_Shape& S,
185                       TopTools_ListIteratorOfListOfShape& It,
186                       Standard_Integer& nbgen)
187 {
188   TopoDS_Compound C;
189   BRep_Builder B;
190   B.MakeCompound(C);
191   B.Add(C,S);
192   char localname[100];
193   if(nbgen<10){
194     Sprintf(localname,"generated_00%d", nbgen++);
195   }
196   else if(nbgen<100){
197     Sprintf(localname,"generated_0%d", nbgen++);
198   }
199   else {
200     Sprintf(localname,"generated_%d", nbgen++);
201   }
202   for(; It.More(); It.Next()){
203     B.Add(C,It.Value());
204   }
205   DBRep::Set(localname,C);
206 }
207   
208 static Standard_Integer CheckHist(Draw_Interpretor& di, 
209                                   Standard_Integer , 
210                                   const char** )
211 {
212   if(Rakk == 0) {
213     //cout<<"No active Builder"<<endl;
214     di<<"No active Builder\n";
215     return 1;
216   }
217   if(!Rakk->IsDone()) {
218     //cout<<"Active Builder Not Done"<<endl;
219     di<<"Active Builder Not Done\n";
220     return 1;
221   }
222   Standard_Integer nbc = Rakk->NbContours();
223   Standard_Integer nbgen = 0;
224   TopTools_ListIteratorOfListOfShape It;
225   TopoDS_Shape curshape;
226   for(Standard_Integer i = 1; i <= nbc; i++){
227     curshape = Rakk->FirstVertex(i);
228     It.Initialize(Rakk->Generated(curshape));
229     PrintHist(curshape,It,nbgen);
230     Standard_Integer nbe = Rakk->NbEdges(i);
231     for(Standard_Integer j = 1; j <= nbe; j++){
232       curshape = Rakk->Edge(i,j);
233       It.Initialize(Rakk->Generated(curshape));
234       PrintHist(curshape,It,nbgen);
235     }
236     curshape = Rakk->LastVertex(i);
237     It.Initialize(Rakk->Generated(curshape));
238     PrintHist(curshape,It,nbgen);
239   }
240   //cout<<"foreach g [lsort [dir gen*]] { wclick; puts [dname $g]; donl $g; }"<<endl;
241   di<<"foreach g [lsort [dir gen*]] { wclick; puts [dname $g]; donl $g; }\n";
242   return 0;
243 }
244
245 static Standard_Integer MKEVOL(Draw_Interpretor& di, 
246                                Standard_Integer narg, 
247                                const char** a)
248 {
249   if(Rake != 0) {delete Rake; Rake = 0;}
250   printtolblend(di);
251   if (narg < 3) return 1;
252   TopoDS_Shape V = DBRep::Get(a[2]);
253   Rake = new BRepFilletAPI_MakeFillet(V);
254   Rake->SetParams(ta,t3d,t2d,t3d,t2d,fl);
255   Rake->SetContinuity(blend_cont, tapp_angle);
256   if (narg == 4) {
257     ChFi3d_FilletShape FSh = ChFi3d_Rational;
258     if (!strcasecmp(a[3], "Q")) {
259       FSh = ChFi3d_QuasiAngular;
260     }
261     else if (!strcasecmp(a[3], "P")) {
262       FSh = ChFi3d_Polynomial;
263     }
264     Rake->SetFilletShape(FSh);
265   }
266   strcpy(name, a[1]);
267   return 0;
268 }
269
270 static Standard_Integer UPDATEVOL(Draw_Interpretor& di, 
271                                   Standard_Integer narg, 
272                                   const char** a)
273 {
274   if(Rake == 0){
275     //cout << "MakeFillet not initialized"<<endl;
276     di << "MakeFillet not initialized\n";
277     return 1 ;
278   }
279   if(narg%2 != 0 || narg < 4) return 1;
280   TColgp_Array1OfPnt2d uandr(1,(narg/2)-1);
281   Standard_Real Rad, Par;
282   TopoDS_Shape aLocalEdge(DBRep::Get(a[1],TopAbs_EDGE));
283   TopoDS_Edge E = TopoDS::Edge(aLocalEdge);
284 //  TopoDS_Edge E = TopoDS::Edge(DBRep::Get(a[1],TopAbs_EDGE));
285   for (Standard_Integer ii = 1; ii <= (narg/2)-1; ii++){
286     Par = Draw::Atof(a[2*ii]);
287     Rad = Draw::Atof(a[2*ii + 1]);
288     uandr.ChangeValue(ii).SetCoord(Par,Rad);
289   }
290   Rake->Add(uandr,E);
291   return 0;
292 }
293
294 static Standard_Integer BUILDEVOL(Draw_Interpretor& di, 
295                                   Standard_Integer, 
296                                   const char**)
297 {
298   if(Rake == 0){
299     //cout << "MakeFillet not initialized"<<endl;
300     di << "MakeFillet not initialized\n";
301     return 1 ;
302   }
303   Rake->Build();
304   if(Rake->IsDone()){
305     TopoDS_Shape result = Rake->Shape();
306     DBRep::Set(name,result);
307     if(Rake != 0) {delete Rake; Rake = 0;}
308     return 0;
309   }
310   if(Rake != 0) {delete Rake; Rake = 0;}
311   return 1;
312 }
313
314
315
316
317 //**********************************************
318 // bfuse or bcut and then blend the section
319 //**********************************************
320
321 Standard_Integer boptopoblend(Draw_Interpretor& di, Standard_Integer narg, const char** a)
322 {
323   printtolblend(di);
324   if(narg < 5)
325   {
326     cout << "Use <command name> result shape1 shape2 radius [-d]" << endl;
327     return 1;
328   }
329
330   Standard_Boolean fuse  = !strcmp(a[0],"bfuseblend");
331   TopoDS_Shape S1 = DBRep::Get(a[2]);
332   TopoDS_Shape S2 = DBRep::Get(a[3]);
333   if (S1.IsNull() || S2.IsNull()) {
334     printf(" Null shapes are not allowed \n");
335     return 1;
336   }
337   Standard_Real Rad = Draw::Atof(a[4]);
338   Standard_Boolean isDebug = Standard_False;
339
340   if(narg == 6)
341   {
342     if(!strcmp(a[5], "-d"))
343     {
344       isDebug = Standard_True;
345     }
346   }
347
348   BOPAlgo_PaveFiller theDSFiller;
349   BOPCol_ListOfShape aLS;
350   aLS.Append(S1); 
351   aLS.Append(S2); 
352   theDSFiller.SetArguments(aLS);
353   //
354   theDSFiller.Perform();
355   if (theDSFiller.ErrorStatus()) {
356     printf("Check types of the arguments, please\n");
357     return 1;
358   }
359
360   BRepAlgoAPI_BooleanOperation* pBuilder=NULL;
361
362   if (fuse)
363     pBuilder = new BRepAlgoAPI_Fuse( S1, S2, theDSFiller );
364   else
365     pBuilder = new BRepAlgoAPI_Cut ( S1, S2, theDSFiller );
366
367   Standard_Boolean anIsDone = pBuilder->IsDone();
368   if (!anIsDone)
369   {
370     printf("boolean operation not done ErrorStatus()=%d\n", pBuilder->ErrorStatus());
371     return 1;
372   }
373
374   TopoDS_Shape ResultOfBop = pBuilder->Shape();
375   
376   delete pBuilder;
377
378   const int aStrLen = 1000;
379   char aBuff[aStrLen];
380
381   if(isDebug)
382   {
383     strcpy(aBuff, a[1]);
384     DBRep::Set( strcat(aBuff, "_bop"), ResultOfBop );
385
386     di << "Intermediate result of BOP-operation is saved to \"" << aBuff << "\" variable\n";
387   }
388
389   pBuilder = new BRepAlgoAPI_Section( S1, S2, theDSFiller );
390   TopoDS_Shape theSection = pBuilder->Shape();
391
392   if(isDebug)
393   {
394     strcpy(aBuff, a[1]);
395     DBRep::Set( strcat(aBuff, "_sec"), theSection );
396      di << "Intermediate bopsection result is saved to \"" << aBuff << "\" variable\n";
397   }
398
399   TopoDS_Compound result;
400   BRep_Builder BB; 
401   BB.MakeCompound(result);
402   
403   TopExp_Explorer Explo( ResultOfBop, TopAbs_SOLID );
404   for (; Explo.More(); Explo.Next())
405   {
406     const TopoDS_Shape& aSolid = Explo.Current();
407
408     BRepFilletAPI_MakeFillet Blender(aSolid);
409     Blender.SetParams(ta,t3d,t2d,t3d,t2d,fl);
410     Blender.SetContinuity( blend_cont, tapp_angle );
411
412     TopExp_Explorer expsec( theSection, TopAbs_EDGE );
413     for (; expsec.More(); expsec.Next())
414     {
415       TopoDS_Edge anEdge = TopoDS::Edge(expsec.Current());
416       Blender.Add( Rad, anEdge );
417     }
418
419     Blender.Build();
420     if (Blender.IsDone())
421       BB.Add( result, Blender.Shape() );
422     else
423     {
424       di << "Error: Cannot find the result of BLEND-operation."
425         " The result of BOP operation will be returned.\n";
426       BB.Add( result, aSolid );
427     }
428   }
429
430   delete pBuilder;
431   DBRep::Set( a[1], result );
432   return 0;
433 }
434
435
436 static Standard_Integer blend1(Draw_Interpretor& di, Standard_Integer narg, const char** a)
437 {
438   if (narg<5) return 1;
439   TopoDS_Shape V = DBRep::Get(a[2]);
440   if(V.IsNull()) return 1;
441   Standard_Integer nb ,i;
442   Standard_Real Rad;
443   Standard_Boolean simul=Standard_False;
444   const char *ns0=(a[1]);
445   Rad = Draw::Atof(a[3]);
446   TopTools_ListOfShape E;
447   for (i=4; i <=(narg-1) ; i++){
448     TopoDS_Shape edge= DBRep::Get(a[i],TopAbs_EDGE);
449    if (edge.IsNull()) return 1 ;
450    if(edge.ShapeType()!=TopAbs_EDGE) return 1;
451     E.Append(edge);
452   } 
453   FilletSurf_Builder aRakk(V,E,Rad);
454   if (simul) aRakk.Simulate();
455   else  aRakk.Perform();
456
457   //if (Rakk.IsDone()==FilletSurf_IsNotOk) 
458   // { FilletSurf_ErrorTypeStatus err=Rakk.StatusError();
459   //   if (err==FilletSurf_EmptyList) cout<< "StatusError=EmptyList"<<endl;
460   //   else if (err==FilletSurf_EdgeNotG1) cout<< "StatusError=NotG1"<<endl;
461   //   else if (err==FilletSurf_FacesNotG1) cout<< "StatusError=facesNotG1"<<endl;   
462   //   else if (err==FilletSurf_EdgeNotOnShape) 
463   //   cout<< "StatusError=edgenotonshape"<<endl;
464   //   else if (err==FilletSurf_NotSharpEdge ) cout<< "StatusError=notsharpedge"<<endl;
465   //   else if (err==FilletSurf_PbFilletCompute) cout <<"StatusError=PBFillet"<<endl;
466   // }
467   // else {
468   //  if (Rakk.IsDone()==FilletSurf_IsPartial) cout <<"resultat partiel"<<endl; 
469   if (aRakk.IsDone()==FilletSurf_IsNotOk)
470    { FilletSurf_ErrorTypeStatus err=aRakk.StatusError();
471      if (err==FilletSurf_EmptyList) di<< "StatusError=EmptyList\n";
472      else if (err==FilletSurf_EdgeNotG1) di<< "StatusError=NotG1\n";
473      else if (err==FilletSurf_FacesNotG1) di<< "StatusError=facesNotG1\n";
474      else if (err==FilletSurf_EdgeNotOnShape)
475      di<< "StatusError=edgenotonshape\n";
476      else if (err==FilletSurf_NotSharpEdge ) di<< "StatusError=notsharpedge\n";
477      else if (err==FilletSurf_PbFilletCompute) di <<"StatusError=PBFillet\n";
478    }
479    else {
480     if (aRakk.IsDone()==FilletSurf_IsPartial) di <<"partial result\n";
481  
482     nb=aRakk.NbSurface();
483     char localname [100];
484     char *temp; 
485     
486     // affichage du type d'arret 
487     
488    if (!simul)
489    { 
490     //if (Rakk.StartSectionStatus()==FilletSurf_NoExtremityOnEdge)
491     //  {cout<<" type deb conges = WLBLOUT"<<endl;}
492     //else if (Rakk.StartSectionStatus()==FilletSurf_OneExtremityOnEdge )
493     //  { cout<<" type deb conges = WLBLSTOP"<<endl;}
494     //else if (Rakk.StartSectionStatus()==FilletSurf_TwoExtremityOnEdge)
495     //  {cout<<" type deb conges = WLBLEND"<<endl;}
496     if (aRakk.StartSectionStatus()==FilletSurf_NoExtremityOnEdge)
497       {di<<" type start fillets = WLBLOUT\n";}
498     else if (aRakk.StartSectionStatus()==FilletSurf_OneExtremityOnEdge)
499       { di<<" type start fillets = WLBLSTOP\n";}
500     else if (aRakk.StartSectionStatus()==FilletSurf_TwoExtremityOnEdge)
501       {di<<" type start fillets = WLBLEND\n";}
502     
503     //if (Rakk.EndSectionStatus()==FilletSurf_NoExtremityOnEdge) 
504     //  {cout<<" type fin  conges = WLBLOUT"<<endl;}
505     //else if (Rakk.EndSectionStatus()==FilletSurf_OneExtremityOnEdge) 
506     //  {cout<<" type fin  conges = WLBLSTOP"<<endl;}
507     //else if (Rakk.EndSectionStatus()==FilletSurf_TwoExtremityOnEdge) 
508     //  { cout<<" type fin  conges = WLBLEND"<<endl;}
509     if (aRakk.EndSectionStatus()==FilletSurf_NoExtremityOnEdge)
510       {di<<" type end fillets = WLBLOUT\n";}
511     else if (aRakk.EndSectionStatus()==FilletSurf_OneExtremityOnEdge)
512       {di<<" type end fillets = WLBLSTOP\n";}
513     else if (aRakk.EndSectionStatus()==FilletSurf_TwoExtremityOnEdge)
514       { di<<" type end fillets = WLBLEND\n";}
515     Standard_Real f,l;
516     f = aRakk.FirstParameter();
517     l = aRakk.LastParameter();
518     //cout<<"parameter on edge start : "<<f<<endl;
519     //cout<<"parameter on edge end   : "<<l<<endl;
520     di<<"parametre on edge start : "<<f<<"\n";
521     di<<"parametre on edge end   : "<<l<<"\n";
522     for (i=1;i<=nb;i++){
523       //precision 
524       //cout<<"precision "<< i << "= "<<Rakk.TolApp3d(i)<<endl;
525       di<<"precision "<< i << "= "<<aRakk.TolApp3d(i)<<"\n";
526       
527       // display resulting surfaces  
528       Sprintf(localname, "%s%d" ,ns0,i);
529       temp = localname;
530       DrawTrSurf::Set(temp,aRakk.SurfaceFillet(i));
531       di << localname<< " ";
532       
533       // display curves 3d 
534       Sprintf(localname, "%s%d" ,"courb1",i);
535       temp =localname; 
536       DrawTrSurf::Set(temp,aRakk.CurveOnFace1(i));
537       di << localname<< " ";
538       Sprintf(localname, "%s%d" ,"courb2",i);
539       temp =localname;
540       DrawTrSurf::Set(temp,aRakk.CurveOnFace2(i));
541       di << localname<< " ";     
542       
543       // display supports 
544       Sprintf(localname, "%s%d" ,"face1",i);
545       temp =localname ;
546       DBRep::Set(temp,aRakk.SupportFace1(i));
547       di << localname<< " ";
548       Sprintf(localname, "%s%d" ,"face2",i);
549       temp =localname; 
550       DBRep::Set(temp,aRakk.SupportFace2(i));
551       di << localname<< " ";
552       
553       // display Pcurves on faces 
554       Sprintf(localname, "%s%d" ,"pcurveonface1",i);
555       temp =localname ;
556       DrawTrSurf::Set(temp,aRakk.PCurveOnFace1(i));
557       di << localname<< " ";
558       Sprintf(localname, "%s%d" ,"pcurveonface2",i);
559       temp =localname; 
560       DrawTrSurf::Set(temp,aRakk.PCurveOnFace2(i));
561       di << localname<< " ";
562       
563       // display Pcurves on the fillet
564       Sprintf(localname, "%s%d" ,"pcurveonconge1",i);
565       temp =localname;
566       DrawTrSurf::Set(temp,aRakk.PCurve1OnFillet(i));
567       di << localname<< " ";
568       Sprintf(localname, "%s%d" ,"pcurveonconge2",i);
569       temp =localname; 
570       DrawTrSurf::Set(temp,aRakk.PCurve2OnFillet(i));
571       di << localname<< " ";
572       
573     } }
574    else{
575    Standard_Integer j;
576   
577    for (i=1;i<=nb;i++)
578     {Standard_Integer s=aRakk.NbSection(i);
579     for (j=1;j<=s;j++)
580      {Handle(Geom_TrimmedCurve) Sec;
581      aRakk.Section(i,j,Sec);
582     Sprintf(localname, "%s%d%d" ,"sec",i,j);
583      temp =localname;
584     DrawTrSurf::Set (temp,Sec);
585     di << localname<< " ";}
586    }}
587  }
588   return 0;
589 }
590
591 //=======================================================================
592 //function : rollingball
593 //purpose  : 
594 //=======================================================================
595
596 Standard_Integer rollingball(Draw_Interpretor& di, Standard_Integer n, const char** a)
597 {
598   if ( n < 2) return 1;
599
600   TopoDS_Shape S = DBRep::Get(a[2]);
601   if ( S.IsNull()) return 1;
602   Standard_Real Rad = Draw::Atof(a[3]);
603   
604   Standard_Real Tol = t3d; //the same as blend ! 1.e-7;
605   
606   BiTgte_Blend Roll;
607   Roll.Init(S,Rad,Tol,Standard_False);
608   
609   Standard_Integer Nb = 0;
610   for ( Standard_Integer i = 4; i <= n-1; i++) {
611     if ( !strcmp(a[i],"@")) {
612       Nb++;
613       continue;
614     }
615
616     if ( Nb == 0) { // return stop faces.
617       TopoDS_Shape aLocalFace(DBRep::Get(a[i],TopAbs_FACE));
618       TopoDS_Face F1 = TopoDS::Face(aLocalFace);
619 //      TopoDS_Face F1 = TopoDS::Face(DBRep::Get(a[i],TopAbs_FACE));
620       if ( F1.IsNull()) {
621         //cout << " Stop face not referenced." << endl;
622         di << " Stop face not referenced.\n";
623         return 1;
624       }
625       Roll.SetStoppingFace(F1);
626     }
627     else if (Nb == 1) { // return faces on which the ball rotates
628       TopoDS_Shape aLocalFace(DBRep::Get(a[i],TopAbs_FACE));
629       TopoDS_Face F1 = TopoDS::Face(aLocalFace);
630 //      TopoDS_Face F1 = TopoDS::Face(DBRep::Get(a[i],TopAbs_FACE));
631       i++;
632       if ( !strcmp(a[i],"@")) {
633         //cout << " Even number of ball support faces is required " << endl;
634         di << " Even number of ball support faces is required \n";
635         return 1;
636       }
637       aLocalFace = DBRep::Get(a[i],TopAbs_FACE);
638       TopoDS_Face F2 = TopoDS::Face(aLocalFace);
639 //      TopoDS_Face F2 = TopoDS::Face(DBRep::Get(a[i],TopAbs_FACE));
640       if ( F1.IsNull() || F2.IsNull()) {
641         //cout << " Support face not referenced." << endl;
642         di << " Support face not referenced.\n";
643         return 1;
644       }
645       Roll.SetFaces(F1,F2);
646     }
647     else if (Nb == 2) { // return the edge on which the ball rotates
648       TopoDS_Shape aLocalShape(DBRep::Get(a[i],TopAbs_EDGE));
649       TopoDS_Edge E = TopoDS::Edge(aLocalShape);
650 //      TopoDS_Edge E = TopoDS::Edge(DBRep::Get(a[i],TopAbs_EDGE));
651       if ( E.IsNull()) {
652         //cout << " Edge not referenced." << endl;
653         di << " Edge not referenced.\n";
654         return 1;
655       }
656       Roll.SetEdge(E);
657     }
658
659   }
660   Standard_Boolean BuildShape = (!strcmp(a[0],"brollingball"));
661
662   Roll.Perform(BuildShape);
663
664   Standard_Boolean ComputeBranches = (!strcmp(a[0],"trollingball"));
665   char localname[100];
666   if (ComputeBranches) {
667     Standard_Integer NbBranches = Roll.NbBranches();
668     for (Standard_Integer i = 1; i <= NbBranches; i++) {
669       Standard_Integer From,To;
670       Roll.IndicesOfBranche(i,From,To);
671       //cout << " Indexes of the " << i << "th Branch : ";
672       //cout << "   " << From << "     " << To << endl;
673       di << " Indexes of the " << i << "th Branch : ";
674       di << "   " << From << "     " << To << "\n";
675       for (Standard_Integer j = From; j <= To; j++) {
676         const TopoDS_Shape& CurF = Roll.Face(j);
677         Sprintf(localname,"%s_%d_%d",a[1],i,j);
678         DBRep::Set(localname,CurF);
679       }
680     }
681     
682   }
683   else 
684     DBRep::Set(a[1],Roll.Shape());
685
686   return 0;
687 }
688
689 //=======================================================================
690 //function : FilletCommands
691 //purpose  : 
692 //=======================================================================
693
694 void  BRepTest::FilletCommands(Draw_Interpretor& theCommands)
695 {
696   static Standard_Boolean done = Standard_False;
697   if (done) return;
698   done = Standard_True;
699
700   DBRep::BasicCommands(theCommands);
701
702   const char* g = "TOPOLOGY Fillet construction commands";
703    
704   theCommands.Add("continuityblend",
705                   "continuityblend C0/C1/C2  [tangle]",__FILE__,
706                   contblend,g);
707
708   theCommands.Add("tolblend",
709                   "tolblend [ta t3d t2d fl]",__FILE__,
710                   tolblend,g);
711
712   theCommands.Add("blend",
713                   "blend result object rad1 ed1 rad2 ed2 ... [R/Q/P]",__FILE__,
714                   BLEND,g);
715
716   theCommands.Add("checkhist",
717                   "checkhist",__FILE__,
718                   CheckHist,g);
719
720   theCommands.Add("mkevol",
721                   "mkevol result object (then use updatevol) [R/Q/P]",__FILE__,
722                   MKEVOL,g);
723
724   theCommands.Add("updatevol",
725                   "updatevol edge u1 rad1 u2 rad2 ...",__FILE__,
726                   UPDATEVOL,g);
727
728   theCommands.Add("buildevol",
729                   "buildevol end of the evol fillet computation",__FILE__,
730                   BUILDEVOL,g);
731
732   theCommands.Add("bfuseblend",
733                   "bfuseblend result shape1 shape2 radius [-d]",__FILE__,
734                   boptopoblend,g);
735   
736   theCommands.Add("bcutblend",
737                   "bcutblend result shape1 tool radius [-d]",__FILE__,
738                   boptopoblend,g);
739
740   theCommands.Add("blend1",
741                   "blend1 result object rad ed1  ed2 ...",__FILE__,
742                   blend1,g); 
743
744   theCommands.Add("rollingball",
745                   "rollingball  r S radius [stopf1 ..] @ [f1 f2 ..] @ [e1 ..]",
746                   __FILE__,
747                   rollingball);
748
749   theCommands.Add("brollingball",
750                   "brollingball r S radius [stopf1 ..] @ [f1 f2 ..] @ [e1 ..]",
751                   __FILE__,
752                   rollingball);
753
754   theCommands.Add("trollingball",
755                   "trollingball r S radius [stopf1 ..] @ [f1 f2 ..] @ [e1 ..]",
756                   __FILE__,
757                   rollingball);
758 }