Salome HOME
PAL10125 - by double click on reference original object becomes selected
[modules/gui.git] / src / GLViewer / GLViewer_Context.cxx
index 4ea362dc25ea363bcac2e32a8c341c1ae272ac2d..264a5657f230363cec8a2ee597b6a7a5d5792a24 100644 (file)
@@ -3,15 +3,14 @@
 // Author:    OCC team
 // Copyright (C) CEA 2004
 
-/****************************************************************************
-**  Class:   GLViewer_Context 
-**  Descr:   OpenGL Context
-**  Module:  GLViewer
-**  Created: UI team, 20.09.02
-*****************************************************************************/
+//================================================================
+// Class       : GLViewer_AspectLine
+// Description : Class for manage of presentations in GLViewer
+//================================================================
 
 #include "GLViewer_Context.h"
 
+#include "GLViewer_Group.h"
 #include "GLViewer_Object.h"
 #include "GLViewer_Viewer2d.h"
 #include "GLViewer_ViewPort2d.h"
 
 #define TOLERANCE  12
 
+//=======================================================================
+// Function: GLViewer_Context
+// Purpose :
+//=======================================================================
 GLViewer_Context::GLViewer_Context( GLViewer_Viewer2d* v ) :
        myGLViewer2d( v ),
        myHighlightColor( Quantity_NOC_CYAN1 ),
        mySelectionColor( Quantity_NOC_RED ),
-       myTolerance( TOLERANCE ),
-       myNumber( 0 )
+       myTolerance( TOLERANCE )
 {
-  myLastPicked = NULL;
-  isLastPickedChanged = false;
+  myUpdateAll = true;
+
+  myLastPicked = 0;
+  myLastPickedChanged = false;
+
   myHFlag = GL_TRUE;
   mySFlag = GL_TRUE;
+
   mySelCurIndex = 0;
 }
 
+//=======================================================================
+// Function: ~GLViewer_Context
+// Purpose :
+//=======================================================================
 GLViewer_Context::~GLViewer_Context()
 {
+    myActiveObjects.clear();
+    myInactiveObjects.clear();
+    mySelectedObjects.clear();
 }
 
+//=======================================================================
+// Function: MoveTo
+// Purpose :
+//=======================================================================
 int GLViewer_Context::MoveTo( int xi, int yi, bool byCircle )
 {
-  GLfloat x = (GLfloat)xi;
-  GLfloat y = (GLfloat)yi;
-  myGLViewer2d->transPoint( x, y );
-  //cout << "GLViewer_Context::MoveTo " << x << " " << y << endl;
+    GLfloat x = (GLfloat)xi;
+    GLfloat y = (GLfloat)yi;
+    myGLViewer2d->transPoint( x, y );
 
-  QValueList<GLViewer_Object*> anUpdatedObjects;
-  
-  ObjectMap::Iterator it;
-  
-  myXhigh = x;
-  myYhigh = y;  
-  
-  //if( !myHFlag )
-  //  return 1;
-
-  GLfloat aXScale;
-  GLfloat aYScale;
-  GLViewer_ViewPort2d* vp = ( GLViewer_ViewPort2d* )myGLViewer2d->getActiveView()->getViewPort();
-  vp->getScale( aXScale, aYScale );
-
-  //bool onlyUpdate = true;
-  GLboolean update = GL_FALSE;
-  GLboolean isHigh = GL_FALSE;
-  GLboolean onObject = GL_FALSE;
+    myXhigh = x;
+    myYhigh = y;  
+
+    GLboolean isHigh = GL_FALSE;
+    GLboolean onObject = GL_FALSE;
+
+    GLViewer_Object* aPrevLastPicked = myLastPicked;
+    GLViewer_Object* lastPicked = 0;
+
+    ObjList anUpdatedObjects;
   
-  GLViewer_Object* aPrevLastPicked = myLastPicked;
-  GLViewer_Object* lastPicked = NULL;
-  QRect* rect;
-  QRegion obj;
-  QRegion intersection;
-  QRect region;
-
-  region.setLeft( (int)(x - myTolerance) );
-  region.setRight( (int)(x + myTolerance) );
-  region.setTop( (int)(y - myTolerance) );
-  region.setBottom( (int)(y + myTolerance) );
-
-  QRegion circle( (int)(x - myTolerance), (int)(y - myTolerance),
-                      (int)(2 * myTolerance), (int)(2 * myTolerance), QRegion::Ellipse );
-
-  for( it = myObjects.begin(); it != myObjects.end(); ++it )
-  {
-    it.key()->setScale( aXScale, aYScale );
-    rect = it.key()->getUpdateRect()->toQRect();
-    obj = QRegion( *rect );
-    intersection = obj.intersect( circle );
+    if( myActiveObjects.isEmpty() )
+        return -1;
 
-    if( !byCircle && rect->intersects( region ) )
+    ObjList::iterator it = myActiveObjects.end();
+    ObjList::iterator itEnd = myActiveObjects.begin();
+    for( it--; ; --it )
     {
-      //      cout << "object : " << it.data() << endl;
-      update = it.key()->highlight( x, y, myTolerance, GL_FALSE );
-      isHigh = it.key()->isHighlighted();
-      onObject = GL_TRUE;
-      //if( update )
-      //    cout << "update" << endl;
-      //if( isHigh )
-      //    cout << "highlight" << endl;
+        GLViewer_Object* object = *it;
+
+        GLViewer_Rect* rect = object->getUpdateRect();
+        if( rect->contains( GLViewer_Pnt( x, y ) ) )
+        {
+            onObject = GL_TRUE;
+            object->highlight( x, y, myTolerance, GL_FALSE );
+            isHigh = object->isHighlighted();
+        }
+
+        if( isHigh )
+        {
+            lastPicked = object;
+            break;
+        }
+
+        if( it == itEnd )
+            break;
     }
 
-    if( byCircle && !intersection.isEmpty() )
+    if( !myHFlag )
     {
-      update = it.key()->highlight( x, y, myTolerance, GL_TRUE );
-      isHigh = it.key()->isHighlighted();
-      onObject = GL_TRUE;
+        myLastPicked = lastPicked;
+        return -1;
     }
-    
-    if( isHigh )
+
+    if ( !onObject )
     {
-      lastPicked = it.key();
-      break;
-    }
-  }
+        //cout << 0 << endl;
+        it = myActiveObjects.begin();
+        itEnd = myActiveObjects.end();
 
-  if( !myHFlag )
-  {
-    myLastPicked = lastPicked; //we need this information everytime
-    return -1;
-  }
-  
-  if ( !onObject )
-  {
-    for( it = myObjects.begin(); it != myObjects.end(); ++it )
-      if( it.key()->unhighlight() )
-       anUpdatedObjects.append( it.key() );
-    
-    myLastPicked = NULL;
-    isLastPickedChanged = aPrevLastPicked != myLastPicked;
-    
-    if( isLastPickedChanged )
-      myGLViewer2d->updateAll();  
-    
-    return 0;
-  }
-  
-  if( !myLastPicked && isHigh )
-  {
-    //cout << "1" << endl;
-    myLastPicked = lastPicked;
-    myHNumber = myObjects[ lastPicked ];
-    anUpdatedObjects.append( myLastPicked );
-  }
-  else if( myLastPicked && !isHigh )
-  {
-    //cout << "2" << endl;
-    //onlyUpdate = 
-    myLastPicked->unhighlight();
-    anUpdatedObjects.append( myLastPicked );
-    //eraseObject( myLastPicked, true );
-    myLastPicked = NULL;
-    myHNumber = -1;
-  }
-  else if( myLastPicked && isHigh )
-  {
-    //cout << "3" << endl;
-    //cout << "HNumber" << myHNumber << endl;
+        for( ; it != itEnd; ++it )
+            (*it)->unhighlight();
 
-    myLastPicked->highlight( x, y, myTolerance, byCircle );
-    if( !myLastPicked->isHighlighted() )
-    {
-      myLastPicked->unhighlight();
-      anUpdatedObjects.append( myLastPicked );
-      myLastPicked = lastPicked;
-      myHNumber = myObjects[ lastPicked ];
-    }
-    anUpdatedObjects.append( myLastPicked );
-  }
+        anUpdatedObjects.append( (*it) );
+
+        myLastPicked = 0;
+        myLastPickedChanged = aPrevLastPicked != myLastPicked;
 
-  isLastPickedChanged = ( aPrevLastPicked != myLastPicked );
+        if( myLastPickedChanged )
+            myGLViewer2d->updateAll();  
 
-  if( isLastPickedChanged/*!onlyUpdate*/ )
+        return 0;
+    }
+
+    if( !myLastPicked && isHigh )
     {
-      myGLViewer2d->updateAll();
-      //myGLViewer2d->activateAllDrawers( true );
+        //cout << 1 << endl;
+        myLastPicked = lastPicked;
+        anUpdatedObjects.append( myLastPicked );
+    }
+    else if( myLastPicked && !isHigh )
+    {
+        //cout << 2 << endl;
+        myLastPicked->unhighlight();
+        anUpdatedObjects.append( myLastPicked );
+        myLastPicked = 0;
+    }
+    else if( myLastPicked && isHigh )
+    {
+        //cout << 3 << endl;
+        //myLastPicked->highlight( x, y, myTolerance, byCircle );
+        if( myLastPicked != lastPicked )
+        {
+            myLastPicked->unhighlight();
+            if( myLastPicked != lastPicked )
+            {
+                myLastPicked = lastPicked;
+                anUpdatedObjects.append( myLastPicked );
+            }
+        }
     }
-  else
-    myGLViewer2d->activateDrawers( anUpdatedObjects, TRUE, TRUE );
 
-  return 0;
+    myLastPickedChanged = ( aPrevLastPicked != myLastPicked );
+
+    if( myLastPickedChanged || myUpdateAll )
+        myGLViewer2d->updateAll();
+    else
+        myGLViewer2d->activateDrawers( anUpdatedObjects, TRUE, TRUE );
+
+    return 0;
 }
 
+//=======================================================================
+// Function: Select
+// Purpose :
+//=======================================================================
 int GLViewer_Context::Select( bool Append, bool byCircle )
 {
-  //cout << "GLViewer_Context::Select " << (int)Append << endl;
-  QValueList<int>::Iterator it;
-  ObjectMap::Iterator oit;
-  SelectionStatus status = SS_Invalid;
+    ObjList::Iterator it, itEnd, oit, oitEnd;
+    SelectionStatus status = SS_Invalid;
 
-  bool onlyUpdate = false;
+    bool updateAll = false;
 
-  QValueList<GLViewer_Object*> aList;
+    ObjList aList;
 
-  if ( !mySFlag )
-    return status;//invalid
-  
-  if( myHFlag && myLastPicked )
-  {
-    if( mySelNumbers.count() == 1 && mySelNumbers.first() == myHNumber )
-      status = SS_LocalChanged;
-    
-    if ( !Append )
+    if ( !mySFlag )
+        return status;//invalid
+
+    if( myHFlag && myLastPicked )
     {
-      for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-        for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-          if( *it == myObjects[ oit.key() ] )
-            if ( myLastPicked != oit.key() )
-            {
-                onlyUpdate = oit.key()->unselect();
-                aList.append( oit.key() );
-            }
+        if( mySelectedObjects.count() == 1 && mySelectedObjects.first() == myLastPicked )
+            status = SS_LocalChanged;
 
-      if( onlyUpdate )
-        myGLViewer2d->updateAll();
-      else
-        myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
+        if ( !Append )
+        {
+            for( it = mySelectedObjects.begin(), itEnd = mySelectedObjects.end() ; it != itEnd; ++it )
+                   if( myLastPicked != *it )
+                {
+                       updateAll = (*it)->unselect() || updateAll;
+                       aList.append( *it );
+                }
 
-      if( mySelNumbers.count() != 0 && status == SS_Invalid )
-       status = SS_GlobalChanged;
-      mySelNumbers.clear();
-    } 
+            if( updateAll || myUpdateAll )
+                myGLViewer2d->updateAll();
+            else
+                myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
 
-    if ( myLastPicked->select( myXhigh, myYhigh, myTolerance, GLViewer_Rect(), false, byCircle, Append )
-      && mySelNumbers.findIndex( myHNumber ) == -1 )
-      /*if ( myLastPicked->select( myXhigh, myYhigh, myTolerance, byCircle, Append ) )
-      //&&( mySelNumbers.findIndex( myHNumber ) == -1 ) )*/
-    {
-      mySelNumbers.append( myHNumber );
-      //cout << "context::select object #" << myHNumber << endl;
-      myGLViewer2d->activateDrawer( myLastPicked, TRUE, TRUE );
-      
-      if( status == SS_Invalid )
-       status = SS_GlobalChanged;
-//      else
-//        status = SS_GlobalChanged;
+            if( mySelectedObjects.count() != 0 && status == SS_Invalid )
+                status = SS_GlobalChanged;
+            mySelectedObjects.clear();
+        } 
+
+        if ( myLastPicked->select( myXhigh, myYhigh, myTolerance, GLViewer_Rect(), false, byCircle, Append )
+             && mySelectedObjects.findIndex( myLastPicked ) == -1 )
+        {
+            mySelectedObjects.append( myLastPicked );
+            myGLViewer2d->activateDrawer( myLastPicked, TRUE, TRUE );
+
+            if( status == SS_Invalid )
+                status = SS_GlobalChanged;
+        }
+        else if( status == SS_LocalChanged )
+            status = SS_GlobalChanged;
+
+        return status;
     }
-    else if( status == SS_LocalChanged )
-      status = SS_GlobalChanged;
-    
-    return status;
-  }
-  
-  if( myHFlag && !myLastPicked )
-  {
-    if ( !Append )
+
+    if( myHFlag && !myLastPicked )
     {
-      for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-        for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-          if( *it == myObjects[ oit.key() ] )
-          {
-            onlyUpdate = oit.key()->unselect();
-            //list.Append( *it );
-            aList.append( oit.key() );
-          } 
-     
-      if( onlyUpdate )
-          myGLViewer2d->updateAll();
-      else
-       myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
-
-      if( mySelNumbers.count() != 0 )
-       status = SS_GlobalChanged;
-      
-      mySelNumbers.clear();
-      //cout << " myHFlag && !myLastPicked  " << endl;
+        if ( !Append )
+        {
+            for( it = mySelectedObjects.begin(), itEnd = mySelectedObjects.end() ; it != itEnd; ++it )
+                   if ( myLastPicked != *it )
+                {
+                       updateAll = (*it)->unselect() || updateAll;
+                       aList.append( *it );
+                }
+
+            if( updateAll || myUpdateAll )
+                myGLViewer2d->updateAll();
+            else
+                myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
+
+            if( mySelectedObjects.count() != 0 )
+                status = SS_GlobalChanged;
+
+            mySelectedObjects.clear();
+        }
+        return status;
     }
-    return status;
-  }
 
-//   if( !myHFlag )
-//   {
-//     GLViewer_Object* lastPicked = NULL;
-//     GLboolean update = FALSE;
-//     GLboolean isSel = GL_FALSE;
-//     list = new int[2];
-//     number = 0;
-//     float xa, xb, ya, yb;
-//     QRect* rect;
-
-//     ObjectMap::Iterator it;
-//     for( it = myObjects.begin(); it != myObjects.end(); ++it )
-//     {
-//       rect = it.key()->getRect();
-//       xa = rect->left();
-//       xb = rect->right();
-//       ya = rect->top();
-//       yb = rect->bottom();      
-      
-//       if( myXhigh >= xa && myXhigh <= xb && myYhigh >= ya && myYhigh <= yb )
-//       {
-//  update = it.key()->select( myXhigh, myYhigh, myTolerance, byCircle, Append );
-//  isSel = it.key()->isSelected();
-//  if( isSel )
-//  {
-//    myLastPicked = it.key();
-//    number = myObjects[ lastPicked ];
-//  }
-//       }
-//     }
-
-//     if ( !Append )
-//     {
-//       for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-//  for( it1 = myObjects.begin(); it1 != myObjects.end(); ++it1 )
-//    if( *it == myObjects[ it1.key() ] )
-//    {
-//      it1.key()->unselect();
-//      myGLViewer2d->initDrawer( it1.key(), it.data() );
-//      list.Append( *it );
-//    }      
-//       myGLViewer2d->activateDrawers( list, TRUE );
-//       mySelNumbers.clear();
-//     }
-//     if ( mySelNumbers.findIndex( myObjects[lastPicked] ) == -1)
-//       mySelNumbers.append( myObjects[lastPicked] );
-
-//     number = mySelNumbers.count();
-//     list = new int[number + 1];
-//     list[0] = number;
-    
-//     for( it = mySelNumbers.begin(), i = 1; it != mySelNumbers.end(); ++it, i++ )
-//       list[i] = *it;
-
-//     myGLViewer2d->initDrawer( myLastPicked, myHNumber );
-//     myGLViewer2d->activateDrawers( list, TRUE );
-//   }
-
-  if( !myHFlag )
-  {
-    bool isSel = false;
-    GLfloat aXScale;
-    GLfloat aYScale;
-    GLViewer_ViewPort2d* vp = ( GLViewer_ViewPort2d* )myGLViewer2d->getActiveView()->getViewPort();
-    vp->getScale( aXScale, aYScale );
-    
-    QRect* rect;
-    QRect region;
-    QRegion obj;
-    
-    region.setLeft( ( int )( myXhigh - myTolerance ) );
-    region.setRight( ( int )( myXhigh + myTolerance ) );
-    region.setTop( ( int )( myYhigh - myTolerance ) );
-    region.setBottom( ( int )( myYhigh + myTolerance ) );
-    
-    QRegion circle( ( int )( myXhigh - myTolerance ), ( int )( myYhigh - myTolerance ),
-                   2 * myTolerance, 2 * myTolerance, QRegion::Ellipse );
-    
-    if ( !Append )
+    if( !myHFlag )
     {
-      for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-       for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-         if( *it == myObjects[ oit.key() ] )
-         {
-           onlyUpdate |= (bool)oit.key()->unselect();
-           aList.append( oit.key() );
-         }
-      
-      if( onlyUpdate )
-       myGLViewer2d->updateAll();
-      else
-       myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
-      
-      if( mySelNumbers.count() != 0 )
-       status = SS_GlobalChanged;
-
-      mySelNumbers.clear();
-    }        
-
-    for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-    {
-      oit.key()->setScale( aXScale, aYScale );
-      rect = oit.key()->getUpdateRect()->toQRect();
-      obj = QRegion( *rect );
-      
-      if( !byCircle && rect->intersects( region ) )
-      {
-       oit.key()->select( myXhigh, myYhigh, myTolerance, GLViewer_Rect(), false, byCircle, Append );
-       isSel = oit.key()->isSelected();
-      }
-      
-      if( byCircle && !obj.intersect( circle ).isEmpty() )
-      {
-       oit.key()->select( myXhigh, myYhigh, myTolerance, GLViewer_Rect(), false, byCircle, Append );
-       isSel = oit.key()->isSelected();
-      }
-      if( isSel )
-      {
-       myLastPicked = oit.key();
-       mySelNumbers.append( myObjects[ myLastPicked ] );
-       myGLViewer2d->activateDrawer( myLastPicked, TRUE, TRUE );
-       status = SS_GlobalChanged;
-       return status;
-      }
+        bool isSel = false;
+        GLfloat aXScale;
+        GLfloat aYScale;
+        GLViewer_ViewPort2d* vp = ( GLViewer_ViewPort2d* )myGLViewer2d->getActiveView()->getViewPort();
+        vp->getScale( aXScale, aYScale );
+
+        if ( !Append )
+        {
+            for( it = mySelectedObjects.begin(), itEnd = mySelectedObjects.end() ; it != itEnd; ++it )
+                if( myLastPicked != *it )
+                {
+                    updateAll = (*it)->unselect() || updateAll;
+                    aList.append( *it );
+                }
+
+            if( updateAll || myUpdateAll )
+                myGLViewer2d->updateAll();
+            else
+                myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
+
+            if( mySelectedObjects.count() != 0 )
+                status = SS_GlobalChanged;
+
+            mySelectedObjects.clear();
+        }        
+
+        for( oit = myActiveObjects.begin(), oitEnd = myActiveObjects.end(); oit != oitEnd; ++oit )
+        {
+            (*oit)->setScale( aXScale, aYScale );
+            GLViewer_Rect* rect = (*oit)->getUpdateRect();
+
+            if( rect->contains( GLViewer_Pnt( myXhigh, myXhigh ) ) )
+            {
+                (*oit)->select( myXhigh, myYhigh, myTolerance, GLViewer_Rect(), false, byCircle, Append );
+                isSel = (*oit)->isSelected();
+            }
+            if( isSel )
+            {
+                myLastPicked = *oit;
+                mySelectedObjects.append( myLastPicked );
+                myGLViewer2d->activateDrawer( myLastPicked, TRUE, TRUE );
+                status = SS_GlobalChanged;
+                return status;
+            }
+        }
     }
-  }
         
-  return SS_NoChanged;
+    return SS_NoChanged;
 }
 
+//=======================================================================
+// Function: SelectByRect
+// Purpose :
+//=======================================================================
 int GLViewer_Context::SelectByRect( const QRect& theRect, bool Append )
 {
     GLfloat aXScale;
@@ -406,63 +307,59 @@ int GLViewer_Context::SelectByRect( const QRect& theRect, bool Append )
 
     SelectionStatus status = SS_NoChanged;
 
-    QValueList<int>::Iterator it;
-    ObjectMap::Iterator oit;
+    ObjList aList;
+    ObjList::Iterator it, itEnd;
 
-    QValueList<GLViewer_Object*> aList;
-
-    if ( !mySFlag || myObjList.empty() )
+    if ( !mySFlag || myActiveObjects.empty() )
         return SS_Invalid;
 
     bool updateAll = false;
     if( !Append )
     {
-        if( mySelNumbers.count() != 0 )
+        if( mySelectedObjects.count() != 0 )
             status = SS_GlobalChanged;
 
-        for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-            for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-                if( *it == myObjects[ oit.key() ] )
-                {
-                    updateAll |= (bool)oit.key()->unselect();
-                    aList.append( oit.key() );
-                }
-        mySelNumbers.clear();
+        for( it = mySelectedObjects.begin(), itEnd = mySelectedObjects.end(); it != itEnd; ++it )
+        {
+            updateAll = (*it)->unselect() || updateAll;
+            aList.append( *it );
+        }
+        mySelectedObjects.clear();
     }
 
-    for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
+    for( it = myActiveObjects.begin(), itEnd = myActiveObjects.end(); it != itEnd; ++it )
     {
         bool isSel = false;
-        oit.key()->setScale( aXScale, aYScale );
-        QRect rect = //myGLViewer2d->getWinObjectRect( oit.key() ); //->getUpdateRect()->toQRect();
-          myGLViewer2d->getQRect( *(oit.key()->getRect()) );
+        (*it)->setScale( aXScale, aYScale );
+        QRect rect = myGLViewer2d->getQRect( *( (*it)->getRect() ) );
 
         if( rect.intersects( theRect ) )
         {
             GLViewer_Rect aRect = myGLViewer2d->getGLVRect( theRect );
-            oit.key()->select( myXhigh, myYhigh, myTolerance, aRect, false, false, Append );
-            isSel = oit.key()->isSelected();
+            (*it)->select( myXhigh, myYhigh, myTolerance, aRect, false, false, Append );
+            isSel = (*it)->isSelected();
         }
 
-        if( isSel && mySelNumbers.findIndex( oit.data() ) == -1 )
+        if( isSel && mySelectedObjects.findIndex( *it ) == -1 )
         {
-            aList.append( oit.key() );
-            mySelNumbers.append( oit.data() );
+            aList.append( *it );
+            mySelectedObjects.append( *it );
             status = SS_GlobalChanged;
         }
     }
 
-    if( updateAll ) //i.e only update
-    {
-        //cout << "Unhilight.ALL" << endl;
+    if( updateAll || myUpdateAll )
         myGLViewer2d->updateAll();
-    }
     else
         myGLViewer2d->activateDrawers( aList, TRUE, TRUE );
 
     return status;
 }
 
+//=======================================================================
+// Function: SetHighlightColor
+// Purpose :
+//=======================================================================
 void GLViewer_Context::SetHighlightColor( Quantity_NameOfColor aCol )
 {
   myHighlightColor = aCol;
@@ -482,6 +379,10 @@ void GLViewer_Context::SetHighlightColor( Quantity_NameOfColor aCol )
   myGLViewer2d->updateColors( colH, colS);
 }
 
+//=======================================================================
+// Function: SetSelectionColor
+// Purpose :
+//=======================================================================
 void GLViewer_Context::SetSelectionColor( Quantity_NameOfColor aCol )
 {
   mySelectionColor = aCol;
@@ -501,21 +402,37 @@ void GLViewer_Context::SetSelectionColor( Quantity_NameOfColor aCol )
   myGLViewer2d->updateColors( colH, colS);
 }
 
+//=======================================================================
+// Function: NbSelected
+// Purpose :
+//=======================================================================
 int GLViewer_Context::NbSelected()
 {
-  return mySelNumbers.count();
+  return mySelectedObjects.count();
 }
 
+//=======================================================================
+// Function: InitSelected
+// Purpose :
+//=======================================================================
 void GLViewer_Context::InitSelected()
 {
   mySelCurIndex = 0;
 }
 
+//=======================================================================
+// Function: MoreSelected
+// Purpose :
+//=======================================================================
 bool GLViewer_Context::MoreSelected()
 {
   return ( mySelCurIndex < NbSelected() );
 }
 
+//=======================================================================
+// Function: NextSelected
+// Purpose :
+//=======================================================================
 bool GLViewer_Context::NextSelected()
 {
   if ( mySelCurIndex >= 0 && mySelCurIndex < NbSelected() )
@@ -527,122 +444,175 @@ bool GLViewer_Context::NextSelected()
   return FALSE;
 }
 
+//=======================================================================
+// Function: SelectedObject
+// Purpose :
+//=======================================================================
 GLViewer_Object* GLViewer_Context::SelectedObject()
 {
-    ObjectMap::Iterator it;
-    for( it = myObjects.begin(); it != myObjects.end(); ++it )
-        if( mySelNumbers[mySelCurIndex] == it.data() )
-            return it.key();
-
-    return NULL;
+    return mySelectedObjects[ mySelCurIndex ];
 }
 
+//=======================================================================
+// Function: isSelected
+// Purpose :
+//=======================================================================
 bool  GLViewer_Context::isSelected( GLViewer_Object* theObj )
 {
-  for( InitSelected(); MoreSelected(); NextSelected() )
-    if( SelectedObject() == theObj )
-      return true;
-
-  return false;
+    return mySelectedObjects.contains( theObj );
 }
 
-int GLViewer_Context::insertObject( GLViewer_Object* object, bool display )
+//=======================================================================
+// Function: insertObject
+// Purpose :
+//=======================================================================
+int GLViewer_Context::insertObject( GLViewer_Object* object, bool display, bool isActive )
 {
 //  cout << "GLViewer_Context::insertObject" << endl;
-  
-    myObjects.insert( object, myNumber++ );
-    myObjList.append( object );
 
-    if( display )
+    if( !object )
+        return -1;
+
+    if( isActive )
     {
-        //QRect* rect = object->getRect()->toQRect();
-        //myGLViewer2d->updateBorders( *rect );
-        myGLViewer2d->activateDrawer( object, FALSE );
+        myActiveObjects.append( object );
+        if( display )
+        {
+            //QRect* rect = object->getRect()->toQRect();
+            //myGLViewer2d->updateBorders( *rect );
+            myGLViewer2d->activateDrawer( object, FALSE );
+        }
     }
+    else
+        myInactiveObjects.append( object );
 
-    return myNumber - 1;
+    return myActiveObjects.count() + myInactiveObjects.count();
 }
 
+//=======================================================================
+// Function: replaceObject
+// Purpose :
+//=======================================================================
 bool GLViewer_Context::replaceObject( GLViewer_Object* oldObject, GLViewer_Object* newObject )
 {
-  if( myObjects.contains( oldObject ) )
+    if( !oldObject || !newObject )
+        return false;
+
+  if( myActiveObjects.contains( oldObject ) )
+  {
+    myActiveObjects.remove( oldObject );
+    myActiveObjects.append( newObject );
+    return true;
+  }
+
+  if( myInactiveObjects.contains( oldObject ) )
   {
-    int index = myObjects[ oldObject ];
-    myObjects.remove( oldObject );
-    myObjects.insert( newObject, index );
-    return GL_TRUE;
+    myInactiveObjects.remove( oldObject );
+    myInactiveObjects.append( newObject );
+    return true;
   }
 
-  return GL_FALSE;
+  return false;
 }
 
+//=======================================================================
+// Function: updateScales
+// Purpose :
+//=======================================================================
 void GLViewer_Context::updateScales( GLfloat scX, GLfloat scY )
 {
-  if( scX && scY )
-    for ( ObjectMap::Iterator it = myObjects.begin(); it != myObjects.end(); ++it )
-      it.key()->setScale( scX, scY );
+  if( scX <= 0 || scY <= 0 )
+      return;
+
+  ObjList::iterator it, itEnd;
+
+  for( it = myActiveObjects.begin(), itEnd = myActiveObjects.end(); it != itEnd; ++it )
+      (*it)->setScale( scX, scY );
+
+  for( it = myInactiveObjects.begin(), itEnd = myInactiveObjects.end(); it != itEnd; ++it )
+      (*it)->setScale( scX, scY );
 }
 
-void GLViewer_Context::clearSelected( bool updateViewer )
+//=======================================================================
+// Function: clearHighlighted
+// Purpose :
+//=======================================================================
+void GLViewer_Context::clearHighlighted()
 {
-  QValueList<int>::Iterator it;
-  ObjectMap::Iterator oit;
+  if( myHFlag && myLastPicked )
+  {
+      myLastPicked->unhighlight();
+      myLastPicked = 0;
 
-  TColStd_SequenceOfInteger list;
+      myGLViewer2d->updateAll();
+  }
+}
 
+//=======================================================================
+// Function: clearSelected
+// Purpose :
+//=======================================================================
+void GLViewer_Context::clearSelected( bool updateViewer )
+{
   if( !mySFlag )
-    return ;
-
-  for( it = mySelNumbers.begin(); it != mySelNumbers.end(); ++it )
-    for( oit = myObjects.begin(); oit != myObjects.end(); ++oit )
-      if( *it == myObjects[ oit.key() ] )
-      {         
-        oit.key()->unselect();
-        //myGLViewer2d->initDrawer( oit.key(), oit.data() );
-        ///myGLViewer2d->initDrawer( oit.key() );
-        list.Append( *it );
-      }          
+    return;
+
+  ObjList::Iterator it, itEnd;
+  ObjList aList;
+
+  for( it = mySelectedObjects.begin(), itEnd = mySelectedObjects.end(); it != itEnd; ++it )
+  {
+    (*it)->unselect();
+    aList.append( *it );
+  }          
         
   if( updateViewer )
-    myGLViewer2d->activateDrawers( list, TRUE );
-  mySelNumbers.clear();    
+    myGLViewer2d->activateDrawers( aList, TRUE );
+  mySelectedObjects.clear();    
 }
 
+//=======================================================================
+// Function: setSelected
+// Purpose :
+//=======================================================================
 void GLViewer_Context::setSelected( GLViewer_Object* object, bool updateViewer )
 {
-  int index = -1;
-  if ( myObjects.contains( object ) )
-    index = myObjects[object];
-
-  if( index == -1 || mySelNumbers.findIndex( index ) != -1 )
+  if( !object )
     return;
 
-  mySelNumbers.append( index );
-  object->setSelected( TRUE );
-
+  if( myActiveObjects.contains( object ) && !mySelectedObjects.contains( object ) )
+  {
+    object->setSelected( TRUE );
+    mySelectedObjects.append( object );
+  }
+     
   if( updateViewer )
     myGLViewer2d->activateDrawer( object, TRUE, TRUE );
 }
 
+//=======================================================================
+// Function: remSelected
+// Purpose :
+//=======================================================================
 void GLViewer_Context::remSelected( GLViewer_Object* object, bool updateViewer )
 {
-  int index = -1;
-  if ( myObjects.contains( object ) )
-    index = myObjects[object];
-
-  if( index == -1 || mySelNumbers.findIndex( index ) == -1 )
+  if( !object || !mySelectedObjects.contains( object ) )
     return;
   
-  mySelNumbers.remove( index );
+  mySelectedObjects.remove( object );
   object->unselect();
-
+  
   if( updateViewer )
     myGLViewer2d->activateDrawer( object, TRUE, TRUE );
 }
 
+//=======================================================================
+// Function: eraseObject
+// Purpose :
+//=======================================================================
 void GLViewer_Context::eraseObject( GLViewer_Object* theObject, bool theUpdateViewer )
 {
-    if( !theObject )
+    if( !theObject || !myActiveObjects.contains( theObject ) )
         return;
 
     theObject->unhighlight();
@@ -651,31 +621,62 @@ void GLViewer_Context::eraseObject( GLViewer_Object* theObject, bool theUpdateVi
 
     if( theUpdateViewer )
         myGLViewer2d->updateAll();
-        //myGLViewer2d->activateAllDrawers( true );
 }
 
+//=======================================================================
+// Function: deleteObject
+// Purpose :
+//=======================================================================
 void GLViewer_Context::deleteObject( GLViewer_Object* theObject, bool updateViewer )
 {
-    if( !theObject || !myObjects.contains(theObject) )
+    if( !theObject ||
+        ( !myActiveObjects.contains( theObject ) && !myInactiveObjects.contains( theObject ) ) )
+        return;
+
+    if( myActiveObjects.contains( theObject ) )      
+        myActiveObjects.remove( theObject );
+    else if( myInactiveObjects.contains( theObject ) )
+        myInactiveObjects.remove( theObject );
+    else 
         return;
+     
+    if( mySelectedObjects.contains( theObject ) )
+        mySelectedObjects.remove( theObject );
 
-    int anIndex = myObjects[theObject];
-    myObjects.remove( theObject );
-    myObjList.remove( theObject );
+    GLViewer_Group* aGroup = theObject->getGroup();
+    if( aGroup )
+        aGroup->removeObject( theObject );
 
     if( myLastPicked == theObject )
-    {
-        myLastPicked = NULL;
-        myHNumber = -1;
-    }
+        myLastPicked = 0;
+
+    myGLViewer2d->updateAll();
+}
 
-    QValueList<int>::Iterator anIt= mySelNumbers.find( anIndex );
-    if( anIt != mySelNumbers.end() )
-        mySelNumbers.remove( anIt );
+//=======================================================================
+// Function: setActive
+// Purpose :
+//=======================================================================
+bool GLViewer_Context::setActive( GLViewer_Object* theObject )
+{
+  if( !theObject || !myInactiveObjects.contains( theObject ) )
+    return false;
 
-    if( mySelCurIndex == anIndex )
-        mySelCurIndex = 0;
+  myInactiveObjects.remove( theObject );
+  myActiveObjects.append( theObject );
+  return true;
+}
 
-    if ( updateViewer )
-      myGLViewer2d->updateAll();
+//=======================================================================
+// Function: setInactive
+// Purpose :
+//=======================================================================
+bool GLViewer_Context::setInactive( GLViewer_Object* theObject )
+{
+  if( !theObject || !myActiveObjects.contains( theObject ) )
+    return false;
+
+  myActiveObjects.remove( theObject );
+  myInactiveObjects.append( theObject );
+  return true;
 }