0027816: Visualization - provide an API for overriding clipping planes list
[occt.git] / src / PrsMgr / PrsMgr_PresentableObject.cxx
1 // Created on: 1997-12-16
2 // Created by: Jean Louis Frenkel
3 // Copyright (c) 1997-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
18 #include <Geom_Transformation.hxx>
19 #include <gp_Pnt.hxx>
20 #include <gp_Trsf.hxx>
21 #include <Graphic3d_DataStructureManager.hxx>
22 #include <Graphic3d_Structure.hxx>
23 #include <Graphic3d_TypeOfStructure.hxx>
24 #include <Prs3d_Presentation.hxx>
25 #include <Prs3d_Projector.hxx>
26 #include <PrsMgr_ModedPresentation.hxx>
27 #include <PrsMgr_PresentableObject.hxx>
28 #include <PrsMgr_Presentation.hxx>
29 #include <PrsMgr_PresentationManager.hxx>
30 #include <Standard_NotImplemented.hxx>
31 #include <Standard_Type.hxx>
32 #include <TColStd_ListIteratorOfListOfInteger.hxx>
33 #include <TColStd_MapOfInteger.hxx>
34
35 IMPLEMENT_STANDARD_RTTIEXT(PrsMgr_PresentableObject,MMgt_TShared)
36
37 //=======================================================================
38 //function : PrsMgr_PresentableObject
39 //purpose  :
40 //=======================================================================
41 PrsMgr_PresentableObject::PrsMgr_PresentableObject (const PrsMgr_TypeOfPresentation3d theType)
42 : myTypeOfPresentation3d (theType),
43   myIsMutable (Standard_False),
44   myZLayer (Graphic3d_ZLayerId_Default),
45   myHasOwnPresentations (Standard_True),
46   myParent (NULL)
47 {
48   //
49 }
50
51 //=======================================================================
52 //function : ~PrsMgr_PresentableObject
53 //purpose  : destructor
54 //=======================================================================
55 PrsMgr_PresentableObject::~PrsMgr_PresentableObject()
56 {
57   gp_Trsf anIdentity;
58   for (PrsMgr_ListOfPresentableObjectsIter anIter (myChildren); anIter.More(); anIter.Next())
59   {
60     anIter.Value()->SetCombinedParentTransform (anIdentity);
61     anIter.Value()->myParent = NULL;
62   }
63 }
64
65 //=======================================================================
66 //function : Fill
67 //purpose  : 
68 //=======================================================================
69 void PrsMgr_PresentableObject::Fill (const Handle(PrsMgr_PresentationManager)& thePrsMgr,
70                                      const Handle(PrsMgr_Presentation)&        thePrs,
71                                      const Standard_Integer                    theMode)
72 {
73   Handle(Prs3d_Presentation) aStruct3d = thePrs->Presentation();
74   Compute (thePrsMgr, aStruct3d, theMode);
75   UpdateTransformation (aStruct3d);
76   aStruct3d->SetClipPlanes (myClipPlanes);
77   aStruct3d->SetTransformPersistence (GetTransformPersistenceMode(), GetTransformPersistencePoint());
78 }
79
80 //=======================================================================
81 //function : Compute
82 //purpose  :
83 //=======================================================================
84 void PrsMgr_PresentableObject::Compute (const Handle(PrsMgr_PresentationManager)& /*aPresentationManager*/,
85                                         const Handle(Prs3d_Presentation)& /*aPresentation*/,
86                                         const Standard_Integer /*aMode*/)
87 {
88   Standard_NotImplemented::Raise("cannot compute in a 3d visualizer");
89 }
90
91 //=======================================================================
92 //function : Compute
93 //purpose  : 
94 //=======================================================================
95 void PrsMgr_PresentableObject::Compute(const Handle(Prs3d_Projector)& /*aProjector*/,
96                                        const Handle(Prs3d_Presentation)& /*aPresentation*/)
97 {
98   Standard_NotImplemented::Raise("cannot compute under a specific projector");
99 }
100
101 //=======================================================================
102 //function : Compute
103 //purpose  : 
104 //=======================================================================
105 void PrsMgr_PresentableObject::Compute(const Handle(Prs3d_Projector)& /* aProjector*/,
106                                        const Handle(Geom_Transformation)& /*aTrsf*/,
107                                                                const Handle(Prs3d_Presentation)& /*aPresentation*/)
108 {
109   Standard_NotImplemented::Raise("cannot compute under a specific projector");
110 }
111
112 //=======================================================================
113 //function : Update
114 //purpose  : 
115 //=======================================================================
116 void PrsMgr_PresentableObject::Update (const Standard_Boolean AllModes) {
117   Standard_Integer l = myPresentations.Length();
118   Handle(PrsMgr_PresentationManager) PM; 
119   for (Standard_Integer i=1; i <= l; i++) {
120     PM = myPresentations(i).Presentation()->PresentationManager();
121     if(AllModes) 
122       PM->Update(this,myPresentations(i).Mode());
123     else{
124       if(PM->IsDisplayed(this,myPresentations(i).Mode()) ||
125          PM->IsHighlighted(this,myPresentations(i).Mode())){
126         PM->Update(this,myPresentations(i).Mode());
127       }
128       else
129         SetToUpdate(myPresentations(i).Mode());
130     }
131   }
132 }
133
134 //=======================================================================
135 //function : Update
136 //purpose  : 
137 //=======================================================================
138 void PrsMgr_PresentableObject::Update (const Standard_Integer aMode, const Standard_Boolean ClearOther) {
139   Standard_Integer l = myPresentations.Length();
140   for (Standard_Integer i=1; i <= l; i++) {
141     if( myPresentations(i).Mode() == aMode){
142        Handle(PrsMgr_PresentationManager) PM=
143          myPresentations(i).Presentation()->PresentationManager();
144        
145        if(PM->IsDisplayed(this,aMode) ||
146           PM->IsHighlighted(this,aMode)){
147          PM->Update(this,aMode);
148          myPresentations(i).Presentation()->SetUpdateStatus(Standard_False);
149          
150        }
151        else
152          SetToUpdate(myPresentations(i).Mode());
153      }
154     
155   }
156   if(ClearOther) {
157     PrsMgr_Presentations save;
158     save =  myPresentations; 
159     myPresentations.Clear();
160     for (Standard_Integer i=1; i <= l; i++) {
161       if( save(i).Mode() == aMode) myPresentations.Append(save(i));
162     }
163   }
164
165 }
166
167 //=======================================================================
168 //function : Presentations
169 //purpose  : 
170 //=======================================================================
171 PrsMgr_Presentations& PrsMgr_PresentableObject::Presentations() {
172   return myPresentations;
173 }
174
175 //=======================================================================
176 //function : HasTransformation
177 //purpose  : 
178 //=======================================================================
179 Standard_Boolean PrsMgr_PresentableObject::HasTransformation() const 
180 {
181   return myTransformation.Form() != gp_Identity;
182 }
183
184 //=======================================================================
185 //function : SetToUpdate
186 //purpose  : 
187 //=======================================================================
188 void PrsMgr_PresentableObject::SetToUpdate(const Standard_Integer aMode)
189 {
190   for(Standard_Integer IP =1; IP<=myPresentations.Length();IP++){
191     if(myPresentations(IP).Mode()==aMode)
192       myPresentations(IP).Presentation()->SetUpdateStatus(Standard_True);
193   }
194 }
195
196 //=======================================================================
197 //function : SetToUpdate
198 //purpose  :
199 //=======================================================================
200 void PrsMgr_PresentableObject::SetToUpdate()
201 {
202   for(Standard_Integer IP =1; IP<=myPresentations.Length();IP++){
203     myPresentations(IP).Presentation()->SetUpdateStatus(Standard_True);
204   }
205 }
206
207 //=======================================================================
208 //function : ToBeUpdated
209 //purpose  : gets the list of modes to be updated
210 //=======================================================================
211 void PrsMgr_PresentableObject::ToBeUpdated(TColStd_ListOfInteger& OutList) const
212 {
213   OutList.Clear();
214   // on dimensionne les buckets a la taille de la seq.
215   TColStd_MapOfInteger MI(myPresentations.Length()); 
216   
217   for(Standard_Integer IP =1; IP<=myPresentations.Length();IP++){
218     const PrsMgr_ModedPresentation& MP = myPresentations(IP);
219     if(MP.Presentation()->MustBeUpdated())
220       if(!MI.Contains(MP.Mode())){
221         OutList.Append(MP.Mode());
222         MI.Add(MP.Mode());
223       }
224   }
225 }
226
227 //=======================================================================
228 //function : SetTypeOfPresentation
229 //purpose  :
230 //=======================================================================
231 void PrsMgr_PresentableObject::SetTypeOfPresentation (const PrsMgr_TypeOfPresentation3d theType)
232 {
233   myTypeOfPresentation3d = theType;
234   for(Standard_Integer aPrsIter = 1; aPrsIter <= myPresentations.Length(); ++aPrsIter)
235   {
236     const Handle(PrsMgr_Presentation)& aPrs  = myPresentations (aPrsIter).Presentation();
237     aPrs->Presentation()->SetVisual (myTypeOfPresentation3d == PrsMgr_TOP_ProjectorDependant
238                                    ? Graphic3d_TOS_COMPUTED
239                                    : Graphic3d_TOS_ALL);
240   }
241 }
242
243 //=======================================================================
244 //function : SetLocalTransformation
245 //purpose  : WARNING : use with only 3D objects...
246 //=======================================================================
247 void PrsMgr_PresentableObject::SetLocalTransformation (const gp_Trsf& theTransformation) 
248 {
249   myLocalTransformation = theTransformation;
250   UpdateTransformation();
251 }
252
253 //=======================================================================
254 //function : ResetTransformation
255 //purpose  : 
256 //=======================================================================
257 void PrsMgr_PresentableObject::ResetTransformation() 
258 {
259   SetLocalTransformation (gp_Trsf());  
260 }
261
262 //=======================================================================
263 //function : SetCombinedParentTransform
264 //purpose  : 
265 //=======================================================================
266 void PrsMgr_PresentableObject::SetCombinedParentTransform (const gp_Trsf& theTransformation) 
267 {
268   myCombinedParentTransform = theTransformation;
269   UpdateTransformation();
270 }
271
272 //=======================================================================
273 //function : UpdateTransformation
274 //purpose  :
275 //=======================================================================
276 void PrsMgr_PresentableObject::UpdateTransformation()
277 {
278   myTransformation = myCombinedParentTransform * myLocalTransformation;
279   myInvTransformation = myTransformation.Inverted();
280   Handle(Geom_Transformation) aTrsf = new Geom_Transformation (myTransformation);
281
282   for (Standard_Integer aPrsIter = 1; aPrsIter <= myPresentations.Length(); ++aPrsIter)
283   {
284     myPresentations (aPrsIter).Presentation()->Transform (aTrsf);
285   }
286   
287   PrsMgr_ListOfPresentableObjectsIter anIter (myChildren);
288
289   for (; anIter.More(); anIter.Next())
290   {
291     anIter.Value()->SetCombinedParentTransform (myTransformation);
292   }
293 }
294
295 //=======================================================================
296 //function : UpdateTransformation
297 //purpose  : 
298 //=======================================================================
299 void PrsMgr_PresentableObject::UpdateTransformation(const Handle(Prs3d_Presentation)& P)
300 {
301   Handle(Geom_Transformation) aTrsf = new Geom_Transformation (myTransformation);
302   P->Transform (aTrsf);  
303 }
304
305 //=======================================================================
306 //function : SetTransformPersistence
307 //purpose  :
308 //=======================================================================
309 void PrsMgr_PresentableObject::SetTransformPersistence (const Graphic3d_TransModeFlags& theFlag,
310                                                         const gp_Pnt&                   thePoint)
311 {
312   myTransformPersistence.Flags     = theFlag;
313   myTransformPersistence.Point.x() = thePoint.X();
314   myTransformPersistence.Point.y() = thePoint.Y();
315   myTransformPersistence.Point.z() = thePoint.Z();
316   for (Standard_Integer aPrsIter = 1; aPrsIter <= myPresentations.Length(); ++aPrsIter)
317   {
318     const Handle(PrsMgr_Presentation)& aPrs3d = myPresentations (aPrsIter).Presentation();
319     if (!aPrs3d.IsNull()
320      && !aPrs3d->Presentation().IsNull())
321     {
322       aPrs3d->Presentation()->SetTransformPersistence (theFlag, thePoint);
323       aPrs3d->Presentation()->ReCompute();
324     }
325   }
326 }
327
328 //=======================================================================
329 //function : GetTransformPersistence
330 //purpose  : 
331 //=======================================================================
332 Graphic3d_TransModeFlags PrsMgr_PresentableObject::GetTransformPersistenceMode() const
333 {
334   return myTransformPersistence.Flags;
335 }
336
337 //=======================================================================
338 //function : GetTransformPersistence
339 //purpose  : 
340 //=======================================================================
341 gp_Pnt PrsMgr_PresentableObject::GetTransformPersistencePoint() const
342 {
343   return gp_Pnt (myTransformPersistence.Point.x(),
344                  myTransformPersistence.Point.y(),
345                  myTransformPersistence.Point.z());
346 }
347
348 //=======================================================================
349 //function : AddChild
350 //purpose  : 
351 //=======================================================================
352 void PrsMgr_PresentableObject::AddChild (const Handle(PrsMgr_PresentableObject)& theObject)
353 {
354   Handle(PrsMgr_PresentableObject) aHandleGuard = theObject;
355   if (theObject->myParent != NULL)
356   {
357     theObject->myParent->RemoveChild (aHandleGuard);
358   }
359
360   myChildren.Append (theObject);  
361   theObject->myParent = this;
362   theObject->SetCombinedParentTransform (myTransformation);
363 }
364
365 //=======================================================================
366 //function : RemoveChild
367 //purpose  : 
368 //=======================================================================
369 void PrsMgr_PresentableObject::RemoveChild (const Handle(PrsMgr_PresentableObject)& theObject)
370 {
371   PrsMgr_ListOfPresentableObjectsIter anIter (myChildren);
372   for (; anIter.More(); anIter.Next())
373   {
374     if (anIter.Value() == theObject)
375     {
376       theObject->myParent = NULL;
377       theObject->SetCombinedParentTransform (gp_Trsf());
378       myChildren.Remove (anIter);
379       break;
380     }
381   }
382 }
383
384 //=======================================================================
385 //function : SetZLayer
386 //purpose  :
387 //=======================================================================
388 void PrsMgr_PresentableObject::SetZLayer (const Graphic3d_ZLayerId theLayerId)
389 {
390   if (myZLayer == theLayerId)
391   {
392     return;
393   }
394
395   myZLayer = theLayerId;
396   for (Standard_Integer aPrsIter = 1; aPrsIter <= myPresentations.Length(); ++aPrsIter)
397   {
398     const PrsMgr_ModedPresentation& aModedPrs = myPresentations (aPrsIter);
399     if (aModedPrs.Presentation().IsNull()
400      || aModedPrs.Presentation()->Presentation().IsNull())
401     {
402       continue;
403     }
404
405     aModedPrs.Presentation()->Presentation()->SetZLayer (theLayerId);
406   }
407 }
408
409 //=======================================================================
410 //function : ZLayer
411 //purpose  :
412 //=======================================================================
413 Graphic3d_ZLayerId PrsMgr_PresentableObject::ZLayer() const
414 {
415   return myZLayer;
416 }
417
418 // =======================================================================
419 // function : AddClipPlane
420 // purpose  :
421 // =======================================================================
422 void PrsMgr_PresentableObject::AddClipPlane (const Handle(Graphic3d_ClipPlane)& thePlane)
423 {
424   // add to collection and process changes
425   if (myClipPlanes.IsNull())
426   {
427     myClipPlanes = new Graphic3d_SequenceOfHClipPlane();
428   }
429
430   myClipPlanes->Append (thePlane);
431   UpdateClipping();
432 }
433
434 // =======================================================================
435 // function : RemoveClipPlane
436 // purpose  :
437 // =======================================================================
438 void PrsMgr_PresentableObject::RemoveClipPlane (const Handle(Graphic3d_ClipPlane)& thePlane)
439 {
440   if (myClipPlanes.IsNull())
441   {
442     return;
443   }
444
445   // remove from collection and process changes
446   for (Graphic3d_SequenceOfHClipPlane::Iterator aPlaneIt (*myClipPlanes); aPlaneIt.More(); aPlaneIt.Next())
447   {
448     const Handle(Graphic3d_ClipPlane)& aPlane = aPlaneIt.Value();
449     if (aPlane != thePlane)
450       continue;
451
452     myClipPlanes->Remove (aPlaneIt);
453     UpdateClipping();
454     return;
455   }
456 }
457
458 // =======================================================================
459 // function : SetClipPlanes
460 // purpose  :
461 // =======================================================================
462 void PrsMgr_PresentableObject::SetClipPlanes (const Handle(Graphic3d_SequenceOfHClipPlane)& thePlanes)
463 {
464   // change collection and process changes
465   myClipPlanes = thePlanes;
466   UpdateClipping();
467 }
468
469 // =======================================================================
470 // function : UpdateClipping
471 // purpose  :
472 // =======================================================================
473 void PrsMgr_PresentableObject::UpdateClipping()
474 {
475   // affect generated structures
476   for (Standard_Integer aPrsIt = 1; aPrsIt <= myPresentations.Length(); ++aPrsIt)
477   {
478     // pass over presentation manager 3d mechanism right to the structures -
479     // we do not interested in display mode collections.
480     const PrsMgr_ModedPresentation& aModedPrs = myPresentations (aPrsIt);
481     if (aModedPrs.Presentation().IsNull()
482      || aModedPrs.Presentation()->Presentation().IsNull())
483     {
484       continue;
485     }
486
487     aModedPrs.Presentation()->Presentation()->SetClipPlanes (myClipPlanes);
488   }
489 }
490
491 // =======================================================================
492 // function : SetMutable
493 // purpose  :
494 // =======================================================================
495 void PrsMgr_PresentableObject::SetMutable (const Standard_Boolean theIsMutable)
496 {
497   if (myIsMutable == theIsMutable)
498   {
499     return;
500   }
501
502   myIsMutable = theIsMutable;
503   for (Standard_Integer aPrsIter = 1; aPrsIter <= myPresentations.Length(); ++aPrsIter)
504   {
505     const PrsMgr_ModedPresentation& aModedPrs = myPresentations (aPrsIter);
506     if (aModedPrs.Presentation().IsNull()
507      || aModedPrs.Presentation()->Presentation().IsNull())
508     {
509       continue;
510     }
511
512     aModedPrs.Presentation()->Presentation()->SetMutable (theIsMutable);
513   }
514 }