1 // Copyright (C) 2007-2012 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
23 #include "LightApp_SelectionMgr.h"
25 #include "LightApp_Study.h"
26 #include "LightApp_DataOwner.h"
27 #include "LightApp_DataSubOwner.h"
28 #include "LightApp_Application.h"
30 #include <SUIT_Session.h>
31 #include <SUIT_Selector.h>
33 #ifndef DISABLE_SALOMEOBJECT
34 #include <SALOME_ListIO.hxx>
35 #include <SALOME_ListIteratorOfListIO.hxx>
37 // Open CASCADE Include
38 #include <TColStd_MapOfInteger.hxx>
39 #include <TColStd_MapIteratorOfMapOfInteger.hxx>
40 #include <TColStd_IndexedMapOfInteger.hxx>
41 #include <TCollection_AsciiString.hxx>
44 #include <QtCore/QSet>
49 LightApp_SelectionMgr::LightApp_SelectionMgr( LightApp_Application* app, const bool fb )
50 : SUIT_SelectionMgr( fb ),
52 myTimeStamp( QTime::currentTime() ),
60 LightApp_SelectionMgr::~LightApp_SelectionMgr()
67 LightApp_Application* LightApp_SelectionMgr::application() const
72 void LightApp_SelectionMgr::setSelected( const SUIT_DataOwnerPtrList& lst, const bool append )
74 SUIT_SelectionMgr::setSelected( lst, append );
76 myTimeStamp = QTime::currentTime();
79 #ifndef DISABLE_SALOMEOBJECT
81 Get all selected objects from selection manager
83 void LightApp_SelectionMgr::selectedObjects( SALOME_ListIO& theList, const QString& theType,
84 const bool convertReferences ) const
86 LightApp_Study* study = dynamic_cast<LightApp_Study*>( application()->activeStudy() );
92 QList<Handle(SALOME_InteractiveObject)> selList;
94 if ( isActualSelectionCache( theType ) ) {
95 selList = selectionCache( theType );
99 if ( !theType.isEmpty() )
100 types.append( theType );
102 types = selectorTypes();
105 for ( QStringList::iterator it = types.begin(); it != types.end(); ++it ) {
106 SUIT_DataOwnerPtrList aList;
107 selected( aList, *it );
109 QList<Handle(SALOME_InteractiveObject)> typeSelList;
111 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr ) {
112 const LightApp_DataOwner* owner = dynamic_cast<const LightApp_DataOwner*>( (*itr).operator->() );
116 if ( !aSet.contains( owner->entry() ) ) {
117 selList.append( owner->IO() );
118 aSet.insert( owner->entry() );
121 typeSelList.append( owner->IO() );
124 if ( isSelectionCacheEnabled() ) {
125 LightApp_SelectionMgr* that = (LightApp_SelectionMgr*)this;
126 that->myCacheSelection.insert( *it, typeSelList );
127 that->myCacheTimes.insert( *it, QTime::currentTime() );
132 QSet<QString> entrySet;
133 for ( QList<Handle(SALOME_InteractiveObject)>::const_iterator itr = selList.begin(); itr != selList.end(); ++itr )
135 Handle(SALOME_InteractiveObject) io = *itr;
136 QString entry( io->getEntry() );
137 // Entry to check object uniqueness.
138 // It is selected owner entry in the case, when we do not convert references,
139 // and entry of a real object, when we convert references.
140 if ( convertReferences ) {
141 QString refEntry = study->referencedToEntry( entry );
142 if ( !entrySet.contains( refEntry ) ) {
143 if ( refEntry != entry ) {
145 QString component = study->componentDataType( entry );
146 theList.Append( new SALOME_InteractiveObject( (const char*)entry.toLatin1(),
147 (const char*)component.toLatin1(),
148 ""/*refobj->Name().c_str()*/ ) );
150 else if ( !io.IsNull() )
151 theList.Append( io );
154 else if ( !entrySet.contains( entry ) && !io.IsNull() )
155 theList.Append( io );
157 entrySet.insert( entry );
162 Append selected objects.
164 void LightApp_SelectionMgr::setSelectedObjects( const SALOME_ListIO& lst, const bool append )
166 SUIT_DataOwnerPtrList owners;
167 for ( SALOME_ListIteratorOfListIO it( lst ); it.More(); it.Next() )
169 if ( it.Value()->hasEntry() )
170 owners.append( new LightApp_DataOwner( it.Value() ) );
173 setSelected( owners, append );
178 Get all selected objects from selection manager
180 void LightApp_SelectionMgr::selectedObjects( QStringList& theList, const QString& theType,
181 const bool convertReferences ) const
183 LightApp_Study* study = dynamic_cast<LightApp_Study*>( application()->activeStudy() );
191 if ( isActualSelectionCache( theType ) )
192 selList = selectionCache( theType );
195 if ( !theType.isEmpty() )
196 types.append( theType );
198 types = selectorTypes();
201 for ( QStringList::iterator it = types.begin(); it != types.end(); ++it ) {
202 SUIT_DataOwnerPtrList aList;
203 selected( aList, *it );
205 QStringList typeSelList;
207 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr ) {
208 const LightApp_DataOwner* owner = dynamic_cast<const LightApp_DataOwner*>( (*itr).operator->() );
212 if ( !aSet.contains( owner->entry() ) ) {
213 selList.append( owner->entry() );
214 aSet.insert( owner->entry() );
217 typeSelList.append( owner->entry() );
220 if ( isSelectionCacheEnabled() ) {
221 LightApp_SelectionMgr* that = (LightApp_SelectionMgr*)this;
222 that->myCacheSelection.insert( *it, typeSelList );
223 that->myCacheTimes.insert( *it, QTime::currentTime() );
234 Emit current selection changed.
236 void LightApp_SelectionMgr::selectionChanged( SUIT_Selector* theSel )
238 SUIT_SelectionMgr::selectionChanged( theSel );
240 myTimeStamp = QTime::currentTime();
242 emit currentSelectionChanged();
245 #ifndef DISABLE_SALOMEOBJECT
248 get map of indexes for the given SALOME_InteractiveObject
250 void LightApp_SelectionMgr::GetIndexes( const Handle(SALOME_InteractiveObject)& IObject,
251 TColStd_IndexedMapOfInteger& theIndex)
255 SUIT_DataOwnerPtrList aList;
258 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr )
260 LightApp_DataSubOwner* subOwner = dynamic_cast<LightApp_DataSubOwner*>( (*itr).operator->() );
261 if ( subOwner && subOwner->entry() == QString(IObject->getEntry()) )
262 theIndex.Add( subOwner->index() );
267 get map of indexes for the given entry of SALOME_InteractiveObject
269 void LightApp_SelectionMgr::GetIndexes( const QString& theEntry, TColStd_IndexedMapOfInteger& theIndex )
273 SUIT_DataOwnerPtrList aList;
276 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr )
278 const LightApp_DataSubOwner* subOwner = dynamic_cast<const LightApp_DataSubOwner*>( (*itr).operator->() );
280 if ( subOwner->entry() == theEntry )
281 theIndex.Add( subOwner->index() );
287 Add or remove interactive objects from selection manager.
289 //bool LightApp_SelectionMgr::AddOrRemoveIndex( const Handle(SALOME_InteractiveObject)& IObject,
290 void LightApp_SelectionMgr::AddOrRemoveIndex( const Handle(SALOME_InteractiveObject)& IObject,
291 const TColStd_MapOfInteger& theIndexes,
294 SUIT_DataOwnerPtrList remainsOwners;
296 SUIT_DataOwnerPtrList aList;
299 QString ioEntry (IObject->getEntry());
302 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr )
304 const LightApp_DataOwner* owner = dynamic_cast<const LightApp_DataOwner*>( (*itr).operator->() );
307 if ( owner->entry() != ioEntry )
309 const LightApp_DataSubOwner* subOwner = dynamic_cast<const LightApp_DataSubOwner*>( owner );
311 remainsOwners.append( new LightApp_DataSubOwner( subOwner->entry(), subOwner->index() ) );
313 remainsOwners.append( new LightApp_DataOwner( owner->entry() ) );
319 remainsOwners = aList;
321 TColStd_MapIteratorOfMapOfInteger It;
322 It.Initialize(theIndexes);
323 for(;It.More();It.Next())
324 remainsOwners.append( new LightApp_DataSubOwner( ioEntry, It.Key() ) );
327 setSelected( remainsOwners, append );
329 emit currentSelectionChanged();
331 // Bug 17269: To avoid calling of selected(aList)
332 //TColStd_IndexedMapOfInteger anIndexes;
333 //GetIndexes( IObject, anIndexes );
334 //return !anIndexes.IsEmpty();
338 select 'subobjects' with given indexes
340 void LightApp_SelectionMgr::selectObjects( const Handle(SALOME_InteractiveObject)& IObject,
341 TColStd_IndexedMapOfInteger theIndex, bool append )
343 SUIT_DataOwnerPtrList aList;
345 if ( theIndex.IsEmpty() )
346 aList.append( new LightApp_DataOwner( QString(IObject->getEntry()) ) );
350 for ( i = 1; i <= theIndex.Extent(); i++ )
351 aList.append( new LightApp_DataSubOwner( QString(IObject->getEntry()), theIndex( i ) ) );
354 setSelected( aList, append );
358 select 'subobjects' with given indexes
360 void LightApp_SelectionMgr::selectObjects( MapIOOfMapOfInteger theMapIO, bool append )
362 SUIT_DataOwnerPtrList aList;
364 MapIOOfMapOfInteger::Iterator it(theMapIO);
365 for ( ; it.More(); it.Next() )
367 if ( it.Value().IsEmpty() )
368 aList.append( new LightApp_DataOwner( QString(it.Key()->getEntry()) ) );
372 for ( i = 1; i <= it.Value().Extent(); i++ )
373 aList.append( new LightApp_DataSubOwner( QString(it.Key()->getEntry()), it.Value()( i ) ) );
377 setSelected( aList, append );
381 get map of selected subowners : object's entry <-> map of indexes
383 void LightApp_SelectionMgr::selectedSubOwners( MapEntryOfMapOfInteger& theMap )
387 TColStd_IndexedMapOfInteger anIndexes;
389 SUIT_DataOwnerPtrList aList;
392 for ( SUIT_DataOwnerPtrList::const_iterator itr = aList.begin(); itr != aList.end(); ++itr )
394 const LightApp_DataSubOwner* subOwner =
395 dynamic_cast<const LightApp_DataSubOwner*>( (*itr).operator->() );
399 if ( !theMap.IsBound( TCollection_AsciiString(subOwner->entry().toLatin1().data()) ) )
401 // if ( !theMap.IsBound( subOwner->entry().toLatin1().data() ) )
405 //Bug 17269: GetIndexes( subOwner->entry(), anIndexes );
406 //Bug 17269: To avoid multiple calling of selected(aList)
407 for ( SUIT_DataOwnerPtrList::const_iterator itr2 = itr; itr2 != aList.end(); ++itr2 )
409 const LightApp_DataSubOwner* subOwner2 =
410 dynamic_cast<const LightApp_DataSubOwner*>( (*itr2).operator->() );
412 if ( subOwner2->entry() == subOwner->entry() )
413 anIndexes.Add( subOwner2->index() );
416 theMap.Bind( subOwner->entry().toLatin1().data(), anIndexes );
424 void LightApp_SelectionMgr::clearSelectionCache()
426 myCacheTimes.clear();
427 myCacheSelection.clear();
430 bool LightApp_SelectionMgr::isSelectionCacheEnabled() const
435 void LightApp_SelectionMgr::setSelectionCacheEnabled( bool on )
437 if ( myCacheState == on )
443 clearSelectionCache();
446 #ifndef DISABLE_SALOMEOBJECT
448 QList<Handle_SALOME_InteractiveObject> LightApp_SelectionMgr::selectionCache( const QString& type ) const
450 QList<Handle_SALOME_InteractiveObject> res;
453 if ( !type.isEmpty() )
454 types.append( type );
456 types = selectorTypes();
459 for ( QStringList::iterator it = types.begin(); it != types.end(); ++it ) {
460 if ( myCacheSelection.contains( *it ) ) {
461 const SelList& lst = myCacheSelection[*it];
462 for ( SelList::const_iterator itr = lst.begin(); itr != lst.end(); ++itr ) {
463 if ( !(*itr).IsNull() && !set.contains( (*itr)->getEntry() ) ) {
465 set.insert( (*itr)->getEntry() );
475 QStringList LightApp_SelectionMgr::selectionCache( const QString& type ) const
480 if ( !type.isEmpty() )
481 types.append( type );
483 types = selectorTypes();
486 for ( QStringList::iterator it = types.begin(); it != types.end(); ++it ) {
487 if ( myCacheSelection.contains( *it ) ) {
488 const SelList& lst = myCacheSelection[*it];
489 for ( SelList::const_iterator itr = lst.begin(); itr != lst.end(); ++itr ) {
490 if ( !set.contains( *itr ) ) {
502 bool LightApp_SelectionMgr::isActualSelectionCache( const QString& type ) const
507 if ( !type.isEmpty() )
508 types.append( type );
510 types = selectorTypes();
512 for ( QStringList::iterator it = types.begin(); it != types.end() && ok; ++it )
513 ok = myCacheTimes.contains( *it ) && myCacheTimes[*it].isValid() && myCacheTimes[*it] >= myTimeStamp;
518 QStringList LightApp_SelectionMgr::selectorTypes() const
521 QList<SUIT_Selector*> selectorList;
522 selectors( selectorList );
523 for ( QList<SUIT_Selector*>::const_iterator it = selectorList.begin(); it != selectorList.end(); ++it ) {
524 if ( (*it)->isEnabled() )
525 types.append( (*it)->type() );