Integration of OCCT 6.5.0 from SVN
[occt.git] / src / AIS / AIS_Selection.cxx
CommitLineData
7fd59977 1#include <AIS_Selection.ixx>
2#include <TCollection_AsciiString.hxx>
3#include <TColStd_SequenceOfTransient.hxx>
4
5#define BUC60953 // SAV_050701 : the array of selected objects has always the same length
6 // independently of number of objects selected. Thus, if there were selected
7 // more than MaxSizeOfResult objects we have got an exception.
8 //
9 // Moreover, Select method was optimized a little bit.
10 // Now it checks the state of incoming owner. If the state is 0
11 // there is no searching for object in <myresult> array.
12
13#define OCC138
14
15#define OCC189 //SAV: 18//03/02 array was replaced with list.
16
17#define OCC1039 //SAV: 25/11/02 clearing selected objects if any on the AIS_Selection remove.
18
19#define USE_MAP //san : 18/04/03 USE_MAP - additional datamap is used to speed up access
20 //to certain owners in <myresult> list
21
22#ifdef BUC60953
23#include <SelectMgr_EntityOwner.hxx>
24#endif
25
26#ifdef OCC138 //VTN Avoding infinit loop in AddOrRemoveSelected and AddOrRemoveCurrentObject methods.
27#include <AIS_InteractiveObject.hxx>
28#endif
29
30#ifndef USE_MAP
31#define MaxSizeOfResult 10000
32#else
33#define MaxSizeOfResult 100000
34#endif
35
36// beurk mais moins qu''avant.... rob
37static void AIS_Sel_CurrentSelection (Handle(AIS_Selection)& InputSel)
38{
39 static Handle(AIS_Selection) theCurrentSelection;
40 if(!InputSel.IsNull())
41 theCurrentSelection = InputSel;
42 else
43 InputSel = theCurrentSelection;
44}
45
46static TColStd_SequenceOfTransient& AIS_Sel_GetSelections()
47{
48 static TColStd_SequenceOfTransient Selections;
49 return Selections;
50}
51
52//=======================================================================
53//function : AIS_Selection
54//purpose :
55//=======================================================================
56AIS_Selection::AIS_Selection(const Standard_CString aName) :
57myName(TCollection_AsciiString(aName)),
58mycuri(0),
59#if !defined USE_MAP && !defined OCC189
60myresult(new TColStd_HArray1OfTransient(1,MaxSizeOfResult)),
61#endif
62myNb(0)
63{
64#ifdef USE_MAP
65 myResultMap.ReSize( MaxSizeOfResult ); // for maximum performnace on medium selections ( < 100000 objects )
66#endif
67}
68
69//=======================================================================
70//function : CreateSelection
71//purpose :
72//=======================================================================
73Standard_Boolean AIS_Selection::CreateSelection(const Standard_CString aName)
74{
75 Handle(AIS_Selection) S = AIS_Selection::Selection(aName);
76 if(!S.IsNull())
77 return Standard_False;
78 S = new AIS_Selection(aName);
79 AIS_Sel_GetSelections().Prepend(S);
80 AIS_Sel_CurrentSelection(S);
81 return Standard_True;
82}
83
84
85//=======================================================================
86//function : Selection
87//purpose :
88//=======================================================================
89Handle(AIS_Selection) AIS_Selection::Selection(const Standard_CString aName)
90{
91 Handle(AIS_Selection) S;
92 if(AIS_Sel_GetSelections().IsEmpty()) return S;
93
94 Handle(Standard_Transient) curobj;
95 Handle(AIS_Selection) Sel;
96// Standard_Boolean found(Standard_False);
97 for(Standard_Integer I =1; I<= AIS_Sel_GetSelections().Length();I++){
98 curobj = AIS_Sel_GetSelections().Value(I);
99 Sel = *((Handle(AIS_Selection)*)&curobj);
100 if(Sel->myName.IsEqual(aName))
101 return Sel;
102 }
103
104 return S;
105}
106
107//=======================================================================
108//function : Find
109//purpose :
110//=======================================================================
111Standard_Boolean AIS_Selection::Find(const Standard_CString aName)
112{
113 Handle(AIS_Selection) S = AIS_Selection::Selection(aName);
114 return !S.IsNull();
115}
116
117//=======================================================================
118//function : SetCurrentSelection
119//purpose :
120//=======================================================================
121Standard_Boolean AIS_Selection::SetCurrentSelection (const Standard_CString aName)
122{
123 AIS_Selection::CreateSelection(aName); // juste pour voir... ?????????????
124
125
126 Handle(AIS_Selection) anAISSelection = AIS_Selection::Selection(aName) ;
127 AIS_Sel_CurrentSelection ( anAISSelection ) ;
128 return Standard_True;
129}
130
131//=======================================================================
132//function : Select
133//purpose :
134//=======================================================================
135void AIS_Selection::Select()
136{
137 Handle(AIS_Selection) S;
138 AIS_Sel_CurrentSelection (S);
139 if(!S.IsNull()){
140 S->myNb=0;
141#if defined OCC189 || defined USE_MAP
142 S->myresult.Clear();
143#ifdef USE_MAP
144 S->myResultMap.Clear();
145#endif
146#endif
147 }
148}
149
150//=======================================================================
151//function : CurrentSelection
152//purpose :
153//=======================================================================
154Handle(AIS_Selection) AIS_Selection::CurrentSelection() {
155 Handle(AIS_Selection) S;
156 AIS_Sel_CurrentSelection (S);
157 return S;
158}
159//=======================================================================
160//function : Select
161//purpose :
162//=======================================================================
163AIS_SelectStatus AIS_Selection::Select(const Handle(Standard_Transient)& anObject)
164{
165 Handle(AIS_Selection) S;
166 AIS_Sel_CurrentSelection (S);
167 if(S.IsNull()) return AIS_SS_NotDone;
168 Handle(AIS_InteractiveObject) anAISObj;
169 Handle(SelectMgr_EntityOwner) owner = Handle(SelectMgr_EntityOwner)::DownCast( anObject );
170 if ( owner.IsNull() )
171 anAISObj = Handle(AIS_InteractiveObject)::DownCast( anObject );
172#ifndef OCC189
173 TColStd_Array1OfTransient& arr = S->myresult->ChangeArray1();
174
175 Standard_Integer Found(-1);
176 Standard_Integer i ;
177
178#ifdef BUC60953
179
180 Standard_Boolean selected = Standard_False;
181 if ( !owner.IsNull() )
182 selected = owner->State() != 0;
183#ifdef OCC138
184 else if(!anAISObj.IsNull())
185 selected = anAISObj->State();
186 }
187#endif
188
189 if ( selected ) // looking up index of object
190#endif
191
192 for( i=arr.Lower() && Found==-1;i<=S->myNb;i++){
193 if(arr(i)==anObject)
194 Found=i;
195 }
196 // Il n''est pas dedans, on le rajoute....
197
198#ifdef BUC60953
199 if ( !selected || Found == -1 ) {
200#else
201 if(Found==-1){
202#endif
203 if((S->myNb)+1>arr.Length()){
204 Handle(TColStd_HArray1OfTransient) NiouTab = new TColStd_HArray1OfTransient(1,arr.Length()+MaxSizeOfResult);
205 // oui bon, mais...
206 for(i=arr.Lower();i<=S->myNb;i++){
207 const Handle(Standard_Transient)& T = S->myresult->Value(i);
208 NiouTab->SetValue(i,T);
209 }
210#ifdef BUC60953
211 S->myresult = NiouTab;
212#endif
213 }
214 (S->myNb)++;
215 S->myresult->SetValue(S->myNb,anObject);
216 return AIS_SS_Added;
217 }
218 // il etait dedans on l''enleve...
219 for(i=Found;i<=S->myNb;i++)
220 arr(i)=arr(i+1);
221 S->myNb--;
222#elif !defined USE_MAP //OCC189
223 AIS_NListTransient::Iterator anIter ( S->myresult );
224 for ( ; anIter.More(); anIter.Next() )
225 if ( anIter.Value() == anObject ) {
226 S->myresult.Remove( anIter );
227 return AIS_SS_Removed;
228 }
229
230 S->myresult.Append( anObject );
231 return AIS_SS_Added;
232#else //USE_MAP
233 if ( S->myResultMap.IsBound( anObject ) ){
234 AIS_NListTransient::Iterator aListIter = S->myResultMap.Find( anObject );
235//skt-----------------------------------------------------------------
236 if( S->myIterator == aListIter )
237 if( S->myIterator.More() )
238 S->myIterator.Next();
239 else
240 S->myIterator = AIS_NListTransient::Iterator();
241//--------------------------------------------------------------------
242#ifdef BUC60953
243 // In the mode of advanced mesh selection only one owner is created
244 // for all selection modes. It is necessary to check the current detected
245 // entity and remove the owner from map only if the detected entity is
246 // the same as previous selected (IsForcedHilight call)
247 if( !anAISObj.IsNull() || ( !owner.IsNull() && !owner->IsForcedHilight() ) )
248 {
249#endif
250 S->myresult.Remove( aListIter );
251 S->myResultMap.UnBind( anObject );
252
253 // update list iterator for next object in <myresult> list if any
254 if ( aListIter.More() ){
255 const Handle(Standard_Transient)& aNextObject = aListIter.Value();
256 if ( S->myResultMap.IsBound( aNextObject ) )
257 S->myResultMap( aNextObject ) = aListIter;
258 else
259 S->myResultMap.Bind( aNextObject, aListIter );
260 }
261 return AIS_SS_Removed;
262 }
263 else
264 return AIS_SS_Added;
265 }
266
267 AIS_NListTransient::Iterator aListIter;
268 S->myresult.Append( anObject, aListIter );
269 S->myResultMap.Bind( anObject, aListIter );
270 return AIS_SS_Added;
271#endif //USE_MAP
272 return AIS_SS_Removed;
273
274}
275
276//=======================================================================
277//function : AddSelect
278//purpose : Always add int the selection
279//=======================================================================
280AIS_SelectStatus AIS_Selection::AddSelect(const Handle(Standard_Transient)& anObject)
281{
282 Handle(AIS_Selection) S;
283 AIS_Sel_CurrentSelection (S);
284 if(S.IsNull()) return AIS_SS_NotDone;
285
286#ifndef OCC189
287 TColStd_Array1OfTransient& arr = S->myresult->ChangeArray1();
288 Standard_Integer i;
289 if((S->myNb)+1>arr.Length()){
290 Handle(TColStd_HArray1OfTransient) NiouTab = new TColStd_HArray1OfTransient(1,arr.Length()+MaxSizeOfResult);
291 // oui bon, mais...
292 for(i=arr.Lower();i<=S->myNb;i++){
293 const Handle(Standard_Transient)& T = S->myresult->Value(i);
294 NiouTab->SetValue(i,T);
295 }
296 S->myresult = NiouTab;
297 }
298 (S->myNb)++;
299 S->myresult->SetValue(S->myNb,anObject);
300#elif !defined USE_MAP //OCC189
301 S->myresult.Append( anObject );
302#else //USE_MAP
303 if ( S->myResultMap.IsBound( anObject ) )
304 return AIS_SS_NotDone;
305
306 AIS_NListTransient::Iterator aListIter;
307 S->myresult.Append( anObject, aListIter );
308 S->myResultMap.Bind( anObject, aListIter );
309#endif
310 return AIS_SS_Added;
311}
312
313
314//=======================================================================
315//function : ClearAndSelect
316//purpose :
317//=======================================================================
318
319void AIS_Selection::ClearAndSelect(const Handle(Standard_Transient)& anObject) {
320 Handle(AIS_Selection) S;
321 AIS_Sel_CurrentSelection (S);
322 if(S.IsNull()) return;
323
324 Select();
325 Select(anObject);
326
327}
328
329
330//=======================================================================
331//function : Extent
332//purpose :
333//=======================================================================
334Standard_Integer AIS_Selection::Extent() {
335 Handle(AIS_Selection) S;
336 AIS_Sel_CurrentSelection (S);
337#if !defined OCC189 && !defined USE_MAP
338 return S->myNb;
339#else
340 return S->myresult.Extent();
341#endif
342}
343
344//=======================================================================
345//function : Single
346//purpose :
347//=======================================================================
348Handle(Standard_Transient) AIS_Selection::Single()
349{
350 Handle(AIS_Selection) S;
351 AIS_Sel_CurrentSelection (S);
352
353 S->Init();
354 return S->Value();
355}
356//=======================================================================
357//function : IsSelected
358//purpose :
359//=======================================================================
360Standard_Boolean AIS_Selection::IsSelected(const Handle(Standard_Transient)& anObject)
361{
362 Handle(AIS_Selection) S;
363 AIS_Sel_CurrentSelection (S);
364 if(S.IsNull()) return Standard_False;
365#ifndef USE_MAP
366 for(S->Init();S->More();S->Next()){
367 if(S->Value()==anObject)
368 return Standard_True;
369 }
370 return Standard_False;
371#else
372 return S->myResultMap.IsBound( anObject );
373#endif
374}
375
376//=======================================================================
377//function : Index
378//purpose :
379//=======================================================================
380
381Standard_Integer AIS_Selection::Index(const Standard_CString aName)
382{
383 Handle (Standard_Transient) curobj;
384 for(Standard_Integer I =1; I<= AIS_Sel_GetSelections().Length();I++){
385 curobj = AIS_Sel_GetSelections().Value(I);
386 if((*((Handle(AIS_Selection)*)&curobj))->myName.IsEqual(aName))
387 return I;
388 }
389 return 0;
390}
391
392//=======================================================================
393//function : Remove
394//purpose :
395//=======================================================================
396
397void AIS_Selection::Remove(const Standard_CString aName)
398{
399 Standard_Integer I = AIS_Selection::Index(aName);
400 if(I!=0) {
401#ifdef OCC1039
402 Handle(AIS_Selection) selection = Handle(AIS_Selection)::DownCast( AIS_Sel_GetSelections().Value(I) );
403 Standard_Integer stored = selection->NbStored();
404 if ( stored )
405 selection->Select();
406#endif
407 AIS_Sel_GetSelections().Remove(I);
408 }
409
410}
411