0023234: Incorrect behavior of AIS_Trihedron
[occt.git] / src / AIS / AIS_LocalContext.cxx
1 // Created on: 1997-01-17
2 // Created by: Robert COUBLANC
3 // Copyright (c) 1997-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 //Modified by ROB : Traque des UpdateConversion intempestifs.
22
23 #define BUC60688       //GG 25/05/00 Add SetSensitivity() methods.
24
25 #define BUC60722        //GG_040900 Disable detection on an unviewable object
26
27 #define IMP160701       //SZV Add InitDetected(),MoreDetected(),NextDetected(),
28 //                       DetectedCurrentShape(),DetectedCurrentObject()
29 //                       methods
30
31 #define ALE70590        //GG  Avoid raise especially under W2000-SP2
32 //              when opening many local context due to a
33 //              system error in the selection name computation routine.
34 //              Many thanks to Philippe CARRET for the helpfull he has 
35 //              give to accelerate the resolution of this problem.
36
37 #include <AIS_LocalContext.ixx>
38 #include <SelectMgr_OrFilter.hxx>
39 #include <SelectMgr_CompositionFilter.hxx>
40 #include <AIS_LocalStatus.hxx>
41 #include <AIS_Shape.hxx>
42 #include <TColStd_ListIteratorOfListOfInteger.hxx>
43 #include <AIS_ListIteratorOfListOfInteractive.hxx>
44 #include <AIS_ListOfInteractive.hxx>
45 #include <AIS_DataMapIteratorOfDataMapOfSelStat.hxx>
46 #include <TopAbs_ShapeEnum.hxx>
47 #include <Graphic3d_Structure.hxx>
48 #include <Prs3d_LineAspect.hxx>
49 #include <Prs3d_PlaneAspect.hxx>
50 #include <Prs3d_PointAspect.hxx>
51 #include <Prs3d_Presentation.hxx>
52 #include <Aspect_TypeOfMarker.hxx>
53 #include <StdSelect_ShapeTypeFilter.hxx>
54 #include <AIS_Selection.hxx>
55 #include <V3d_Viewer.hxx>
56 #include <V3d_View.hxx>
57 #include <Visual3d_TransientManager.hxx>
58 #include <Visual3d_View.hxx>
59
60 #ifdef ALE70590
61 #include <stdio.h>
62 #else
63 #include <Standard_SStream.hxx>
64 #endif
65
66 static TCollection_AsciiString AIS_Local_SelName(const Standard_Address address,
67                                                  const Standard_Integer anIndex)
68 {
69 //  TCollection_AsciiString SelName;
70 #ifdef ALE70590
71   char string[100];
72   sprintf(string,"%p_%d", address, anIndex);    // works under any system 
73   TCollection_AsciiString SelName(string);
74 #else
75   Standard_SStream stream;
76   stream<<address;      // something is wrong here using the SStream because
77 //              the following access to rdbuf crash for an unknown reason 
78 //              especially under W2000 with SP2 and sometime under WNT and W98.
79 //              NOTE that stream is not ended by a NULL char and it's probably
80 //              one of the reasons why this crash.
81 //              In any case the resulting ascii string give a wrong and random
82 //              name under WINDOWS !
83   TCollection_AsciiString SelName(stream.rdbuf()->str());
84 //  SelName = TCollection_AsciiString("AIS_Local_");
85   TCollection_AsciiString theind(anIndex);
86   SelName += "_";
87   SelName += theind;
88 #endif
89   return SelName;
90 }
91
92
93 //=======================================================================
94 //function : AIS_LocalContext
95 //purpose  : 
96 //=======================================================================
97
98
99 AIS_LocalContext::AIS_LocalContext(){}
100
101 AIS_LocalContext::AIS_LocalContext(const Handle(AIS_InteractiveContext)& aCtx,
102                                    const Standard_Integer Index,
103                                    const Standard_Boolean LoadDisplayed,
104                                    const Standard_Boolean AcceptStandardModes,
105                                    const Standard_Boolean AcceptEraseOfTemp,
106                                    const Standard_Boolean BothViewers):
107 myCTX(aCtx),
108 myLoadDisplayed(LoadDisplayed),
109 myAcceptStdMode(AcceptStandardModes),
110 myAcceptErase(AcceptEraseOfTemp),
111 mySM(aCtx->SelectionManager()),
112 myMainVS(new StdSelect_ViewerSelector3d(aCtx->MainSelector()->Projector())),
113 myFilters(new SelectMgr_OrFilter()),
114 myAutoHilight(Standard_True),
115 mylastindex(0),
116 mylastgood(0),
117 myCurDetected(0)
118 #ifdef IMP160701
119 ,myAISCurDetected(0)
120 #endif
121 {
122   // bind self to AIS_InteractiveContext::myLocalContexts. Further, the
123   // constructor executes logic that implies that the context is already
124   // created and mapped.
125   aCtx->myLocalContexts.Bind (Index, this);
126
127   myMainPM = aCtx->MainPrsMgr();
128   mySelName = AIS_Local_SelName(this, Index);
129   AIS_Selection::CreateSelection(mySelName.ToCString());
130
131   mySM->Add(myMainVS);
132   if(myLoadDisplayed) LoadContextObjects();
133   Process(Standard_False);
134
135 }
136
137
138 //=======================================================================
139 //function : SetContext
140 //purpose  : 
141 //=======================================================================
142
143 void AIS_LocalContext::SetContext(const Handle(AIS_InteractiveContext)& aCtx)
144 {  myCTX = aCtx;}
145
146 //=======================================================================
147 //function : Display
148 //purpose  : 
149 //=======================================================================
150
151 Standard_Boolean AIS_LocalContext::Display(const Handle(AIS_InteractiveObject)& anInteractive,
152                                            const Standard_Integer WhichMode,
153                                            const Standard_Boolean AllowShapeDecomposition,
154                                            const Standard_Integer ActivationMode)
155 {
156   if(myActiveObjects.IsBound(anInteractive)){
157     const Handle(AIS_LocalStatus)& STAT = myActiveObjects(anInteractive);
158     
159     if(STAT->DisplayMode() == -1){
160       if(!myMainPM->IsDisplayed(anInteractive,WhichMode))
161         myMainPM->Display(anInteractive,WhichMode);
162       if(STAT->IsTemporary())
163         STAT->SetDisplayMode(WhichMode);
164     }
165     else if(STAT->DisplayMode()!=WhichMode && STAT->IsTemporary()){
166       myMainPM->Erase(anInteractive,STAT->DisplayMode());
167       STAT->SetDisplayMode(WhichMode);
168       if(!myMainPM->IsDisplayed(anInteractive,WhichMode))
169         myMainPM->Display(anInteractive,WhichMode);
170     }
171     
172     if(ActivationMode!=-1){
173       if(!STAT->IsActivated(ActivationMode)){
174         STAT->ClearSelectionModes();
175         mySM->Load(anInteractive,myMainVS);
176         STAT->AddSelectionMode(ActivationMode);
177         mySM->Activate(anInteractive,ActivationMode,myMainVS);
178       }
179     }
180   }
181   else {
182     Handle(AIS_LocalStatus) Att = new AIS_LocalStatus();
183     
184     if(anInteractive->AcceptShapeDecomposition() && AllowShapeDecomposition)
185       Att->SetDecomposition(Standard_True);
186     else 
187       Att->SetDecomposition(Standard_False);
188     // status temporary or not
189     if(myCTX->DisplayStatus(anInteractive) == AIS_DS_None ||
190        myCTX->DisplayStatus(anInteractive) == AIS_DS_Temporary)
191       Att->SetTemporary(Standard_True);
192     else
193       Att->SetTemporary(Standard_False); 
194
195
196     
197     if(!myCTX->IsDisplayed(anInteractive,WhichMode)){
198       
199       //storing information....
200       Att->SetDisplayMode(WhichMode);
201       if (ActivationMode!=-1)
202         Att->AddSelectionMode(ActivationMode);
203       Standard_Integer HiMod = anInteractive->HasHilightMode()? anInteractive->HilightMode(): WhichMode;
204       Att->SetHilightMode(HiMod);
205
206       if(!myMainPM->IsDisplayed(anInteractive,WhichMode))
207         myMainPM->Display(anInteractive,WhichMode);
208       
209       if(ActivationMode!=-1){
210         mySM->Load(anInteractive,myMainVS);
211         mySM->Activate(anInteractive,ActivationMode,myMainVS);
212       }
213     }
214     else{
215       Standard_Integer HiMod = anInteractive->HasHilightMode()? anInteractive->HilightMode(): WhichMode;
216       Att->SetHilightMode(HiMod);
217     }
218     myActiveObjects.Bind(anInteractive,Att);
219   }  
220   Process(anInteractive);
221
222   
223   
224
225   return Standard_True;
226 }
227
228 //=======================================================================
229 //function : Load
230 //purpose  : 
231 //=======================================================================
232
233 Standard_Boolean AIS_LocalContext::
234 Load(const Handle(AIS_InteractiveObject)& anInteractive,
235      const Standard_Boolean AllowShapeDecomposition,
236      const Standard_Integer ActivationMode)
237 {
238   if(myActiveObjects.IsBound(anInteractive)) return Standard_False;
239   Handle(AIS_LocalStatus) Att = new AIS_LocalStatus();
240   
241   if(anInteractive->AcceptShapeDecomposition() && AllowShapeDecomposition)
242     Att->SetDecomposition(Standard_True);
243   else 
244     Att->SetDecomposition(Standard_False);
245   
246   if(!myCTX->IsDisplayed(anInteractive))
247     Att->SetTemporary(Standard_True);
248   else
249     Att->SetTemporary(Standard_False);
250   Att->SetDisplayMode(-1);
251   
252   //storing information....
253   if(ActivationMode!=-1)
254     Att->AddSelectionMode(ActivationMode);
255   Standard_Integer HiMod = anInteractive->HasHilightMode()? anInteractive->HilightMode():0;
256   Att->SetHilightMode(HiMod);
257   //Action
258   
259   mySM->Load(anInteractive,myMainVS);
260   if(ActivationMode != -1){
261     mySM->Activate(anInteractive,ActivationMode,myMainVS);
262   }
263   myActiveObjects.Bind(anInteractive,Att);
264   Process(anInteractive);
265   return Standard_True;
266 }
267
268 //=======================================================================
269 //function : ClearPrs
270 //purpose  : 
271 //=======================================================================
272
273 Standard_Boolean AIS_LocalContext::
274 ClearPrs(const Handle(AIS_InteractiveObject)& anInteractive,
275          const Standard_Integer aMode)
276 {
277   if(!myActiveObjects.IsBound(anInteractive))
278     return Standard_False;
279
280   Standard_Boolean jobdone(Standard_False);
281   const Handle(AIS_LocalStatus)& STAT = myActiveObjects(anInteractive);
282   
283   //Display step
284   if(STAT->IsSubIntensityOn()) {
285     STAT->SubIntensityOff();
286     if(STAT->HilightMode()==aMode)
287       myMainPM->Unhighlight(anInteractive,STAT->HilightMode());
288   }
289   myMainPM->Clear(anInteractive,aMode); // correction connexions 23/09/97
290   jobdone = Standard_True;
291   if(STAT->DisplayMode()==aMode)
292     STAT->SetDisplayMode(-1);
293   return jobdone;
294 }
295 //=======================================================================
296 //function : Erase
297 //purpose  : 
298 //=======================================================================
299
300 Standard_Boolean AIS_LocalContext::
301 Erase(const Handle(AIS_InteractiveObject)& anInteractive)
302 {
303   if(!myActiveObjects.IsBound(anInteractive))
304     return Standard_False;
305   const Handle(AIS_LocalStatus)& STAT = myActiveObjects(anInteractive);
306   
307   //Display step
308   if(STAT->IsSubIntensityOn()) {
309     STAT->SubIntensityOff();
310     myMainPM->Unhighlight(anInteractive,STAT->HilightMode());
311   }
312
313   Standard_Boolean status(Standard_False);
314
315   if(STAT->DisplayMode()!=-1) {
316     if(IsSelected(anInteractive))
317       AddOrRemoveSelected(anInteractive);
318     if(myMainPM->IsHighlighted(anInteractive,STAT->HilightMode()))
319       myMainPM->Unhighlight(anInteractive,STAT->HilightMode());
320     myMainPM->Erase(anInteractive,STAT->DisplayMode());
321     STAT->SetDisplayMode(-1);
322     status = Standard_True;
323   }
324   if(STAT->IsTemporary()){
325     if(myMainPM->IsDisplayed(anInteractive,STAT->HilightMode()))
326       myMainPM->Erase(anInteractive,STAT->HilightMode());
327   }
328   //selection step
329   
330   TColStd_ListIteratorOfListOfInteger It(STAT->SelectionModes());
331   for(;It.More();It.Next())
332     mySM->Deactivate(anInteractive,It.Value(),myMainVS);
333   //  STAT->ClearSelectionModes();
334   return status;
335 }
336
337
338 //=======================================================================
339 //function : SetShapeDecomposition
340 //purpose  : 
341 //=======================================================================
342
343 void AIS_LocalContext::SetShapeDecomposition(const Handle(AIS_InteractiveObject)& aStoredObject, 
344                                                 const Standard_Boolean aStatus)
345 {
346   if(!myActiveObjects.IsBound(aStoredObject)) return;
347   
348   if(aStatus == myActiveObjects(aStoredObject)->Decomposed()) 
349     return;
350   
351   myActiveObjects(aStoredObject)->SetDecomposition(aStatus);
352
353   Process(aStoredObject);
354 }
355
356 //=======================================================================
357 //function : Clear
358 //purpose  : 
359 //=======================================================================
360
361 void AIS_LocalContext::Clear(const AIS_ClearMode aType)
362 {
363   switch (aType){
364   case AIS_CM_All:
365     {
366       ClearObjects();
367       myFilters->Clear();
368       while(!myListOfStandardMode.IsEmpty())
369         DeactivateStandardMode(AIS_Shape::SelectionType(myListOfStandardMode.Last()));
370       break;
371     }
372   case AIS_CM_Interactive:
373     ClearObjects();
374     break;
375   case AIS_CM_Filters:
376     myFilters->Clear();
377     break;
378   case AIS_CM_StandardModes:
379     {
380       while(!myListOfStandardMode.IsEmpty())
381         DeactivateStandardMode(AIS_Shape::SelectionType(myListOfStandardMode.Last()));
382       break;
383     }
384   case AIS_CM_TemporaryShapePrs:
385     ClearDetected();
386   }
387   UpdateSort();
388 }
389 //=======================================================================
390 //function : ActivateMode
391 //purpose  : 
392 //=======================================================================
393
394 void AIS_LocalContext::ActivateMode(const Handle(AIS_InteractiveObject)& aSelectable,
395                                        const Standard_Integer aMode)
396 {
397   if(!myActiveObjects.IsBound(aSelectable)) return;
398 //  if(myActiveObjects(aSelectable)->SelectionMode()!=aMode)
399 //    mySM->Deactivate(aSelectable,aMode,myMainVS);
400   if(aMode != -1){
401     myActiveObjects(aSelectable)->AddSelectionMode(aMode);
402     mySM->Activate(aSelectable,aMode,myMainVS);
403   }
404   UpdateSort();
405 }
406 //=======================================================================
407 //function : ActivateMode
408 //purpose  : 
409 //=======================================================================
410
411 void AIS_LocalContext::DeactivateMode(const Handle(AIS_InteractiveObject)& aSelectable,
412                                          const Standard_Integer aMode)
413 {
414   if(!myActiveObjects.IsBound(aSelectable)) return;
415   
416   if(aMode==-1) return;
417   
418   myActiveObjects(aSelectable)->RemoveSelectionMode(aMode);
419   mySM->Deactivate(aSelectable,aMode,myMainVS);
420   UpdateSort();
421   
422 }
423 //=======================================================================
424 //function : ActivateMode
425 //purpose  : 
426 //=======================================================================
427
428 void AIS_LocalContext::Deactivate(const Handle(AIS_InteractiveObject)& aSelectable)
429 {
430   if(!myActiveObjects.IsBound(aSelectable)) return;
431   
432   mySM->Deactivate(aSelectable,myMainVS);
433   myActiveObjects(aSelectable)->ClearSelectionModes();
434   UpdateSort();
435 }
436
437 //=======================================================================
438 //function : Remove
439 //purpose  : 
440 //=======================================================================
441
442 Standard_Boolean AIS_LocalContext::Remove(const Handle(AIS_InteractiveObject)& aSelectable)
443 {
444   if(!myActiveObjects.IsBound(aSelectable)) return Standard_False;
445
446   if(IsSelected(aSelectable))
447     AddOrRemoveSelected(aSelectable,Standard_False);
448     
449   const Handle(AIS_LocalStatus)& Att = myActiveObjects(aSelectable);
450   
451   TColStd_ListIteratorOfListOfInteger It;
452   Standard_Boolean jobdone(Standard_False);
453   // it is checked which were the temporary attributes 
454   // and they are set to 0
455
456   // desactivate standard modes
457   if(Att->Decomposed()){
458     for(It.Initialize(myListOfStandardMode);It.More();It.Next()){
459       mySM->Deactivate(aSelectable,It.Value(),myMainVS);
460     }
461   }
462   
463   // if object or temporary presentations...
464   if(Att->IsTemporary())
465     {
466       if(Att->IsSubIntensityOn())
467         myMainPM->Unhighlight(aSelectable,Att->HilightMode());
468       
469       // remove if bug on clear correct...
470       myMainPM->Erase(aSelectable,Att->DisplayMode());
471       myMainPM->Clear(aSelectable,Att->DisplayMode());
472       if(myMainPM->IsDisplayed(aSelectable,Att->HilightMode()))
473         myMainPM->Erase(aSelectable,Att->HilightMode());
474       //        myMainPM->Clear(aSelectable,Att->HilightMode());
475       jobdone = Standard_True;
476     }
477   // if below intensity
478   else
479     {
480       if(Att->IsSubIntensityOn())
481         myCTX->SubIntensityOff(aSelectable);
482     }
483   // desactivate stored proper modes
484   for(It.Initialize(Att->SelectionModes());It.More();It.Next()){
485     mySM->Deactivate(aSelectable,It.Value(),myMainVS);
486   }
487 // pop : si je laisses cela plantes dans les elements de construction  
488 //       alors a toi de jouer ROB
489 //  RemoveSelected(aSelectable);
490
491   if(IsSelected(aSelectable))
492     AddOrRemoveSelected(aSelectable);
493   myActiveObjects.UnBind(aSelectable);
494
495   //Last detected object keeps for lastindex initialization.
496   Handle(SelectMgr_EntityOwner) aLastPicked = myMainVS->OnePicked();
497
498   UpdateSort();
499
500   //Object removes from SelectMgr
501   if( mySM->Contains(aSelectable) )
502     mySM->Remove(aSelectable);
503
504   //Object removes from Detected sequence
505   AIS_SequenceOfInteractive detectAIS;
506
507   Standard_Integer i = 1;
508   for(i = 1 ; i < myAISDetectedSeq.Length(); i++)
509   {
510     Handle(AIS_InteractiveObject) anObj = DetectedCurrentObject();
511     if( !anObj.IsNull() && anObj != aSelectable )
512       myAISDetectedSeq.Remove( i );
513   }
514
515   Standard_Integer aHM = aSelectable->HasHilightMode() ? aSelectable->HilightMode() : 0;
516
517   //EntityOwners remove from AIS_Selection
518   Handle(AIS_Selection) aSel = AIS_Selection::Selection(mySelName.ToCString());
519   AIS_NListTransient::Iterator anIter(aSel->Objects()); 
520   AIS_NListTransient removeEntites;
521   for(; anIter.More(); anIter.Next()){
522     const Handle(Standard_Transient)& Tr = anIter.Value();
523     if (!Tr.IsNull()){
524       const Handle(SelectMgr_EntityOwner)& anOwnr = *((const Handle(SelectMgr_EntityOwner)*) &Tr);
525       if(anOwnr->Selectable() == aSelectable){
526         removeEntites.Append(Tr);
527         if(IsSelected(anOwnr))
528           anOwnr->Unhilight(myMainPM, aHM);//Unhilight selected
529       }
530     }
531   }
532   AIS_NListTransient::Iterator anIterRemove(removeEntites); 
533   for(; anIterRemove.More(); anIterRemove.Next())
534     aSel->Select(anIterRemove.Value());//EntityOwner removes from the selection data
535
536   //EntityOwners remove from myMapOfOwner
537   SelectMgr_IndexedMapOfOwner ownersToKeep; 
538   const Handle(V3d_Viewer)& aViewer = myCTX->CurrentViewer();
539   for(i = 1; i <= myMapOfOwner.Extent(); i++){
540     const Handle(SelectMgr_EntityOwner)& anOwner = myMapOfOwner(i) ;
541     if(!anOwner.IsNull())
542       if(anOwner->Selectable() != aSelectable)
543         ownersToKeep.Add(anOwner);
544       else
545       {
546         if(anOwner->IsHilighted(myMainPM, aHM))
547         {
548           for(aViewer->InitActiveViews(); aViewer->MoreActiveViews(); aViewer->NextActiveViews())
549             Unhilight(anOwner, aViewer->ActiveView());
550         }
551       }
552   }
553   myMapOfOwner.Clear();
554   myMapOfOwner.Assign(ownersToKeep);
555   mylastindex = myMapOfOwner.FindIndex(aLastPicked);
556
557   return Standard_True;
558 }
559
560 //=======================================================================
561 //function : ActivateStandardMode
562 //purpose  : 
563 //=======================================================================
564
565 void AIS_LocalContext::ActivateStandardMode(const TopAbs_ShapeEnum aType)
566 {
567   
568   //check if it is not in the list
569   TColStd_ListIteratorOfListOfInteger It(myListOfStandardMode);
570   for(;It.More();It.Next())
571     if(It.Value()==aType)  return;
572   Standard_Integer IMode = AIS_Shape::SelectionMode(aType);
573   
574
575   // create a hidden filter answering ok to the type except for :
576   // if the type is shape...
577   // if the filters already impact at the type <aType>
578   if(aType != TopAbs_SHAPE){
579     if(myStdFilters[IMode].IsNull())
580       myStdFilters[IMode] = new StdSelect_ShapeTypeFilter(aType);
581     if(!HasFilters(aType))
582       myFilters->Add(myStdFilters[IMode]);
583   }
584   
585   // the mode is activated for all objects of type Shape 
586   // accepting the decomposition in standard mode.
587   myListOfStandardMode.Append(IMode);
588   
589   AIS_DataMapIteratorOfDataMapOfSelStat ItM(myActiveObjects);
590
591   for(;ItM.More();ItM.Next()){
592 #ifdef BUC60722
593     AIS_DisplayStatus DS = 
594         myCTX->DisplayStatus(Handle(AIS_InteractiveObject)::DownCast(ItM.Key()));
595     if( ItM.Value()->Decomposed() && (DS != AIS_DS_FullErased)  )
596 #else
597     if(ItM.Value()->Decomposed())
598 #endif
599       myCTX->SelectionManager()->Activate(ItM.Key(),
600                                           IMode,
601                                           myMainVS);
602   }
603   
604 }
605
606 //=======================================================================
607 //function : DeActivateStandardMode
608 //purpose  : 
609 //=======================================================================
610
611 void AIS_LocalContext::DeactivateStandardMode(const TopAbs_ShapeEnum aType)
612 {
613   TColStd_ListIteratorOfListOfInteger It(myListOfStandardMode);
614   Standard_Integer IMode = AIS_Shape::SelectionMode(aType);
615   for(;It.More();It.Next())
616     if(It.Value()==IMode) {
617       AIS_DataMapIteratorOfDataMapOfSelStat ItM(myActiveObjects);
618       
619       for(;ItM.More();ItM.Next()){
620         if(ItM.Value()->Decomposed()){
621           myCTX->SelectionManager()->Deactivate(ItM.Key(),
622                                                 IMode,
623                                                 myMainVS);
624           ItM.Value()->RemoveSelectionMode(IMode);
625         }
626       }
627       myListOfStandardMode.Remove(It);
628       if(myFilters->IsIn(myStdFilters[IMode]))
629         myFilters->Remove(myStdFilters[IMode]);
630       UpdateSort();
631       return;
632     }   
633   UpdateSort();
634 }
635
636 //=======================================================================
637 //function : AddFilter
638 //purpose  : 
639 //=======================================================================
640
641 void AIS_LocalContext::AddFilter(const Handle(SelectMgr_Filter)& aFilter)
642 {
643   // it is checked if the filter impacts at the type of active sub-shape 
644   // for which a filter of type has been already implemented...
645
646   TColStd_ListIteratorOfListOfInteger It(myListOfStandardMode);
647   
648   for(;It.More();It.Next()){
649     if(aFilter->ActsOn(AIS_Shape::SelectionType(It.Value())))
650       if(myFilters->IsIn(myStdFilters[It.Value()]))
651         myFilters->Remove(myStdFilters[It.Value()]);
652   } 
653   myFilters->Add(aFilter);
654 }
655
656 //=======================================================================
657 //function : RemoveFilter
658 //purpose  : 
659 //=======================================================================
660
661 void AIS_LocalContext::RemoveFilter(const Handle(SelectMgr_Filter)& aFilter)
662 {
663   if(myFilters->IsIn(aFilter)) myFilters->Remove(aFilter);
664   
665   // it is checked if the filter for type standard is active.
666   // if yes, it is checked there are still similarities among the
667   // remaining filters...
668   //     otherwise, the standard filter is restored to
669   //     continu selecting active modes...
670   TColStd_ListIteratorOfListOfInteger It(myListOfStandardMode);
671   TopAbs_ShapeEnum SE;
672   for(;It.More();It.Next()){
673     SE = AIS_Shape::SelectionType(It.Value());
674     if(aFilter->ActsOn(SE))
675       if(!HasFilters(SE))
676         myFilters->Add(myStdFilters[It.Value()]);
677   }
678 }
679
680
681
682 Standard_Boolean AIS_LocalContext::HasSameProjector(const Handle(Select3D_Projector)& thePrj) const
683 {
684   const Handle(Select3D_Projector)& aCurPrj = myMainVS->Projector();
685   if (aCurPrj->Perspective() != thePrj->Perspective())
686     return Standard_False;  
687   if (aCurPrj->Perspective() && aCurPrj->Focus() != thePrj->Focus())
688     return Standard_False;
689   const gp_GTrsf& aCurTrsf = aCurPrj->Transformation();
690   const gp_GTrsf& aPrjTrsf = thePrj->Transformation();
691
692   for (Standard_Integer i = 1; i <= 3; ++i)
693   {
694     for (Standard_Integer j = 1; j <= 3 ; ++j)
695     {
696       if (aCurTrsf.Value (i, j) != aPrjTrsf.Value (i, j))
697         return Standard_False;
698     }
699   }
700
701   return Standard_True;
702 }
703
704
705 //=======================================================================
706 //function : Terminate
707 //purpose  : 
708 //=======================================================================
709
710 void AIS_LocalContext::Terminate( const Standard_Boolean updateviewer )
711 {
712   ClearDetected();
713   Clear();
714   myMapOfOwner.Clear();
715   
716   mylastindex=0;
717   // clear the selector...
718   myMainVS->Clear();
719   myCTX->SelectionManager()->Remove(myMainVS);
720   
721
722   AIS_Selection::SetCurrentSelection(mySelName.ToCString());
723   Handle(AIS_Selection) S = AIS_Selection::CurrentSelection();
724   Handle(Standard_Transient) Tr;
725   for(S->Init();S->More();S->Next()){
726     Tr = S->Value();
727     (*((Handle(SelectMgr_EntityOwner)*)&Tr))->State(0);
728   }
729
730       
731   AIS_Selection::Select();
732   AIS_Selection::Remove(mySelName.ToCString());
733
734   // CLE
735   // const Handle(V3d_Viewer)& Vwr = myCTX->CurrentViewer();
736   Handle(V3d_Viewer) Vwr = myCTX->CurrentViewer();
737   // ENDCLE
738   Handle(V3d_View) curV;
739   for(Vwr->InitActiveViews();Vwr->MoreActiveViews();Vwr->NextActiveViews()){
740     curV = Vwr->ActiveView(); 
741     Visual3d_TransientManager::ClearDraw( curV->View(), updateviewer );
742   }
743
744
745 #ifdef DEB
746   Handle(V3d_View) BidV;
747   myMainVS->ClearAreas(BidV);
748   myMainVS->ClearSensitive(BidV);
749   
750 #endif
751 }
752
753
754 //=======================================================================
755 //function : SubIntensity
756 //purpose  : 
757 //=======================================================================
758
759 void AIS_LocalContext::SubIntensityOn(const Handle(AIS_InteractiveObject)& anObject)
760 {
761   if(!myActiveObjects.IsBound(anObject)) return;
762   
763   const Handle(AIS_LocalStatus)& Att = myActiveObjects(anObject);
764
765   if(Att->IsTemporary()) 
766     myMainPM->Color(anObject,myCTX->SubIntensityColor(),Att->DisplayMode());
767   
768   Att->SubIntensityOn();
769 }
770 //=======================================================================
771 //function : SubIntensity
772 //purpose  : 
773 //=======================================================================
774
775 void AIS_LocalContext::SubIntensityOff(const Handle(AIS_InteractiveObject)& anObject)
776 {
777   if(!myActiveObjects.IsBound(anObject)) return;
778   
779   const Handle(AIS_LocalStatus)& Att = myActiveObjects(anObject);
780
781   if(Att->IsTemporary()) 
782     myMainPM->Unhighlight(anObject);
783   Att->SubIntensityOff();
784 }
785
786
787 //=======================================================================
788 //function : Hilight
789 //purpose  : 
790 //=======================================================================
791
792 void AIS_LocalContext::Hilight(const  Handle(AIS_InteractiveObject)& anObject)
793 {
794   if(!myActiveObjects.IsBound(anObject)){
795     Standard_Integer HiMod = anObject->HasHilightMode()? anObject->HilightMode() : 0; 
796     Handle(AIS_LocalStatus) Att = new AIS_LocalStatus(Standard_True,
797                                                       Standard_False,
798                                                       -1,-1,HiMod);
799     myActiveObjects.Bind(anObject,Att);
800     
801   }
802   const Handle(AIS_LocalStatus)& Att = myActiveObjects(anObject);
803   myMainPM->Color(anObject,myCTX->HilightColor(),Att->HilightMode());
804   Att->SubIntensityOn();
805 }
806 //=======================================================================
807 //function : Hilight
808 //purpose  : 
809 //=======================================================================
810
811 void AIS_LocalContext::Hilight(const  Handle(AIS_InteractiveObject)& anObject,
812                                const Quantity_NameOfColor Col)
813 {
814   if(!myActiveObjects.IsBound(anObject)){
815     Standard_Integer HiMod = anObject->HasHilightMode()? anObject->HilightMode() : 0; 
816     Handle(AIS_LocalStatus) Att = new AIS_LocalStatus(Standard_True,
817                                                       Standard_False,
818                                                       -1,-1,HiMod);
819     myActiveObjects.Bind(anObject,Att);
820     
821   }
822   const Handle(AIS_LocalStatus)& Att = myActiveObjects(anObject);
823   myMainPM->Color(anObject,Col,Att->HilightMode());
824   Att->SubIntensityOn();
825   Att->SetHilightColor(Col);
826 }
827
828 //=======================================================================
829 //function : Unhilight
830 //purpose  : 
831 //=======================================================================
832
833 void AIS_LocalContext::Unhilight(const Handle(AIS_InteractiveObject)& anObject)
834 {
835   if(!myActiveObjects.IsBound(anObject)) return;
836   
837   // chieck if by hazard the object is somewhere else...
838   Standard_Integer Indx;
839   Standard_Boolean IsSomeWhereElse  = 
840     myCTX->IsInLocal(anObject,Indx) && Indx != myCTX->IndexOfCurrentLocal();
841   
842   const Handle(AIS_LocalStatus)& Att = myActiveObjects(anObject);
843   myMainPM->Unhighlight(anObject,Att->HilightMode());
844   if(Att->IsTemporary() && Att->DisplayMode()==-1)
845     if(!IsSomeWhereElse)
846       myMainPM->Erase(anObject,Att->HilightMode());
847   
848   Att->SubIntensityOff();
849   Att->SetHilightColor(Quantity_NOC_WHITE);
850 }
851
852
853 //=======================================================================
854 //function : IsIn
855 //purpose  : 
856 //=======================================================================
857
858 Standard_Boolean AIS_LocalContext::
859 IsIn(const Handle(AIS_InteractiveObject)& anObject) const 
860 {
861   return myActiveObjects.IsBound(anObject);
862 }
863
864 //=======================================================================
865 //function : IsHilighted
866 //purpose  : 
867 //=======================================================================
868
869 Standard_Boolean AIS_LocalContext::IsHilighted(const Handle(AIS_InteractiveObject)& anObject) const 
870 {
871   if(!myActiveObjects.IsBound(anObject)) return Standard_False;
872   return myActiveObjects(anObject)->IsSubIntensityOn();
873 }
874
875 Standard_Boolean AIS_LocalContext::IsHilighted(const Handle(AIS_InteractiveObject)& anObject,
876                                                Standard_Boolean& WithColor,
877                                                Quantity_NameOfColor& HiCol) const 
878 {
879   if(!myActiveObjects.IsBound(anObject)) return Standard_False;
880   if( myActiveObjects(anObject)->IsSubIntensityOn()){
881     HiCol = myActiveObjects(anObject)->HilightColor();
882     if(HiCol==Quantity_NOC_WHITE)
883       WithColor = Standard_True;
884     else
885       WithColor = Standard_False;
886     return Standard_True;
887   }
888   return Standard_False;
889 }
890
891
892 void AIS_LocalContext::SetDisplayPriority(const Handle(AIS_InteractiveObject)& anObject,
893                                           const Standard_Integer Prior)
894 {
895   if(!myActiveObjects.IsBound(anObject)) return;
896   const Handle(AIS_LocalStatus)& STAT = myActiveObjects(anObject);
897   if(STAT->DisplayMode()==-1) return;
898   myMainPM->SetDisplayPriority(anObject,STAT->DisplayMode(),Prior);
899   if(STAT->IsSubIntensityOn())
900     myMainPM->SetDisplayPriority(anObject,STAT->HilightMode(),Prior);
901   
902   
903 }
904
905 //=======================================================================
906 //function : DisplayedObjects
907 //purpose  : 
908 //=======================================================================
909 Standard_Integer AIS_LocalContext::DisplayedObjects(TColStd_MapOfTransient& theMap) const
910 {
911   Standard_Integer NbDisp(0);
912   for(AIS_DataMapIteratorOfDataMapOfSelStat it(myActiveObjects);it.More();it.Next()){
913     const Handle(SelectMgr_SelectableObject)& SO = it.Key();
914     if(!theMap.Contains(SO))
915       if(it.Value()->DisplayMode()!=-1){
916         theMap.Add(SO);
917         NbDisp++;
918       }
919   }
920   return NbDisp;
921 }
922
923
924 //=======================================================================
925 //function : IsDisplayed
926 //purpose  : 
927 //=======================================================================
928
929 Standard_Boolean AIS_LocalContext::IsDisplayed(const Handle(AIS_InteractiveObject)& anObject) const 
930 {
931   if(!myActiveObjects.IsBound(anObject)) return Standard_False;
932   return (myActiveObjects(anObject)->DisplayMode()!=-1);
933 }
934
935 //=======================================================================
936 //function : IsDisplayed
937 //purpose  : 
938 //=======================================================================
939
940 Standard_Boolean AIS_LocalContext::IsDisplayed(const Handle(AIS_InteractiveObject)& anObject,
941                                                   const Standard_Integer aMode) const 
942 {
943   if(!myActiveObjects.IsBound(anObject)) return Standard_False;
944   return (myActiveObjects(anObject)->DisplayMode()==aMode);
945 }
946
947 //=======================================================================
948 //function : SelectionModes
949 //purpose  : 
950 //=======================================================================
951
952 const TColStd_ListOfInteger& AIS_LocalContext::
953 SelectionModes(const Handle(AIS_InteractiveObject)& anObject) const 
954 {
955   return myActiveObjects(anObject)->SelectionModes(); 
956 }
957
958 //=======================================================================
959 //function : Status
960 //purpose  : 
961 //=======================================================================
962
963 TCollection_AsciiString AIS_LocalContext::Status() const 
964 {
965   TCollection_AsciiString t;
966   return t;
967 }
968
969 const Handle(AIS_LocalStatus)& AIS_LocalContext::Status(const Handle(AIS_InteractiveObject)& anObject) const 
970 {
971   return myActiveObjects(anObject);
972 }
973
974 //=======================================================================
975 //function : LoadContextObjects
976 //purpose  : 
977 //=======================================================================
978
979 void AIS_LocalContext::LoadContextObjects()
980 {
981   AIS_ListIteratorOfListOfInteractive It;
982   if(myLoadDisplayed) {
983     AIS_ListOfInteractive LL;
984     myCTX->DisplayedObjects(LL,Standard_True);
985     Handle(AIS_LocalStatus) Att;
986     for (It.Initialize(LL);It.More();It.Next()){
987       Att= new AIS_LocalStatus();
988       Att->SetDecomposition((It.Value()->AcceptShapeDecomposition() && myAcceptStdMode));
989       Att->SetTemporary(Standard_False);
990       Att->SetHilightMode(It.Value()->HasHilightMode()? It.Value()->HilightMode(): 0);
991       
992       myActiveObjects.Bind(It.Value(),Att);
993     }
994   }
995 }
996
997 void AIS_LocalContext::UnloadContextObjects()
998 {
999   AIS_ListIteratorOfListOfInteractive It;
1000   if(myLoadDisplayed) 
1001   {
1002     AIS_ListOfInteractive LL;
1003     myCTX->DisplayedObjects(LL,Standard_True);
1004     
1005     for (It.Initialize(LL);It.More();It.Next())
1006     {
1007       myActiveObjects.UnBind(It.Value());
1008     }
1009   }
1010 }
1011 //=======================================================================
1012 //function : Process
1013 //purpose  : 
1014 //=======================================================================
1015
1016 void AIS_LocalContext::Process(const Handle(SelectMgr_SelectableObject)& anObject,
1017                                const Standard_Boolean WithProj)
1018
1019   if(!myActiveObjects.IsBound(anObject)) return;
1020   if(myActiveObjects(anObject)->Decomposed())
1021     ActivateStandardModes(anObject,WithProj);
1022   else
1023     {
1024       TColStd_ListIteratorOfListOfInteger It(myActiveObjects(anObject)->SelectionModes());
1025       for(;It.More();It.Next())
1026         myCTX->SelectionManager()->Activate(anObject,It.Value(),myMainVS,WithProj);
1027     }
1028 }
1029
1030 //=======================================================================
1031 //function : Process
1032 //purpose  : 
1033 //=======================================================================
1034
1035 void AIS_LocalContext::Process(const Standard_Boolean WithProj)
1036
1037
1038   myMainVS->Clear();
1039   
1040   AIS_DataMapIteratorOfDataMapOfSelStat It(myActiveObjects);
1041   
1042   for(;It.More();It.Next()){
1043     myCTX->SelectionManager()->Load(It.Key(),myMainVS);
1044     if(It.Value()->Decomposed()) 
1045       ActivateStandardModes(It.Key(),WithProj);
1046     else if( myCTX->GetAutoActivateSelection() )
1047     {
1048       It.Value()->AddSelectionMode(0);
1049       myCTX->SelectionManager()->Activate(It.Key(),0,myMainVS,WithProj);
1050     }
1051   }
1052
1053 }
1054
1055 //=======================================================================
1056 //function : ActivateModes
1057 //purpose  : 
1058 //=======================================================================
1059
1060 void AIS_LocalContext::ActivateStandardModes(const Handle(SelectMgr_SelectableObject)& anObject,
1061                                              const Standard_Boolean WithProj)
1062
1063   if(!myActiveObjects.IsBound(anObject)) return;
1064   
1065   TColStd_ListIteratorOfListOfInteger itl (myListOfStandardMode);
1066
1067   const Handle(AIS_LocalStatus)&  LS = myActiveObjects(anObject);
1068   if(LS->Decomposed()){
1069     for(;itl.More();itl.Next()){
1070       myCTX->SelectionManager()->Activate(anObject,itl.Value(),myMainVS,WithProj);
1071       LS->AddSelectionMode(itl.Value());
1072     }
1073   }
1074 }
1075
1076
1077 //=======================================================================
1078 //function : ClearObjects
1079 //purpose  : 
1080 //=======================================================================
1081
1082 void AIS_LocalContext::ClearObjects()
1083 {
1084   AIS_DataMapIteratorOfDataMapOfSelStat It(myActiveObjects);
1085   for(;It.More();It.Next())
1086     {
1087       Handle(AIS_InteractiveObject) SO =
1088         Handle(AIS_InteractiveObject)::DownCast(It.Key());
1089       
1090       const Handle(AIS_LocalStatus)& CurAtt = It.Value();
1091       //TColStd_ListIteratorOfListOfInteger ItL;
1092       // if object is temporary the presentations managed by myMainPM are removed
1093       AIS_DisplayStatus TheDS = myCTX->DisplayStatus(SO);
1094       
1095       if(TheDS != AIS_DS_Displayed){
1096         if(myMainPM->IsDisplayed(SO,CurAtt->DisplayMode())){
1097           if(CurAtt->IsSubIntensityOn()&&
1098              myMainPM->IsHighlighted(SO,CurAtt->HilightMode()))
1099             myMainPM->Unhighlight(SO,CurAtt->HilightMode());
1100           myMainPM->Erase(SO,CurAtt->DisplayMode());
1101         }
1102         
1103         if(CurAtt->IsTemporary()){
1104           myMainPM->Erase(SO,CurAtt->DisplayMode());}
1105 //        myMainPM->Clear(SO,CurAtt->DisplayMode());}
1106       }
1107       else {
1108         if (CurAtt->IsSubIntensityOn()){
1109           myCTX->SubIntensityOff(Handle(AIS_InteractiveObject)::DownCast(SO));}
1110         Standard_Integer DiMo = SO->HasDisplayMode()?
1111           SO->DisplayMode():myCTX->DisplayMode();
1112         if(CurAtt->DisplayMode()!=-1 &&
1113            CurAtt->DisplayMode()!= DiMo)
1114           myMainPM->Erase(SO,CurAtt->DisplayMode());
1115       }
1116       
1117       TColStd_ListIteratorOfListOfInteger ITL(CurAtt->SelectionModes());
1118       for(;ITL.More();ITL.Next())
1119         mySM->Deactivate(SO,ITL.Value(),myMainVS);
1120       
1121       if(CurAtt->IsTemporary())
1122         mySM->Remove(SO,myMainVS);
1123       
1124     }
1125   ClearSelected( Standard_False );
1126   myActiveObjects.Clear();
1127 //  myMainVS->ClearAreas();myMainVS->ClearSensitive();
1128 }
1129
1130
1131 Standard_Boolean AIS_LocalContext::IsDecompositionOn() const 
1132 {return !myListOfStandardMode.IsEmpty();}
1133
1134
1135
1136
1137 //=======================================================================
1138 //function : HasAlreadyFilters
1139 //purpose  : 
1140 //=======================================================================
1141
1142 Standard_Boolean AIS_LocalContext::
1143 HasFilters(const TopAbs_ShapeEnum aType) const 
1144 {
1145   return myFilters->ActsOn(aType);
1146 }
1147
1148 void AIS_LocalContext::ClearDetected()
1149 {
1150   for(Standard_Integer I=1;I<=myMapOfOwner.Extent();I++){
1151     
1152     if(!myMapOfOwner(I).IsNull()){
1153       if(myMapOfOwner(I)->IsHilighted(myMainPM))
1154         myMapOfOwner(I)->Unhilight(myMainPM);
1155       else if (myMapOfOwner(I)->IsHilighted(myCTX->CollectorPrsMgr()))
1156         myMapOfOwner(I)->Unhilight(myCTX->CollectorPrsMgr());
1157       
1158       else{
1159         const Handle(SelectMgr_SelectableObject)& SO = 
1160           myMapOfOwner.FindKey(I)->Selectable();
1161         if(myActiveObjects.IsBound(SO)){
1162           const Handle(AIS_LocalStatus)& Att = myActiveObjects(SO);
1163           
1164           if(Att->IsTemporary() &&
1165              Att->DisplayMode()==-1 && 
1166              Att->SelectionModes().IsEmpty()){
1167             myMapOfOwner(I)->Clear(myMainPM);
1168             //myMapOfOwner(I)->Clear();//rob-jmi...
1169           }
1170         }
1171       }
1172     }
1173   }
1174
1175 }
1176
1177 void AIS_LocalContext::UpdateConversion()
1178 {
1179   myMainVS->UpdateConversion();
1180 }
1181
1182 void AIS_LocalContext::UpdateSort()
1183 {
1184   myMainVS->UpdateSort();
1185 }
1186
1187
1188
1189 //=======================================================================
1190 //function : IMMEDIATE MODE
1191 //purpose  : 
1192 //=======================================================================
1193
1194 Standard_Boolean  AIS_LocalContext::BeginImmediateDraw()
1195 {
1196   if(myMainPM->IsImmediateModeOn()){
1197     myMainPM->BeginDraw();
1198     return Standard_True;
1199   }
1200   return Standard_False;
1201 }
1202
1203
1204 Standard_Boolean AIS_LocalContext::ImmediateAdd(const Handle(AIS_InteractiveObject)& anIObj,
1205                                                       const Standard_Integer aMode)
1206 {
1207   if(!myMainPM->IsImmediateModeOn())
1208     return Standard_False;
1209   myMainPM->Add(anIObj,aMode);
1210   return Standard_True;
1211 }
1212
1213 Standard_Boolean AIS_LocalContext::ImmediateRemove(const Handle(AIS_InteractiveObject)& anIObj,
1214                                                    const Standard_Integer aMode)
1215 {
1216   if(!myMainPM->IsImmediateModeOn())   return Standard_False;
1217   myMainPM->Remove(anIObj,aMode);
1218   return Standard_True;
1219 }
1220
1221 Standard_Boolean AIS_LocalContext::EndImmediateDraw(const Handle(V3d_View)& aView,
1222                                                           const Standard_Boolean DoubleBuf)
1223 {
1224   if(!myMainPM->IsImmediateModeOn()) return Standard_False;
1225   myMainPM->EndDraw(aView,DoubleBuf);
1226   return Standard_True;
1227 }
1228
1229 Standard_Boolean AIS_LocalContext::IsImmediateModeOn() const
1230 {return myMainPM->IsImmediateModeOn();}
1231
1232 void AIS_LocalContext::SetSensitivityMode(const StdSelect_SensitivityMode aMode) {
1233
1234   myMainVS->SetSensitivityMode(aMode);
1235 }
1236
1237 StdSelect_SensitivityMode AIS_LocalContext::SensitivityMode() const {
1238
1239   return myMainVS->SensitivityMode();
1240 }
1241
1242 void AIS_LocalContext::SetSensitivity(const Standard_Real aPrecision) {
1243
1244   myMainVS->SetSensitivity(aPrecision);
1245 }
1246
1247 Standard_Real AIS_LocalContext::Sensitivity() const {
1248
1249   return myMainVS->Sensitivity();
1250 }
1251
1252 void AIS_LocalContext::SetPixelTolerance(const Standard_Integer aPrecision) {
1253
1254   myMainVS->SetPixelTolerance(aPrecision);
1255 }
1256
1257 Standard_Integer AIS_LocalContext::PixelTolerance() const {
1258
1259   return myMainVS->PixelTolerance();
1260 }
1261
1262 //=======================================================================
1263 //function : SetZLayer
1264 //purpose  :
1265 //=======================================================================
1266
1267 void AIS_LocalContext::SetZLayer (const Handle(AIS_InteractiveObject)& theIObj,
1268                                   const Standard_Integer theLayerId)
1269 {
1270   if (!myActiveObjects.IsBound (theIObj)) 
1271     return;
1272
1273   const Handle(AIS_LocalStatus)& aStatus = myActiveObjects (theIObj);
1274   if (aStatus->DisplayMode () == -1)
1275     return;
1276
1277   theIObj->SetZLayer (myMainPM, theLayerId);
1278 }
1279
1280 //=======================================================================
1281 //function : GetZLayer
1282 //purpose  : 
1283 //=======================================================================
1284
1285 Standard_Integer AIS_LocalContext::GetZLayer (const Handle(AIS_InteractiveObject)& theIObj) const
1286 {
1287   if (!myActiveObjects.IsBound (theIObj)) 
1288     return -1;
1289
1290   return theIObj->GetZLayer (myMainPM);
1291 }