X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;f=src%2FXGUI%2FXGUI_Displayer.cpp;h=978d6154936421e9f0332bbd4520b7a4e65fb3b4;hb=220bd2b37119be1c65abf88a88792445cb9d99f8;hp=a191509e5bd9723bcfd6ab7844f206a431f8a71f;hpb=19fc4aa0b7041736b4a099bb1fc3ddc89695a338;p=modules%2Fshaper.git diff --git a/src/XGUI/XGUI_Displayer.cpp b/src/XGUI/XGUI_Displayer.cpp index a191509e5..978d61549 100644 --- a/src/XGUI/XGUI_Displayer.cpp +++ b/src/XGUI/XGUI_Displayer.cpp @@ -38,11 +38,15 @@ #include #include #include +#include +#include +#include #include #include #include #include #include +#include #include @@ -99,10 +103,10 @@ QString qIntListInfo(const QIntList& theValues, const QString& theSeparator = QS } XGUI_Displayer::XGUI_Displayer(XGUI_Workshop* theWorkshop) - : myWorkshop(theWorkshop), myEnableUpdateViewer(true), myNeedUpdate(false) + : myWorkshop(theWorkshop), myNeedUpdate(false), + myIsTrihedronActive(false), myViewerBlockedRecursiveCount(0) { - enableUpdateViewer(true); - myCustomPrs = std::shared_ptr(new XGUI_CustomPrs()); + myCustomPrs = std::shared_ptr(new XGUI_CustomPrs(theWorkshop)); } XGUI_Displayer::~XGUI_Displayer() @@ -221,7 +225,7 @@ bool XGUI_Displayer::display(ObjectPtr theObject, AISObjectPtr theAIS, if(anAISIO->Width() > 1) { for(int aModeIdx = 0; aModeIdx < myActiveSelectionModes.length(); ++aModeIdx) { int aMode = myActiveSelectionModes.value(aModeIdx); - double aPrecision = (aMode == getSelectionMode(TopAbs_VERTEX))? 15 : + double aPrecision = (aMode == getSelectionMode(TopAbs_VERTEX))? 20 : (anAISIO->Width() + 2); aContext->SetSelectionSensitivity(anAISIO, aMode, aPrecision); } @@ -248,7 +252,7 @@ bool XGUI_Displayer::erase(ObjectPtr theObject, const bool theUpdateViewer) Handle(AIS_InteractiveObject) anAIS = anObject->impl(); if (!anAIS.IsNull()) { emit beforeObjectErase(theObject, anObject); - aContext->Remove(anAIS, theUpdateViewer); + aContext->Remove(anAIS, false/*update viewer*/); aErased = true; } } @@ -260,6 +264,10 @@ bool XGUI_Displayer::erase(ObjectPtr theObject, const bool theUpdateViewer) qDebug(QString("erase object: %1").arg(aPtrStr.str().c_str()).toStdString().c_str()); qDebug(getResult2AISObjectMapInfo().c_str()); #endif + + if (theUpdateViewer) + updateViewer(); + return aErased; } @@ -314,7 +322,16 @@ bool XGUI_Displayer::redisplay(ObjectPtr theObject, bool theUpdateViewer) arg(!isEqualShapes || isCustomized).arg(isEqualShapes).arg(isCustomized).toStdString().c_str()); #endif if (!isEqualShapes || isCustomized) { + /// if shapes are equal and presentation are customized, selection should be restored + bool aNeedToRestoreSelection = isEqualShapes && isCustomized; + if (aNeedToRestoreSelection) + myWorkshop->module()->storeSelection(); + aContext->Redisplay(aAISIO, false); + + if (aNeedToRestoreSelection) + myWorkshop->module()->restoreSelection(); + aRedisplayed = true; #ifdef DEBUG_FEATURE_REDISPLAY qDebug(" Redisplay happens"); @@ -364,9 +381,9 @@ void XGUI_Displayer::deactivate(ObjectPtr theObject, const bool theUpdateViewer) void XGUI_Displayer::deactivateObjects(const QObjectPtrList& theObjList, const bool theUpdateViewer) { - //Handle(AIS_InteractiveObject) aTriehedron = getTrihedron(); - //if (!aTriehedron.IsNull()) - // deactivateAIS(aTriehedron); + //Handle(AIS_InteractiveObject) aTrihedron = getTrihedron(); + //if (!aTrihedron.IsNull()) + // deactivateAIS(aTrihedron); QObjectPtrList::const_iterator anIt = theObjList.begin(), aLast = theObjList.end(); for (; anIt != aLast; anIt++) { @@ -402,6 +419,40 @@ int XGUI_Displayer::getSelectionMode(int theShapeType) AIS_Shape::SelectionMode((TopAbs_ShapeEnum)theShapeType); } +bool XGUI_Displayer::isVisible(XGUI_Displayer* theDisplayer, const ObjectPtr& theObject) +{ + bool aVisible = false; + GeomPresentablePtr aPrs = std::dynamic_pointer_cast(theObject); + ResultPtr aResult = std::dynamic_pointer_cast(theObject); + if (aPrs.get() || aResult.get()) { + aVisible = theDisplayer->isVisible(theObject); + // compsolid is not visualized in the viewer, but should have presentation when all sub solids are + // visible. It is useful for highlight presentation where compsolid shape is selectable + if (!aVisible && aResult.get() && aResult->groupName() == ModelAPI_ResultCompSolid::group()) { + ResultCompSolidPtr aCompsolidResult = std::dynamic_pointer_cast(aResult); + if (aCompsolidResult.get() != NULL) { // change colors for all sub-solids + bool anAllSubsVisible = aCompsolidResult->numberOfSubs() > 0; + for(int i = 0; i < aCompsolidResult->numberOfSubs() && anAllSubsVisible; i++) { + anAllSubsVisible = theDisplayer->isVisible(aCompsolidResult->subResult(i)); + } + aVisible = anAllSubsVisible; + } + } + } + else { + // check if all results of the feature are visible + FeaturePtr aFeature = ModelAPI_Feature::feature(theObject); + std::list aResults = aFeature->results(); + std::list::const_iterator aIt; + aVisible = !aResults.empty(); + for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) { + aVisible = aVisible && theDisplayer->isVisible(*aIt); + } + } + return aVisible; +} + + void XGUI_Displayer::activateObjects(const QIntList& theModes, const QObjectPtrList& theObjList, const bool theUpdateViewer) { @@ -452,10 +503,12 @@ void XGUI_Displayer::activateObjects(const QIntList& theModes, const QObjectPtrL //} // Add trihedron because it has to partisipate in selection - Handle(AIS_InteractiveObject) aTrihedron = getTrihedron(); - if (!aTrihedron.IsNull()) - aPrsList.Append(aTrihedron); - + Handle(AIS_InteractiveObject) aTrihedron; + if (isTrihedronActive()) { + aTrihedron = getTrihedron(); + if (!aTrihedron.IsNull() && aContext->IsDisplayed(aTrihedron)) + aPrsList.Append(aTrihedron); + } if (aPrsList.Extent() == 0) return; @@ -468,7 +521,7 @@ void XGUI_Displayer::activateObjects(const QIntList& theModes, const QObjectPtrL } if (!aTrihedron.IsNull()) { foreach(int aMode, myActiveSelectionModes) - aContext->SetSelectionSensitivity(aTrihedron, aMode, 8); + aContext->SetSelectionSensitivity(aTrihedron, aMode, 20); } // VSV It seems that there is no necessity to update viewer on activation //if (theUpdateViewer && isActivationChanged) @@ -494,8 +547,8 @@ void XGUI_Displayer::setSelected(const QList& theValues, if (aContext.IsNull()) return; if (aContext->HasOpenedContext()) { - aContext->UnhilightSelected(); - aContext->ClearSelected(); + aContext->UnhilightSelected(false); + aContext->ClearSelected(false); foreach (ModuleBase_ViewerPrs aPrs, theValues) { const TopoDS_Shape& aShape = aPrs.shape(); if (!aShape.IsNull()) { @@ -518,8 +571,8 @@ void XGUI_Displayer::setSelected(const QList& theValues, } } } else { - aContext->UnhilightCurrents(); - aContext->ClearCurrents(); + aContext->UnhilightCurrents(false); + aContext->ClearCurrents(false); foreach (ModuleBase_ViewerPrs aPrs, theValues) { ObjectPtr anObject = aPrs.object(); ResultPtr aResult = std::dynamic_pointer_cast(anObject); @@ -555,7 +608,7 @@ bool XGUI_Displayer::eraseAll(const bool theUpdateViewer) Handle(AIS_InteractiveObject) anIO = aAISObj->impl(); if (!anIO.IsNull()) { emit beforeObjectErase(aObj, aAISObj); - aContext->Remove(anIO, false); + aContext->Remove(anIO, false/*update viewer*/); aErased = true; } } @@ -570,30 +623,47 @@ bool XGUI_Displayer::eraseAll(const bool theUpdateViewer) return aErased; } -void XGUI_Displayer::deactivateTrihedron() const +void deactivateObject(Handle(AIS_InteractiveContext) theContext, + Handle(AIS_InteractiveObject) theObject, + const bool theClear = true) { - Handle(AIS_InteractiveObject) aTrihedron = getTrihedron(); - if (!aTrihedron.IsNull()) { - Handle(AIS_InteractiveContext) aContext = AISContext(); - aContext->Deactivate(aTrihedron); + if (!theObject.IsNull()) { + theContext->Deactivate(theObject); + //if (theClear) { + //theObject->ClearSelected(); + // theContext->LocalContext()->ClearOutdatedSelection(theObject, true); + //} } } -Handle(AIS_InteractiveObject) XGUI_Displayer::getTrihedron() const +void XGUI_Displayer::deactivateTrihedron(const bool theUpdateViewer) const { + Handle(AIS_InteractiveObject) aTrihedron = getTrihedron(); Handle(AIS_InteractiveContext) aContext = AISContext(); - if (!aContext.IsNull()) { - AIS_ListOfInteractive aList; - aContext->DisplayedObjects(aList, true); - AIS_ListIteratorOfListOfInteractive aIt; - for (aIt.Initialize(aList); aIt.More(); aIt.Next()) { - Handle(AIS_Trihedron) aTrihedron = Handle(AIS_Trihedron)::DownCast(aIt.Value()); - if (!aTrihedron.IsNull()) { - return aTrihedron; - } - } + if (!aTrihedron.IsNull() && aContext->IsDisplayed(aTrihedron)) { + Handle(AIS_Trihedron) aTrie = Handle(AIS_Trihedron)::DownCast(aTrihedron); + deactivateObject(aContext, aTrie); + + /// #1136 hidden axis are selected in sketch + /// workaround for Cascade: there is a crash in AIS_LocalContext::ClearOutdatedSelection + /// for Position AIS object in SelectionModes. + deactivateObject(aContext, aTrie->XAxis()); + deactivateObject(aContext, aTrie->YAxis()); + deactivateObject(aContext, aTrie->Axis()); + deactivateObject(aContext, aTrie->Position()); + + deactivateObject(aContext, aTrie->XYPlane()); + deactivateObject(aContext, aTrie->XZPlane()); + deactivateObject(aContext, aTrie->YZPlane()); + + if (theUpdateViewer) + updateViewer(); } - return Handle(AIS_InteractiveObject)(); +} + +Handle(AIS_InteractiveObject) XGUI_Displayer::getTrihedron() const +{ + return myWorkshop->viewer()->trihedron(); } void XGUI_Displayer::openLocalContext() @@ -720,20 +790,28 @@ ObjectPtr XGUI_Displayer::getObject(const Handle(AIS_InteractiveObject)& theIO) bool XGUI_Displayer::enableUpdateViewer(const bool isEnabled) { - bool aWasEnabled = myEnableUpdateViewer; + bool aWasEnabled = isUpdateEnabled(); + if (isEnabled) + myViewerBlockedRecursiveCount--; + else + myViewerBlockedRecursiveCount++; - myEnableUpdateViewer = isEnabled; - if (myNeedUpdate && myEnableUpdateViewer) { + if (myNeedUpdate && isUpdateEnabled()) { updateViewer(); myNeedUpdate = false; } return aWasEnabled; } +bool XGUI_Displayer::isUpdateEnabled() const +{ + return myViewerBlockedRecursiveCount == 0; +} + void XGUI_Displayer::updateViewer() const { Handle(AIS_InteractiveContext) aContext = AISContext(); - if (!aContext.IsNull() && myEnableUpdateViewer) { + if (!aContext.IsNull() && isUpdateEnabled()) { myWorkshop->viewer()->Zfitall(); aContext->UpdateCurrentViewer(); } else { @@ -746,13 +824,15 @@ void XGUI_Displayer::activateAIS(const Handle(AIS_InteractiveObject)& theIO, { Handle(AIS_InteractiveContext) aContext = myWorkshop->viewer()->AISContext(); if (!aContext.IsNull()) { - aContext->Activate(theIO, theMode, theUpdateViewer); + aContext->Activate(theIO, theMode, false); #ifdef DEBUG_ACTIVATE_AIS ObjectPtr anObject = getObject(theIO); anInfo.append(ModuleBase_Tools::objectInfo((*anIt))); qDebug(QString("activateAIS: theMode = %1, object = %2").arg(theMode).arg(anInfo).toStdString().c_str()); #endif + if (theUpdateViewer) + updateViewer(); } } @@ -778,7 +858,8 @@ Handle(AIS_InteractiveContext) XGUI_Displayer::AISContext() const Handle(AIS_InteractiveContext) aContext = myWorkshop->viewer()->AISContext(); if (!aContext.IsNull() && !aContext->HasOpenedContext()) { aContext->OpenLocalContext(); - //deactivateTrihedron(); + if (!isTrihedronActive()) + deactivateTrihedron(true); aContext->DefaultDrawer()->VIsoAspect()->SetNumber(0); aContext->DefaultDrawer()->UIsoAspect()->SetNumber(0); } @@ -802,7 +883,7 @@ bool XGUI_Displayer::displayAIS(AISObjectPtr theAIS, const bool toActivateInSele Handle(AIS_InteractiveContext) aContext = AISContext(); Handle(AIS_InteractiveObject) anAISIO = theAIS->impl(); if (!aContext.IsNull() && !anAISIO.IsNull()) { - aContext->Display(anAISIO, 0/*wireframe*/, 0, theUpdateViewer, true, AIS_DS_Displayed); + aContext->Display(anAISIO, 0/*wireframe*/, 0, false/*update viewer*/, true, AIS_DS_Displayed); aDisplayed = true; aContext->Deactivate(anAISIO); aContext->Load(anAISIO); @@ -817,6 +898,8 @@ bool XGUI_Displayer::displayAIS(AISObjectPtr theAIS, const bool toActivateInSele } } } + if (theUpdateViewer) + updateViewer(); } return aDisplayed; } @@ -828,10 +911,12 @@ bool XGUI_Displayer::eraseAIS(AISObjectPtr theAIS, const bool theUpdateViewer) if (!aContext.IsNull()) { Handle(AIS_InteractiveObject) anAISIO = theAIS->impl(); if (!anAISIO.IsNull() && aContext->IsDisplayed(anAISIO)) { - aContext->Remove(anAISIO, theUpdateViewer); + aContext->Remove(anAISIO, false/*update viewer*/); aErased = true; } } + if (aErased && theUpdateViewer) + updateViewer(); return aErased; } @@ -1033,22 +1118,21 @@ bool XGUI_Displayer::activate(const Handle(AIS_InteractiveObject)& theIO, // trihedron AIS check should be after the AIS loading. // If it is not loaded, it is steel selectable in the viewer. - //Handle(AIS_Trihedron) aTrihedron = Handle(AIS_Trihedron)::DownCast(theIO); - //if (aTrihedron.IsNull()) { - //aContext->Load(anAISIO, -1, true); + Handle(AIS_Trihedron) aTrihedron; + if (!isTrihedronActive()) + aTrihedron = Handle(AIS_Trihedron)::DownCast(theIO); + if (aTrihedron.IsNull()) { // In order to clear active modes list if (theModes.size() == 0) { - //aContext->Load(anAISIO, 0, true); activateAIS(theIO, 0, theUpdateViewer); } else { foreach(int aMode, theModes) { - //aContext->Load(anAISIO, aMode, true); if (!aModesActivatedForIO.contains(aMode)) { activateAIS(theIO, aMode, theUpdateViewer); isActivationChanged = true; } } - //} + } } return isActivationChanged; } @@ -1120,3 +1204,43 @@ std::string XGUI_Displayer::getResult2AISObjectMapInfo() const return QString("myResult2AISObjectMap: size = %1\n%2\n").arg(myResult2AISObjectMap.size()). arg(aContent.join("\n")).toStdString().c_str(); } + +void XGUI_Displayer::activateTrihedron(bool theIsActive) +{ + myIsTrihedronActive = theIsActive; + if (!myIsTrihedronActive) { + deactivateTrihedron(true); + } +} + +void XGUI_Displayer::displayTrihedron(bool theToDisplay) const +{ + Handle(AIS_InteractiveContext) aContext = AISContext(); + if (aContext.IsNull()) + return; + + Handle(AIS_Trihedron) aTrihedron = myWorkshop->viewer()->trihedron(); + + if (theToDisplay) { + if (!aContext->IsDisplayed(aTrihedron)) + aContext->Display(aTrihedron, + 0 /*wireframe*/, + -1 /* selection mode */, + Standard_True /* update viewer*/, + Standard_False /* allow decomposition */, + AIS_DS_Displayed /* xdisplay status */); + + if (!isTrihedronActive()) + deactivateTrihedron(false); + else + activate(aTrihedron, myActiveSelectionModes, false); + } else { + deactivateTrihedron(false); + //aContext->LocalContext()->ClearOutdatedSelection(aTrihedron, true); + // the selection from the previous activation modes should be cleared manually (#26172) + + aContext->Erase(aTrihedron); + } + + updateViewer(); +}