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