mirror of
https://git.dev.opencascade.org/repos/occt.git
synced 2025-08-04 13:13:25 +03:00
0024965: Problem in local selection mode with selected objects staying in the viewer
Added method to clear outdated selection of entity owners on recompute (update) of selection. Added test case to check selection behavior in local context. Cosmetic corrections
This commit is contained in:
@@ -1241,26 +1241,36 @@ void AIS_InteractiveContext::RecomputePrsOnly(const Handle(AIS_InteractiveObject
|
||||
//function : RecomputeSelectionOnly
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
void AIS_InteractiveContext::RecomputeSelectionOnly(const Handle(AIS_InteractiveObject)& anIObj)
|
||||
void AIS_InteractiveContext::RecomputeSelectionOnly (const Handle(AIS_InteractiveObject)& theIO)
|
||||
{
|
||||
if(anIObj.IsNull()) return;
|
||||
mgrSelector->RecomputeSelection(anIObj);
|
||||
if (theIO.IsNull())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
mgrSelector->RecomputeSelection (theIO);
|
||||
|
||||
|
||||
TColStd_ListOfInteger LI;
|
||||
TColStd_ListIteratorOfListOfInteger Lit;
|
||||
ActivatedModes(anIObj,LI);
|
||||
if(!HasOpenedContext()){
|
||||
if(!myObjects.IsBound(anIObj)) return;
|
||||
|
||||
if (myObjects(anIObj)->GraphicStatus() == AIS_DS_Displayed)
|
||||
if (HasOpenedContext())
|
||||
{
|
||||
for (Standard_Integer aContextIdx = 1; aContextIdx <= myLocalContexts.Extent(); aContextIdx++)
|
||||
{
|
||||
for(Lit.Initialize(LI);Lit.More();Lit.Next())
|
||||
{
|
||||
mgrSelector->Activate(anIObj,Lit.Value(),myMainSel);
|
||||
}
|
||||
myLocalContexts (aContextIdx)->ClearOutdatedSelection (theIO, Standard_False);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (!myObjects.IsBound (theIO) ||
|
||||
myObjects (theIO)->GraphicStatus() != AIS_DS_Displayed)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
TColStd_ListOfInteger aModes;
|
||||
ActivatedModes (theIO, aModes);
|
||||
TColStd_ListIteratorOfListOfInteger aModesIter (aModes);
|
||||
for (; aModesIter.More(); aModesIter.Next())
|
||||
{
|
||||
mgrSelector->Activate (theIO, aModesIter.Value(), myMainSel);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1287,6 +1297,11 @@ void AIS_InteractiveContext::Update (const Handle(AIS_InteractiveObject)& theIOb
|
||||
|
||||
mgrSelector->Update(theIObj);
|
||||
|
||||
for (Standard_Integer aContextIdx = 1; aContextIdx <= myLocalContexts.Extent(); aContextIdx++)
|
||||
{
|
||||
myLocalContexts (aContextIdx)->ClearOutdatedSelection (theIObj, Standard_False);
|
||||
}
|
||||
|
||||
if (theUpdateViewer)
|
||||
{
|
||||
if (!myObjects.IsBound (theIObj))
|
||||
|
@@ -332,13 +332,17 @@ is
|
||||
---Purpose: Clears local context selection.
|
||||
-- @param toUpdateViewer [in] if TRUE the viewer will be updated.
|
||||
|
||||
ClearSelected (me : mutable;
|
||||
theIO : InteractiveObject from AIS;
|
||||
toUpdateViewer : Boolean from Standard = Standard_True);
|
||||
---Purpose: Removes an interactive object from the local context selection.
|
||||
-- Method deselects all associated entity owners.
|
||||
ClearOutdatedSelection (me : mutable;
|
||||
theIO : InteractiveObject from AIS;
|
||||
toClearDeactivated : Boolean from Standard);
|
||||
---Purpose: Clears outdated selection and detection of owners for the
|
||||
-- interactive object. Use this method if selection structures
|
||||
-- of the interactive object have changed. The method unhilights
|
||||
-- and removes outdated entity owners from lists of selected
|
||||
-- and detected owners.
|
||||
-- @param theIO [in] the interactive object.
|
||||
-- @param toUpdateViewer [in] if TRUE the viewer will be updated.
|
||||
-- @param toClearDeactivated [in] pass TRUE to treat deactivated
|
||||
-- entity owners as 'outdated' when clearing the selection.
|
||||
|
||||
---Category: GET THE DETECTED
|
||||
|
||||
|
@@ -333,8 +333,7 @@ Erase(const Handle(AIS_InteractiveObject)& anInteractive)
|
||||
|
||||
UpdateSort();
|
||||
|
||||
// Remove object from current selection of local context
|
||||
ClearSelected (anInteractive, Standard_False);
|
||||
ClearOutdatedSelection (anInteractive, Standard_True);
|
||||
|
||||
return status;
|
||||
}
|
||||
@@ -503,8 +502,7 @@ Standard_Boolean AIS_LocalContext::Remove(const Handle(AIS_InteractiveObject)& a
|
||||
|
||||
UpdateSort();
|
||||
|
||||
// Remove object from current selection of local context
|
||||
ClearSelected (aSelectable, Standard_False);
|
||||
ClearOutdatedSelection (aSelectable, Standard_True);
|
||||
|
||||
return Standard_True;
|
||||
}
|
||||
|
@@ -72,6 +72,8 @@
|
||||
|
||||
#include <AIS_LocalContext.jxx>
|
||||
#include <StdSelect_BRepOwner.hxx>
|
||||
#include <TColStd_ListOfInteger.hxx>
|
||||
#include <TColStd_ListIteratorOfListOfInteger.hxx>
|
||||
#include <TColStd_MapOfTransient.hxx>
|
||||
#include <TColStd_MapIteratorOfMapOfTransient.hxx>
|
||||
#include <Prs3d_Presentation.hxx>
|
||||
@@ -915,28 +917,78 @@ void AIS_LocalContext::ClearSelected (const Standard_Boolean updateviewer)
|
||||
}
|
||||
|
||||
//==================================================
|
||||
// Function: ClearSelected
|
||||
// Function: ClearOutdatedSelection
|
||||
// Purpose :
|
||||
//==================================================
|
||||
void AIS_LocalContext::ClearSelected (const Handle(AIS_InteractiveObject)& theIO,
|
||||
const Standard_Boolean toUpdateViewer)
|
||||
void AIS_LocalContext::ClearOutdatedSelection (const Handle(AIS_InteractiveObject)& theIO,
|
||||
const Standard_Boolean toClearDeactivated)
|
||||
{
|
||||
// Keep last detected object for lastindex initialization.
|
||||
Handle(SelectMgr_EntityOwner) aLastPicked = myMainVS->OnePicked();
|
||||
// 1. Collect selectable entities
|
||||
SelectMgr_IndexedMapOfOwner aValidOwners;
|
||||
|
||||
// Remove the interactive object from detected sequence
|
||||
for (Standard_Integer anIdx = 1; anIdx <= myAISDetectedSeq.Length(); ++anIdx)
|
||||
const TColStd_ListOfInteger& aModes = SelectionModes (theIO);
|
||||
|
||||
TColStd_ListIteratorOfListOfInteger aModeIter (aModes);
|
||||
for (; aModeIter.More(); aModeIter.Next())
|
||||
{
|
||||
Handle(AIS_InteractiveObject) aDetectedIO = myAISDetectedSeq.Value (anIdx);
|
||||
if (!aDetectedIO.IsNull() && aDetectedIO == theIO)
|
||||
int aMode = aModeIter.Value();
|
||||
if (!theIO->HasSelection(aMode))
|
||||
{
|
||||
myAISDetectedSeq.Remove (anIdx--);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (toClearDeactivated && !mySM->IsActivated (theIO, myMainVS, aMode))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
Handle(SelectMgr_Selection) aSelection = theIO->Selection(aMode);
|
||||
for (aSelection->Init(); aSelection->More(); aSelection->Next())
|
||||
{
|
||||
Handle(SelectBasics_SensitiveEntity) anEntity = aSelection->Sensitive();
|
||||
if (anEntity.IsNull())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
Handle(SelectMgr_EntityOwner) anOwner =
|
||||
Handle(SelectMgr_EntityOwner)::DownCast (anEntity->OwnerId());
|
||||
|
||||
if (anOwner.IsNull())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
aValidOwners.Add(anOwner);
|
||||
}
|
||||
}
|
||||
|
||||
Standard_Integer aHilightMode = theIO->HasHilightMode() ? theIO->HilightMode() : 0;
|
||||
// 2. Refresh context's detection and selection and keep only active owners
|
||||
// Keep last detected object for lastindex initialization.
|
||||
Handle(SelectMgr_EntityOwner) aLastPicked = myMainVS->OnePicked();
|
||||
|
||||
// Remove entity owners from AIS_Selection
|
||||
// Remove entity owners from detected sequences
|
||||
for (Standard_Integer anIdx = 1; anIdx <= myDetectedSeq.Length(); ++anIdx)
|
||||
{
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMainVS->Picked (myDetectedSeq (anIdx));
|
||||
if (anOwner.IsNull() || anOwner->Selectable() != theIO || aValidOwners.Contains (anOwner))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
myDetectedSeq.Remove (anIdx--);
|
||||
|
||||
if (anIdx < myCurDetected)
|
||||
{
|
||||
myCurDetected--;
|
||||
}
|
||||
}
|
||||
myCurDetected = Max (myCurDetected, 1);
|
||||
|
||||
Standard_Boolean isAISRemainsDetected = Standard_False;
|
||||
|
||||
// 3. Remove entity owners from AIS_Selection
|
||||
const Handle(V3d_Viewer)& aViewer = myCTX->CurrentViewer();
|
||||
Handle(AIS_Selection) aSelection = AIS_Selection::Selection (mySelName.ToCString());
|
||||
AIS_NListTransient::Iterator anIter (aSelection->Objects());
|
||||
AIS_NListTransient aRemoveEntites;
|
||||
@@ -948,22 +1000,27 @@ void AIS_LocalContext::ClearSelected (const Handle(AIS_InteractiveObject)& theIO
|
||||
continue;
|
||||
}
|
||||
|
||||
aRemoveEntites.Append (anOwner);
|
||||
|
||||
if (IsSelected (anOwner))
|
||||
if (aValidOwners.Contains (anOwner))
|
||||
{
|
||||
anOwner->Unhilight (myMainPM, aHilightMode);
|
||||
isAISRemainsDetected = Standard_True;
|
||||
}
|
||||
|
||||
aRemoveEntites.Append (anOwner);
|
||||
anOwner->SetSelected (Standard_False);
|
||||
for (aViewer->InitActiveViews(); aViewer->MoreActiveViews(); aViewer->NextActiveViews())
|
||||
{
|
||||
Unhilight (anOwner, aViewer->ActiveView());
|
||||
}
|
||||
}
|
||||
|
||||
AIS_NListTransient::Iterator anIterRemove (aRemoveEntites);
|
||||
for (; anIterRemove.More(); anIterRemove.Next())
|
||||
{
|
||||
aSelection->Select (anIterRemove.Value());
|
||||
}
|
||||
|
||||
// Remove entity owners from myMapOfOwner
|
||||
// 4. Remove entity owners from myMapOfOwner
|
||||
SelectMgr_IndexedMapOfOwner anOwnersToKeep;
|
||||
const Handle(V3d_Viewer)& aViewer = myCTX->CurrentViewer();
|
||||
for (Standard_Integer anIdx = 1; anIdx <= myMapOfOwner.Extent(); anIdx++)
|
||||
{
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMapOfOwner (anIdx);
|
||||
@@ -972,7 +1029,7 @@ void AIS_LocalContext::ClearSelected (const Handle(AIS_InteractiveObject)& theIO
|
||||
continue;
|
||||
}
|
||||
|
||||
if (anOwner->Selectable() != theIO)
|
||||
if (anOwner->Selectable() != theIO || aValidOwners.Contains (anOwner))
|
||||
{
|
||||
anOwnersToKeep.Add (anOwner);
|
||||
}
|
||||
@@ -988,9 +1045,25 @@ void AIS_LocalContext::ClearSelected (const Handle(AIS_InteractiveObject)& theIO
|
||||
myMapOfOwner.Assign (anOwnersToKeep);
|
||||
mylastindex = myMapOfOwner.FindIndex (aLastPicked);
|
||||
|
||||
if (toUpdateViewer)
|
||||
if (!isAISRemainsDetected)
|
||||
{
|
||||
aViewer->Update();
|
||||
// Remove the interactive object from detected sequences
|
||||
for (Standard_Integer anIdx = 1; anIdx <= myAISDetectedSeq.Length(); ++anIdx)
|
||||
{
|
||||
Handle(AIS_InteractiveObject) aDetectedIO = myAISDetectedSeq.Value (anIdx);
|
||||
if (aDetectedIO.IsNull() || aDetectedIO != theIO)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
myAISDetectedSeq.Remove (anIdx--);
|
||||
|
||||
if (anIdx < myAISCurDetected)
|
||||
{
|
||||
myAISCurDetected--;
|
||||
}
|
||||
}
|
||||
myAISCurDetected = Max (myAISCurDetected, 1);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1361,7 +1434,7 @@ Standard_Integer AIS_LocalContext::HilightNextDetected (const Handle(V3d_View)&
|
||||
{
|
||||
myCurDetected = 1;
|
||||
}
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMainVS->Picked (myCurDetected);
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMainVS->Picked (myDetectedSeq (myCurDetected));
|
||||
if (anOwner.IsNull())
|
||||
{
|
||||
return 0;
|
||||
@@ -1386,7 +1459,7 @@ Standard_Integer AIS_LocalContext::HilightPreviousDetected (const Handle(V3d_Vie
|
||||
{
|
||||
myCurDetected = 1;
|
||||
}
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMainVS->Picked (myCurDetected);
|
||||
Handle(SelectMgr_EntityOwner) anOwner = myMainVS->Picked (myDetectedSeq (myCurDetected));
|
||||
if (anOwner.IsNull())
|
||||
{
|
||||
return 0;
|
||||
|
Reference in New Issue
Block a user