0023634: Eliminate Polyline and Polygon usage in drawers
[occt.git] / src / AIS / AIS_Shape.cxx
1 // Created on: 1996-12-20
2 // Created by: Robert COUBLANC
3 // Copyright (c) 1996-1999 Matra Datavision
4 // Copyright (c) 1999-2012 OPEN CASCADE SAS
5 //
6 // The content of this file is subject to the Open CASCADE Technology Public
7 // License Version 6.5 (the "License"). You may not use the content of this file
8 // except in compliance with the License. Please obtain a copy of the License
9 // at http://www.opencascade.org and read it completely before using this file.
10 //
11 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
12 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
13 //
14 // The Original Code and all software distributed under the License is
15 // distributed on an "AS IS" basis, without warranty of any kind, and the
16 // Initial Developer hereby disclaims all such warranties, including without
17 // limitation, any warranties of merchantability, fitness for a particular
18 // purpose or non-infringement. Please see the License for the specific terms
19 // and conditions governing the rights and limitations under the License.
20
21
22 #include <AIS_Shape.ixx>
23
24
25 #include <Standard_ErrorHandler.hxx>
26 #include <OSD_Timer.hxx>
27 #include <TColStd_ListIteratorOfListOfInteger.hxx>
28
29 #include <Quantity_Color.hxx>
30
31 #include <gp_Pnt.hxx>
32 #include <Bnd_Box.hxx>
33 #include <BRep_Builder.hxx>
34 #include <BRepTools_ShapeSet.hxx>
35 #include <BRepTools.hxx>
36 #include <BRepBndLib.hxx>
37 #include <TopExp.hxx>
38 #include <TopExp_Explorer.hxx>
39
40 #include <Aspect_TypeOfLine.hxx>
41 #include <Graphic3d_Structure.hxx>
42 #include <Graphic3d_Group.hxx>
43 #include <Graphic3d_AspectLine3d.hxx>
44 #include <Graphic3d_AspectText3d.hxx>
45 #include <Graphic3d_AspectMarker3d.hxx>
46 #include <Graphic3d_AspectFillArea3d.hxx>
47 #include <Graphic3d_ArrayOfPolylines.hxx>
48 #include <Graphic3d_MaterialAspect.hxx>
49
50 #include <Prs3d_Presentation.hxx>
51 #include <Prs3d_Root.hxx>
52 #include <Prs3d_ShadingAspect.hxx>
53 #include <Prs3d_Drawer.hxx>
54 #include <Prs3d_IsoAspect.hxx>
55
56 #include <StdPrs_WFShape.hxx>
57 #include <StdPrs_WFDeflectionShape.hxx>
58 #include <StdPrs_ShadedShape.hxx>
59 #include <StdPrs_HLRShape.hxx>
60 #include <StdPrs_HLRPolyShape.hxx>
61
62 #include <PrsMgr_ModedPresentation.hxx>
63
64 #include <Select3D_SensitiveEntity.hxx>
65 #include <StdSelect.hxx>
66 #include <StdSelect_BRepSelectionTool.hxx>
67 #include <StdSelect_BRepOwner.hxx>
68 #include <StdSelect_DisplayMode.hxx>
69
70 #include <AIS_GraphicTool.hxx>
71 #include <AIS_InteractiveContext.hxx>
72 #include <AIS_Drawer.hxx>
73 #include <HLRBRep.hxx>
74 #include <Precision.hxx>
75
76 #include <Standard_Failure.hxx>
77 #include <Standard_ErrorHandler.hxx>
78 #include <Select3D_SensitiveBox.hxx>
79 #include <TopoDS_Iterator.hxx>
80
81 static Standard_Boolean myFirstCompute;
82
83 Standard_Real AIS_Shape::GetDeflection(const TopoDS_Shape& aShape,
84                                        const Handle(Prs3d_Drawer)& aDrawer)
85 {
86   // WARNING: this same piece of code appears several times in Prs3d classes
87   Standard_Real aDeflection = aDrawer->MaximalChordialDeviation();
88   if (aDrawer->TypeOfDeflection() == Aspect_TOD_RELATIVE) {
89     Bnd_Box B;
90     BRepBndLib::Add(aShape, B, Standard_False);
91     if ( ! B.IsVoid() )
92     {
93       Standard_Real aXmin, aYmin, aZmin, aXmax, aYmax, aZmax;
94       B.Get(aXmin, aYmin, aZmin, aXmax, aYmax, aZmax);
95       aDeflection = Max( aXmax-aXmin, Max(aYmax-aYmin, aZmax-aZmin)) *
96                     aDrawer->DeviationCoefficient() * 4;
97     }
98   }
99   return aDeflection;
100 }
101
102 void AIS_Shape::DisplayBox(const Handle(Prs3d_Presentation)& aPrs,
103                            const Bnd_Box& B,
104                            const Handle(Prs3d_Drawer)& aDrawer)
105 {
106   static const Standard_Integer Indx[][3] =
107   { { 0, 0, 0 }, { 1, 0, 0 }, { 1, 0, 1 }, { 0, 0, 1 },
108     { 0, 1, 1 }, { 1, 1, 1 }, { 1, 1, 0 }, { 0, 1, 0 },
109     { 0, 0, 0 }, { 0, 0, 1 }, { 1, 0, 1 }, { 1, 1, 1 },
110     { 0, 1, 1 }, { 0, 1, 0 }, { 1, 1, 0 }, { 1, 0, 0 } };
111
112   if ( B.IsVoid() )
113     return; // nothing to show
114
115   Standard_Real X[2],Y[2],Z[2];
116   B.Get(X[0], Y[0], Z[0], X[1], Y[1], Z[1]);
117
118   Handle(Graphic3d_Group) G = Prs3d_Root::CurrentGroup(aPrs);
119   Quantity_Color Q;
120   Aspect_TypeOfLine A;
121   Standard_Real W;
122   aDrawer->LineAspect()->Aspect()->Values(Q,A,W);
123
124   G->SetGroupPrimitivesAspect(new Graphic3d_AspectLine3d(Q,Aspect_TOL_DOTDASH,W));
125
126   Handle(Graphic3d_ArrayOfPolylines) aPolyline = new Graphic3d_ArrayOfPolylines(16);
127   Standard_Integer i(0);
128   for(;i<16;i++)
129     aPolyline->AddVertex(X[Indx[i][0]],Y[Indx[i][1]],Z[Indx[i][2]]);
130   G->AddPrimitiveArray(aPolyline);
131 }
132
133 static Standard_Boolean IsInList(const TColStd_ListOfInteger& LL, const Standard_Integer aMode)
134 {
135   TColStd_ListIteratorOfListOfInteger It(LL);
136   for(;It.More();It.Next()){
137     if(It.Value()==aMode) 
138       return Standard_True;}
139   return Standard_False;
140 }
141
142 //==================================================
143 // Function: 
144 // Purpose :
145 //==================================================
146
147 AIS_Shape::
148 AIS_Shape(const TopoDS_Shape& shap):
149 AIS_InteractiveObject(PrsMgr_TOP_ProjectorDependant),
150 myshape(shap),
151 myCompBB(Standard_True),
152 myInitAng(0.)
153 {
154   myFirstCompute = Standard_True;
155   SetHilightMode(0);
156   myDrawer->SetShadingAspectGlobal(Standard_False);
157 }
158
159 //=======================================================================
160 //function : Type
161 //purpose  : 
162 //=======================================================================
163 AIS_KindOfInteractive AIS_Shape::Type() const 
164 {return AIS_KOI_Shape;}
165
166
167 //=======================================================================
168 //function : Signature
169 //purpose  : 
170 //=======================================================================
171 Standard_Integer AIS_Shape::Signature() const 
172 {return 0;}
173
174 //=======================================================================
175 //function : AcceptShapeDecomposition
176 //purpose  : 
177 //=======================================================================
178 Standard_Boolean AIS_Shape::AcceptShapeDecomposition() const 
179 {return Standard_True;}
180
181 //=======================================================================
182 //function : Compute
183 //purpose  : 
184 //=======================================================================
185 void AIS_Shape::Compute(const Handle(PrsMgr_PresentationManager3d)& /*aPresentationManager*/,
186                         const Handle(Prs3d_Presentation)& aPrs,
187                         const Standard_Integer aMode)
188 {  
189   aPrs->Clear();
190   if(myshape.IsNull()) return;
191
192   // wire,edge,vertex -> pas de HLR + priorite display superieure
193   Standard_Integer TheType = (Standard_Integer) myshape.ShapeType();
194   if(TheType>4 && TheType<8) {
195     aPrs->SetVisual(Graphic3d_TOS_ALL);
196     aPrs->SetDisplayPriority(TheType+2);
197   }
198   // Shape vide -> Assemblage vide.
199   if (myshape.ShapeType() == TopAbs_COMPOUND) {
200     TopoDS_Iterator anExplor (myshape);
201
202     if (!anExplor.More()) {
203       return;
204     }
205   }
206
207   if (IsInfinite()) aPrs->SetInfiniteState(Standard_True); //not taken in account duting FITALL
208   switch (aMode) {
209   case 0:{
210     try { OCC_CATCH_SIGNALS  StdPrs_WFDeflectionShape::Add(aPrs,myshape,myDrawer); }
211     catch (Standard_Failure) { 
212 #ifdef DEB
213       cout << "AIS_Shape::Compute()  failed"<< endl;
214 #endif
215       cout << "a Shape should be incorrect : No Compute can be maked on it  "<< endl;     
216 // presentation of the bounding box is calculated
217 //      Compute(aPresentationManager,aPrs,2);
218     }
219     break;
220   }
221   case 1:
222     {
223       Standard_Real prevangle ;
224       Standard_Real newangle  ; 
225       Standard_Real prevcoeff ;
226       Standard_Real newcoeff  ; 
227       
228       
229       if (OwnDeviationAngle(newangle,prevangle) ||
230           OwnDeviationCoefficient(newcoeff,prevcoeff))
231         if (Abs (newangle - prevangle) > Precision::Angular() ||
232             Abs (newcoeff - prevcoeff) > Precision::Confusion()  ) { 
233 #ifdef DEB
234           cout << "AIS_Shape : compute"<<endl;
235           cout << "newangl   : " << newangle << " # de " << "prevangl  : " << prevangle << " OU "<<endl;
236           cout << "newcoeff  : " << newcoeff << " # de " << "prevcoeff : " << prevcoeff << endl;
237 #endif
238           BRepTools::Clean(myshape);
239         }
240       
241       //shading only on face...
242       if ((Standard_Integer) myshape.ShapeType()>4)
243         StdPrs_WFDeflectionShape::Add(aPrs,myshape,myDrawer);
244       else {
245         myDrawer->SetShadingAspectGlobal(Standard_False);
246         if (IsInfinite()) StdPrs_WFDeflectionShape::Add(aPrs,myshape,myDrawer);
247         else {
248           {
249             try {
250               OCC_CATCH_SIGNALS
251               StdPrs_ShadedShape::Add(aPrs,myshape,myDrawer);
252             }
253             catch (Standard_Failure) {
254 #ifdef DEB
255               cout << "AIS_Shape::Compute() in ShadingMode failed"<< endl;
256 #endif
257               StdPrs_WFShape::Add(aPrs,myshape,myDrawer);
258             }
259           }
260         }
261       }
262       Standard_Real value = Transparency() ;
263       if( value > 0. ) {
264         SetTransparency( value );
265       }
266       break;
267     }
268   case 2:
269     {
270       // bounding box
271       if (IsInfinite()) StdPrs_WFDeflectionShape::Add(aPrs,myshape,myDrawer);
272       else DisplayBox(aPrs,BoundingBox(),myDrawer);
273     }
274   } // end switch
275   aPrs->ReCompute(); // for hidden line recomputation if necessary...
276 }
277
278 //=======================================================================
279 //function : Compute
280 //purpose  : 
281 //=======================================================================
282
283 void AIS_Shape::Compute(const Handle(PrsMgr_PresentationManager2d)& /*aPresentationManager*/,
284                         const Handle(Graphic2d_GraphicObject)& /*aGRO*/,
285                         const Standard_Integer /*aMode*/)
286 {
287 }
288
289 //=======================================================================
290 //function : Compute
291 //purpose  : Hidden Line Removal
292 //=======================================================================
293 void AIS_Shape::Compute(const Handle(Prs3d_Projector)& aProjector,
294                         const Handle(Prs3d_Presentation)& aPresentation)
295 {
296   Compute(aProjector,aPresentation,myshape);
297 }
298
299 //=======================================================================
300 //function : Compute
301 //purpose  : 
302 //=======================================================================
303
304 void AIS_Shape::Compute(const Handle(Prs3d_Projector)&     aProjector,
305                         const Handle(Geom_Transformation)& TheTrsf,
306                         const Handle(Prs3d_Presentation)&  aPresentation)
307 {
308   const TopLoc_Location& loc = myshape.Location();
309   TopoDS_Shape shbis = myshape.Located(TopLoc_Location(TheTrsf->Trsf())*loc);
310   Compute(aProjector,aPresentation,shbis);
311 }
312
313 //=======================================================================
314 //function : Compute
315 //purpose  : 
316 //=======================================================================
317
318 void AIS_Shape::Compute(const Handle(Prs3d_Projector)& aProjector,
319                         const Handle(Prs3d_Presentation)& aPresentation,
320                         const TopoDS_Shape& SH)
321 {
322   if (SH.ShapeType() == TopAbs_COMPOUND) {
323     TopoDS_Iterator anExplor (SH);
324
325     if (!anExplor.More()) // Shape vide -> Assemblage vide.
326       return;
327   }
328
329   Handle (Prs3d_Drawer) defdrawer = GetContext()->DefaultDrawer();
330   if (defdrawer->DrawHiddenLine()) 
331     {myDrawer->EnableDrawHiddenLine();}
332   else {myDrawer->DisableDrawHiddenLine();}
333
334   Aspect_TypeOfDeflection prevdef = defdrawer->TypeOfDeflection();
335   defdrawer->SetTypeOfDeflection(Aspect_TOD_RELATIVE);
336
337 // coefficients for calculation
338
339   Standard_Real prevangle, newangle ,prevcoeff,newcoeff ; 
340   if (OwnHLRDeviationAngle(newangle,prevangle) || OwnHLRDeviationCoefficient(newcoeff, prevcoeff))
341     if (Abs (newangle - prevangle) > Precision::Angular() ||
342         Abs (newcoeff - prevcoeff) > Precision::Confusion()  ) { 
343 #ifdef DEB
344       cout << "AIS_Shape : compute"<<endl;
345       cout << "newangle  : " << newangle << " # de " << "prevangl  : " << prevangle << " OU "<<endl;
346       cout << "newcoeff  : " << newcoeff << " # de " << "prevcoeff : " << prevcoeff << endl;
347 #endif
348       BRepTools::Clean(SH);
349     }
350   
351   {
352     try {
353       OCC_CATCH_SIGNALS
354       StdPrs_HLRPolyShape::Add(aPresentation,SH,myDrawer,aProjector);
355     }
356     catch (Standard_Failure) {
357 #ifdef DEB
358       cout <<"AIS_Shape::Compute(Proj) HLR Algorithm failed" << endl;
359 #endif
360       StdPrs_WFShape::Add(aPresentation,SH,myDrawer);
361     }
362   }
363
364   defdrawer->SetTypeOfDeflection (prevdef);
365 }
366
367 //=======================================================================
368 //function : SelectionType
369 //purpose  : gives the type according to the Index of Selection Mode
370 //=======================================================================
371
372 TopAbs_ShapeEnum AIS_Shape::SelectionType(const Standard_Integer aMode)
373 {
374   switch(aMode){
375   case 1:
376     return TopAbs_VERTEX;
377   case 2:
378     return TopAbs_EDGE;
379   case 3:
380     return TopAbs_WIRE;
381   case 4:
382     return TopAbs_FACE;
383   case 5:
384     return TopAbs_SHELL;
385   case 6:
386     return TopAbs_SOLID;
387   case 7:
388     return TopAbs_COMPSOLID;
389   case 8:
390     return TopAbs_COMPOUND;
391   case 0:
392   default:
393     return TopAbs_SHAPE;
394   }
395   
396 }
397 //=======================================================================
398 //function : SelectionType
399 //purpose  : gives the SelectionMode according to the Type od Decomposition...
400 //=======================================================================
401 Standard_Integer AIS_Shape::SelectionMode(const TopAbs_ShapeEnum aType)
402 {
403   switch(aType){
404   case TopAbs_VERTEX:
405     return 1;
406   case TopAbs_EDGE:
407     return 2;
408   case TopAbs_WIRE:
409     return 3;
410   case  TopAbs_FACE:
411     return 4;
412   case TopAbs_SHELL:
413     return 5;
414   case TopAbs_SOLID:
415     return 6;
416   case TopAbs_COMPSOLID:
417     return 7;
418   case TopAbs_COMPOUND:
419     return 8;
420   case TopAbs_SHAPE:
421   default:
422     return 0;
423   }
424 }
425
426
427 //=======================================================================
428 //function : ComputeSelection
429 //purpose  : 
430 //=======================================================================
431
432 void AIS_Shape::ComputeSelection(const Handle(SelectMgr_Selection)& aSelection,
433                                               const Standard_Integer aMode)
434 {
435   if(myshape.IsNull()) return;
436   if (myshape.ShapeType() == TopAbs_COMPOUND) {
437     TopoDS_Iterator anExplor (myshape);
438
439     if (!anExplor.More()) // empty Shape -> empty Assembly.
440       return;
441   }
442
443   static TopAbs_ShapeEnum TypOfSel;
444   TypOfSel = AIS_Shape::SelectionType(aMode);
445   TopoDS_Shape shape = myshape;
446   if( HasTransformation() ) {
447     Handle(Geom_Transformation) trsf = Transformation();
448     shape = shape.Located(TopLoc_Location(trsf->Trsf())*shape.Location());
449   }
450
451 // POP protection against crash in low layers
452
453   Standard_Real aDeflection = GetDeflection(shape, myDrawer);
454   Standard_Boolean autoTriangulation = Standard_True;
455   try {  
456     OCC_CATCH_SIGNALS
457     StdSelect_BRepSelectionTool::Load(aSelection,
458                                       this,
459                                       shape,
460                                       TypOfSel,
461                                       aDeflection,
462                                       myDrawer->HLRAngle(),
463                                       autoTriangulation); 
464   } catch ( Standard_Failure ) {
465 //    cout << "a Shape should be incorrect : A Selection on the Bnd  is activated   "<<endl;
466     if ( aMode == 0 ) {
467       Bnd_Box B = BoundingBox();
468       Handle(StdSelect_BRepOwner) aOwner = new StdSelect_BRepOwner(shape,this);
469       Handle(Select3D_SensitiveBox) aSensitiveBox = new Select3D_SensitiveBox(aOwner,B);
470       aSelection->Add(aSensitiveBox);
471     }
472   }
473
474   // insert the drawer in the BrepOwners for hilight...
475   StdSelect::SetDrawerForBRepOwner(aSelection,myDrawer);
476 }
477
478 Quantity_NameOfColor AIS_Shape::Color() const {
479 Quantity_Color aColor;
480   Color(aColor);
481   return aColor.Name();
482 }
483
484 void AIS_Shape::Color( Quantity_Color& aColor ) const {
485   aColor = myDrawer->ShadingAspect()->Color(myCurrentFacingModel);
486 }
487
488 Graphic3d_NameOfMaterial AIS_Shape::Material() const {
489   return (myDrawer->ShadingAspect()->Material(myCurrentFacingModel)).Name();
490 }
491
492 Standard_Real AIS_Shape::Transparency() const {
493   return myDrawer->ShadingAspect()->Transparency(myCurrentFacingModel);
494 }
495
496 //=======================================================================
497 //function : SetColor
498 //purpose  : 
499 //=======================================================================
500
501 void AIS_Shape::SetColor(const Quantity_NameOfColor aCol)
502 {
503   SetColor(Quantity_Color(aCol));
504 }
505
506 //=======================================================================
507 //function : SetColor
508 //purpose  : 
509 //=======================================================================
510
511 void AIS_Shape::SetColor(const Quantity_Color &aCol)
512 {
513   if( !HasColor() && !IsTransparent() && !HasMaterial() ) {
514     myDrawer->SetShadingAspect(new Prs3d_ShadingAspect());
515   }
516   hasOwnColor = Standard_True;
517
518   myDrawer->ShadingAspect()->SetColor(aCol,myCurrentFacingModel);
519   myDrawer->ShadingAspect()->SetTransparency(myTransparency,myCurrentFacingModel);
520   myDrawer->SetShadingAspectGlobal(Standard_False);
521
522
523   const Standard_Real WW = HasWidth()? Width():AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_Line);
524
525   myDrawer->SetLineAspect(new Prs3d_LineAspect(aCol,Aspect_TOL_SOLID,WW));
526   myDrawer->SetWireAspect(new Prs3d_LineAspect(aCol,Aspect_TOL_SOLID,WW));
527   myDrawer->SetFreeBoundaryAspect(new Prs3d_LineAspect(aCol,Aspect_TOL_SOLID,WW));
528   myDrawer->SetUnFreeBoundaryAspect(new Prs3d_LineAspect(aCol,Aspect_TOL_SOLID,WW));
529   myDrawer->SetSeenLineAspect(new Prs3d_LineAspect(aCol,Aspect_TOL_SOLID,WW));
530
531   // fast shading modification...
532   if(!GetContext().IsNull()){
533     if( GetContext()->MainPrsMgr()->HasPresentation(this,1)){
534       Handle(Prs3d_Presentation) aPresentation = 
535         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
536       Handle(Graphic3d_Group) aCurGroup = Prs3d_Root::CurrentGroup(aPresentation);
537       Handle(Graphic3d_AspectFillArea3d) anAreaAspect = myDrawer->ShadingAspect()->Aspect();
538       Handle(Graphic3d_AspectLine3d) aLineAspect = myDrawer->LineAspect()->Aspect();
539
540       // Set aspects for presentation and for group
541       aPresentation->SetPrimitivesAspect(anAreaAspect);
542       aPresentation->SetPrimitivesAspect(aLineAspect);
543       // Check if aspect of given type is set for the group, 
544       // because setting aspect for group with no already set aspect
545       // can lead to loss of presentation data
546       if (aCurGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
547         aCurGroup->SetGroupPrimitivesAspect(anAreaAspect);
548       if (aCurGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_LINE))
549         aCurGroup->SetGroupPrimitivesAspect(aLineAspect);
550     }
551   }
552
553   LoadRecomputable(0);
554   LoadRecomputable(2);
555 }
556
557 //=======================================================================
558 //function : UnsetColor
559 //purpose  : 
560 //=======================================================================
561
562 void AIS_Shape::UnsetColor()
563 {
564   if ( !HasColor() )
565   {
566     myToRecomputeModes.Clear();
567     return;
568   }
569   hasOwnColor = Standard_False;
570
571   Handle(Prs3d_LineAspect) NullAsp;
572   Handle(Prs3d_ShadingAspect) NullShA;
573   
574   if(!HasWidth()) {
575     myDrawer->SetLineAspect(NullAsp);
576     myDrawer->SetWireAspect(NullAsp);
577     myDrawer->SetFreeBoundaryAspect(NullAsp);
578     myDrawer->SetUnFreeBoundaryAspect(NullAsp);
579     myDrawer->SetSeenLineAspect(NullAsp);
580   }
581   else {
582     Quantity_Color CC;
583     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Line,CC);
584     myDrawer->LineAspect()->SetColor(CC);
585     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Wire,CC);
586     myDrawer->WireAspect()->SetColor(CC);
587     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Free,CC);
588     myDrawer->FreeBoundaryAspect()->SetColor(CC);
589     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_UnFree,CC);
590     myDrawer->UnFreeBoundaryAspect()->SetColor(CC);
591     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Seen,CC);
592     myDrawer->SeenLineAspect()->SetColor(CC);
593   }
594
595   if( HasMaterial() || IsTransparent()) {
596     Graphic3d_MaterialAspect mat = AIS_GraphicTool::GetMaterial(HasMaterial()? myDrawer : myDrawer->Link());
597     if( HasMaterial() ) {
598       Quantity_Color color = myDrawer->Link()->ShadingAspect()->Color(myCurrentFacingModel);
599       mat.SetColor(color);
600     }
601     if( IsTransparent() ) {
602       Standard_Real trans = myDrawer->ShadingAspect()->Transparency(myCurrentFacingModel);
603       mat.SetTransparency(trans);
604     }
605     myDrawer->ShadingAspect()->SetMaterial(mat,myCurrentFacingModel);
606   }
607   else {
608     myDrawer->SetShadingAspect(NullShA);
609   }
610
611   if(!GetContext().IsNull()){
612     if(GetContext()->MainPrsMgr()->HasPresentation(this,1)){
613       Handle(Prs3d_Presentation) aPresentation = 
614         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
615       Handle(Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup(aPresentation);
616
617       Handle(Graphic3d_AspectFillArea3d) anAreaAsp = myDrawer->Link()->ShadingAspect()->Aspect();
618       Handle(Graphic3d_AspectLine3d) aLineAsp = myDrawer->Link()->LineAspect()->Aspect();
619       Quantity_Color CC;
620       AIS_GraphicTool::GetInteriorColor(myDrawer->Link(),CC);
621       anAreaAsp->SetInteriorColor(CC);
622       aPresentation->SetPrimitivesAspect(anAreaAsp);
623       aPresentation->SetPrimitivesAspect(aLineAsp);
624       // Check if aspect of given type is set for the group, 
625       // because setting aspect for group with no already set aspect
626       // can lead to loss of presentation data
627       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
628         aGroup->SetGroupPrimitivesAspect(anAreaAsp);
629       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_LINE))
630         aGroup->SetGroupPrimitivesAspect(aLineAsp);
631     }
632   }
633   LoadRecomputable(0);
634   LoadRecomputable(2);
635 }
636
637 //=======================================================================
638 //function : SetWidth
639 //purpose  : 
640 //=======================================================================
641
642 void AIS_Shape::SetWidth(const Standard_Real W)
643 {
644   if(HasColor() || HasWidth()){
645     myDrawer->LineAspect()->SetWidth(W);
646     myDrawer->WireAspect()->SetWidth(W);
647     myDrawer->FreeBoundaryAspect()->SetWidth(W);
648     myDrawer->UnFreeBoundaryAspect()->SetWidth(W);
649     myDrawer->SeenLineAspect()->SetWidth(W);
650   }
651   else{
652     Quantity_Color CC;
653     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Line,CC);
654     myDrawer->SetLineAspect(new Prs3d_LineAspect(CC,Aspect_TOL_SOLID,W));
655     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Wire,CC);
656     myDrawer->SetWireAspect(new Prs3d_LineAspect(CC,Aspect_TOL_SOLID,W));
657     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Free,CC);
658     myDrawer->SetFreeBoundaryAspect(new Prs3d_LineAspect(CC,Aspect_TOL_SOLID,W));
659     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_UnFree,CC);
660     myDrawer->SetUnFreeBoundaryAspect(new Prs3d_LineAspect(CC,Aspect_TOL_SOLID,W));
661     AIS_GraphicTool::GetLineColor(myDrawer->Link(),AIS_TOA_Seen,CC);
662     myDrawer->SetSeenLineAspect(new Prs3d_LineAspect(CC,Aspect_TOL_SOLID,W));
663   }
664   myOwnWidth = W;
665   LoadRecomputable(0); // means that it is necessary to recompute only the wireframe....
666   LoadRecomputable(2); // and the bounding box...
667 }
668
669 //=======================================================================
670 //function : UnsetWidth
671 //purpose  : 
672 //=======================================================================
673
674 void AIS_Shape::UnsetWidth()
675 {
676   if(myOwnWidth == 0.0)
677   {
678     myToRecomputeModes.Clear();
679     return;
680   }
681   myOwnWidth=0.0;
682
683   Handle(Prs3d_LineAspect) NullAsp;
684
685   if(!HasColor()){
686     myDrawer->SetLineAspect(NullAsp);
687     myDrawer->SetWireAspect(NullAsp);
688     myDrawer->SetFreeBoundaryAspect(NullAsp);
689     myDrawer->SetUnFreeBoundaryAspect(NullAsp);
690     myDrawer->SetSeenLineAspect(NullAsp);
691   }
692   else{
693     myDrawer->LineAspect()->SetWidth(AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_Line));
694     myDrawer->WireAspect()->SetWidth(AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_Wire));
695     myDrawer->FreeBoundaryAspect()->SetWidth(AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_Free));
696     myDrawer->UnFreeBoundaryAspect()->SetWidth(AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_UnFree));
697     myDrawer->SeenLineAspect()->SetWidth(AIS_GraphicTool::GetLineWidth(myDrawer->Link(),AIS_TOA_Seen));
698   }
699   LoadRecomputable(0);
700 }
701
702 //=======================================================================
703 //function : SetMaterial
704 //purpose  : 
705 //=======================================================================
706
707 void AIS_Shape::SetMaterial(const Graphic3d_NameOfMaterial aMat)
708 {
709   SetMaterial(Graphic3d_MaterialAspect(aMat));
710 }
711
712 //=======================================================================
713 //function : SetMaterial
714 //purpose  : 
715 //=======================================================================
716
717 void AIS_Shape::SetMaterial(const Graphic3d_MaterialAspect& aMat)
718 {
719   if( !HasColor() && !IsTransparent() && !HasMaterial() ) {
720     myDrawer->SetShadingAspect(new Prs3d_ShadingAspect());
721   }
722   hasOwnMaterial = Standard_True;
723
724   myDrawer->ShadingAspect()->SetMaterial(aMat,myCurrentFacingModel);
725   myDrawer->ShadingAspect()->SetTransparency(myTransparency,myCurrentFacingModel);
726
727   if(!GetContext().IsNull()){
728     if(GetContext()->MainPrsMgr()->HasPresentation(this,1)){
729       Handle(Prs3d_Presentation) aPresentation = 
730         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
731       Handle(Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup(aPresentation);
732     
733       Handle(Graphic3d_AspectFillArea3d) anAreaAsp = myDrawer->ShadingAspect()->Aspect();
734       aPresentation->SetPrimitivesAspect(anAreaAsp);
735       // Check if aspect of given type is set for the group, 
736       // because setting aspect for group with no already set aspect
737       // can lead to loss of presentation data
738       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
739         aGroup->SetGroupPrimitivesAspect(anAreaAsp);
740     }
741     myRecomputeEveryPrs =Standard_False; // no mode to recalculate  :only viewer update
742     myToRecomputeModes.Clear();
743   }
744 }
745 //=======================================================================
746 //function : UnsetMaterial
747 //purpose  : 
748 //=======================================================================
749
750 void AIS_Shape::UnsetMaterial()
751 {
752   if( !HasMaterial() ) return;
753
754   if( HasColor() || IsTransparent()) {
755     Graphic3d_MaterialAspect mat = AIS_GraphicTool::GetMaterial(myDrawer->Link()); 
756     if( HasColor() ) {
757       Quantity_Color color = myDrawer->ShadingAspect()->Color(myCurrentFacingModel);
758       mat.SetColor(color);
759     }
760     if( IsTransparent() ) {
761       Standard_Real trans = myDrawer->ShadingAspect()->Transparency(myCurrentFacingModel);
762       mat.SetTransparency(trans);
763     }
764     myDrawer->ShadingAspect()->SetMaterial(mat,myCurrentFacingModel);
765   } else {
766     Handle(Prs3d_ShadingAspect) SA;
767     myDrawer->SetShadingAspect(SA);
768   }
769   hasOwnMaterial = Standard_False;
770   if(!GetContext().IsNull()){
771     if(GetContext()->MainPrsMgr()->HasPresentation(this,1)){
772       Handle(Prs3d_Presentation) aPresentation = 
773         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
774       Handle(Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup(aPresentation);
775       Handle(Graphic3d_AspectFillArea3d) anAreaAsp = myDrawer->ShadingAspect()->Aspect();
776       aPresentation->SetPrimitivesAspect(anAreaAsp);
777       // Check if aspect of given type is set for the group, 
778       // because setting aspect for group with no already set aspect
779       // can lead to loss of presentation data
780       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
781         aGroup->SetGroupPrimitivesAspect(anAreaAsp);
782     }
783   }
784   myRecomputeEveryPrs =Standard_False; // no mode to recalculate :only viewer update
785   myToRecomputeModes.Clear();  
786 }
787
788 //=======================================================================
789 //function : SetTransparency
790 //purpose  : 
791 //=======================================================================
792
793 void AIS_Shape::SetTransparency(const Standard_Real AValue)
794 {
795   if ( !HasColor() && !HasMaterial() ) {
796     myDrawer->SetShadingAspect(new Prs3d_ShadingAspect());
797   }
798   myDrawer->ShadingAspect()->SetTransparency(AValue,myCurrentFacingModel);
799   myTransparency = AValue;
800
801   if(!GetContext().IsNull()){
802     if(GetContext()->MainPrsMgr()->HasPresentation(this,1)){
803       Handle(Prs3d_Presentation) aPresentation = 
804         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
805       Handle(Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup(aPresentation);
806       Handle(Graphic3d_AspectFillArea3d) anAreaAsp = myDrawer->ShadingAspect()->Aspect();
807       aPresentation->SetPrimitivesAspect(anAreaAsp);
808       //force highest priority for transparent objects
809       aPresentation->SetDisplayPriority(10);
810       // Check if aspect of given type is set for the group, 
811       // because setting aspect for group with no already set aspect
812       // can lead to loss of presentation data
813       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
814         aGroup->SetGroupPrimitivesAspect(anAreaAsp);
815     }
816   }
817   myRecomputeEveryPrs =Standard_False; // no mode to recalculate :only viewer update
818   myToRecomputeModes.Clear();
819 }
820
821 //=======================================================================
822 //function : UnsetTransparency
823 //purpose  : 
824 //=======================================================================
825
826 void AIS_Shape::UnsetTransparency()
827 {
828   if( HasColor() || HasMaterial() ) {
829     myDrawer->ShadingAspect()->SetTransparency(0.0,myCurrentFacingModel);
830   } else {
831     Handle(Prs3d_ShadingAspect) SA;
832     myDrawer->SetShadingAspect(SA);
833   }
834
835   myTransparency = 0.0;
836
837   if(!GetContext().IsNull()){
838     if(GetContext()->MainPrsMgr()->HasPresentation(this,1)){
839       Handle(Prs3d_Presentation) aPresentation = 
840         GetContext()->MainPrsMgr()->CastPresentation(this,1)->Presentation();
841       Handle(Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup(aPresentation);
842       Handle(Graphic3d_AspectFillArea3d) anAreaAsp = myDrawer->ShadingAspect()->Aspect();
843       aPresentation->SetPrimitivesAspect(anAreaAsp);
844       // Check if aspect of given type is set for the group, 
845       // because setting aspect for group with no already set aspect
846       // can lead to loss of presentation data
847       if (aGroup->IsGroupPrimitivesAspectSet(Graphic3d_ASPECT_FILL_AREA))
848         aGroup->SetGroupPrimitivesAspect(anAreaAsp);
849
850       aPresentation->ResetDisplayPriority();
851     }
852   }
853   myRecomputeEveryPrs =Standard_False; // no mode to recalculate :only viewer update
854   myToRecomputeModes.Clear();
855 }
856
857 //=======================================================================
858 //function : LoadRecomputable
859 //purpose  : 
860 //=======================================================================
861
862 void AIS_Shape::LoadRecomputable(const Standard_Integer TheMode)
863 {
864   myRecomputeEveryPrs = Standard_False;
865   if(!IsInList(myToRecomputeModes,TheMode))
866     myToRecomputeModes.Append(TheMode);
867 }
868
869 //=======================================================================
870 //function : BoundingBox
871 //purpose  : 
872 //=======================================================================
873
874 const Bnd_Box& AIS_Shape::BoundingBox()  
875 {
876   if (myshape.ShapeType() == TopAbs_COMPOUND) {
877     TopoDS_Iterator anExplor (myshape);
878
879     if (!anExplor.More()) { // empty Shape  -> empty Assembly.
880       myBB.SetVoid();
881       return myBB;
882     }
883   }
884
885   if(myCompBB) {
886     BRepBndLib::AddClose(myshape, myBB);
887     myCompBB = Standard_False;
888   }
889   return myBB;
890 }
891
892 //*****
893 //***** Reset
894 //=======================================================================
895 //function : SetOwnDeviationCoefficient
896 //purpose  : resets myhasOwnDeviationCoefficient to Standard_False and
897 //           returns Standard_True if it change
898 //=======================================================================
899
900 Standard_Boolean AIS_Shape::SetOwnDeviationCoefficient ()
901 {
902   Standard_Boolean itSet = myDrawer->IsOwnDeviationCoefficient();
903   if(itSet)  myDrawer->SetDeviationCoefficient();
904   return itSet;
905 }
906
907 //=======================================================================
908 //function : SetHLROwnDeviationCoefficient
909 //purpose  : resets myhasOwnHLRDeviationCoefficient to Standard_False and
910 //           returns Standard_True if it change
911 //=======================================================================
912
913 Standard_Boolean AIS_Shape::SetOwnHLRDeviationCoefficient ()
914 {
915   Standard_Boolean itSet = myDrawer->IsOwnHLRDeviationCoefficient();
916   if(itSet)  myDrawer->SetHLRDeviationCoefficient();
917   return itSet;
918
919 }
920
921 //=======================================================================
922 //function : SetOwnDeviationAngle
923 //purpose  : resets myhasOwnDeviationAngle to Standard_False and
924 //           returns Standard_True if it change
925 //=======================================================================
926
927 Standard_Boolean AIS_Shape::SetOwnDeviationAngle ()
928 {
929   Standard_Boolean itSet = myDrawer->IsOwnDeviationAngle();
930   if(itSet)  myDrawer->SetDeviationAngle();
931   return itSet;
932
933 }
934
935 //=======================================================================
936 //function : SetOwnHLRDeviationAngle
937 //purpose  : resets myhasOwnHLRDeviationAngle to Standard_False and
938 //           returns Standard_True if it change
939 //=======================================================================
940
941 Standard_Boolean AIS_Shape::SetOwnHLRDeviationAngle ()
942 {
943   Standard_Boolean itSet = myDrawer->IsOwnHLRDeviationAngle();
944   if(itSet)  myDrawer->SetHLRAngle();
945   return itSet;
946
947 }
948 //***** SetOwn
949 //=======================================================================
950 //function : SetOwnDeviationCoefficient
951 //purpose  : 
952 //=======================================================================
953
954 void AIS_Shape::SetOwnDeviationCoefficient ( const Standard_Real  aCoefficient )
955 {
956   myDrawer->SetDeviationCoefficient( aCoefficient );
957   SetToUpdate(0) ; // WireFrame
958   SetToUpdate(1) ; // Shadding
959 }
960
961 //=======================================================================
962 //function : SetOwnHLRDeviationCoefficient
963 //purpose  : 
964 //=======================================================================
965
966 void AIS_Shape::SetOwnHLRDeviationCoefficient ( const Standard_Real  aCoefficient )
967 {
968   myDrawer->SetHLRDeviationCoefficient( aCoefficient );
969   
970 }
971
972 //=======================================================================
973 //function : SetOwnDeviationAngle
974 //purpose  : 
975 //=======================================================================
976
977 void AIS_Shape::SetOwnDeviationAngle ( const Standard_Real  anAngle )
978 {
979
980   myDrawer->SetDeviationAngle(anAngle );
981   SetToUpdate(0) ;   // WireFrame
982 }
983 //=======================================================================
984 //function : SetOwnDeviationAngle
985 //purpose  : 
986 //=======================================================================
987
988 void AIS_Shape::SetAngleAndDeviation ( const Standard_Real  anAngle )
989 {
990   Standard_Real OutAngl,OutDefl;
991   HLRBRep::PolyHLRAngleAndDeflection(anAngle,OutAngl,OutDefl);
992   SetOwnDeviationAngle(anAngle) ;
993   SetOwnDeviationCoefficient(OutDefl) ;
994   myInitAng = anAngle;
995   SetToUpdate(0);
996   SetToUpdate(1);
997 }
998
999 //=======================================================================
1000 //function : UserAngle
1001 //purpose  : 
1002 //=======================================================================
1003
1004 Standard_Real AIS_Shape::UserAngle() const
1005 {
1006   return myInitAng ==0. ? GetContext()->DeviationAngle(): myInitAng;
1007 }
1008
1009
1010 //=======================================================================
1011 //function : SetHLRAngleAndDeviation
1012 //purpose  : 
1013 //=======================================================================
1014
1015 void AIS_Shape::SetHLRAngleAndDeviation ( const Standard_Real  anAngle )
1016 {
1017   Standard_Real OutAngl,OutDefl;
1018   HLRBRep::PolyHLRAngleAndDeflection(anAngle,OutAngl,OutDefl);
1019   SetOwnHLRDeviationAngle( OutAngl );
1020   SetOwnHLRDeviationCoefficient(OutDefl);
1021
1022 }
1023 //=======================================================================
1024 //function : SetOwnHLRDeviationAngle
1025 //purpose  : 
1026 //=======================================================================
1027
1028 void AIS_Shape::SetOwnHLRDeviationAngle ( const Standard_Real  anAngle )
1029 {
1030   myDrawer->SetHLRAngle( anAngle );
1031 }
1032
1033 //***** GetOwn
1034 //=======================================================================
1035 //function : OwnDeviationCoefficient
1036 //purpose  : 
1037 //=======================================================================
1038
1039 Standard_Boolean AIS_Shape::OwnDeviationCoefficient ( Standard_Real &  aCoefficient,
1040                                                       Standard_Real & aPreviousCoefficient ) const
1041 {
1042   aCoefficient = myDrawer->DeviationCoefficient();
1043   aPreviousCoefficient = myDrawer->PreviousDeviationCoefficient ();
1044   return myDrawer->IsOwnDeviationCoefficient() ;
1045 }
1046
1047 //=======================================================================
1048 //function : OwnHLRDeviationCoefficient
1049 //purpose  : 
1050 //=======================================================================
1051
1052 Standard_Boolean AIS_Shape::OwnHLRDeviationCoefficient ( Standard_Real & aCoefficient,
1053                                                          Standard_Real & aPreviousCoefficient ) const
1054 {
1055   aCoefficient = myDrawer->HLRDeviationCoefficient();
1056   aPreviousCoefficient = myDrawer->PreviousHLRDeviationCoefficient ();
1057   return myDrawer->IsOwnHLRDeviationCoefficient();
1058
1059 }
1060
1061 //=======================================================================
1062 //function : OwnDeviationAngle
1063 //purpose  : 
1064 //=======================================================================
1065
1066 Standard_Boolean AIS_Shape::OwnDeviationAngle ( Standard_Real &  anAngle,
1067                                                 Standard_Real & aPreviousAngle ) const
1068 {
1069   anAngle = myDrawer->DeviationAngle();
1070   aPreviousAngle = myDrawer->PreviousDeviationAngle (); 
1071   return myDrawer->IsOwnDeviationAngle();
1072 }
1073
1074 //=======================================================================
1075 //function : OwnHLRDeviationAngle
1076 //purpose  : 
1077 //=======================================================================
1078
1079 Standard_Boolean AIS_Shape::OwnHLRDeviationAngle ( Standard_Real &  anAngle,
1080                                                    Standard_Real & aPreviousAngle ) const
1081 {
1082   anAngle = myDrawer->HLRAngle();
1083   aPreviousAngle = myDrawer->PreviousHLRDeviationAngle (); 
1084   return myDrawer->IsOwnHLRDeviationAngle();
1085 }