typedef
NCollection_DataMap<int, NCollection_DataMap<TopoDS_Shape, MapNewToOld, TopTools_ShapeMapHasher> >
HistoryMap;
+typedef
+ NCollection_DataMap<int, NCollection_DataMap<TopoDS_Shape, ListOfShape, TopTools_ShapeMapHasher> >
+ MapModified;
//==================================================================================================
GeomAlgoAPI_MakeShape::GeomAlgoAPI_MakeShape()
myDone(false)
{
myHist = 0;
+ myModifHist = 0;
}
//==================================================================================================
if (myHist) {
delete (HistoryMap*)myHist;
}
+ if (myModifHist) {
+ delete (MapModified*)myModifHist;
+ }
}
//==================================================================================================
BRepBuilderAPI_MakeShape* aMakeShape = implPtr<BRepBuilderAPI_MakeShape>();
try {
aList = aMakeShape->Modified(theOldShape->impl<TopoDS_Shape>());
- } catch(Standard_NoSuchObject) {
+ } catch(Standard_NoSuchObject const&) {
}
} else if(myBuilderType == OCCT_BOPAlgo_Builder) {
BOPAlgo_Builder* aBOPBuilder = implPtr<BOPAlgo_Builder>();
}
}
+//==================================================================================================
+void GeomAlgoAPI_MakeShape::modifiedCached(const GeomShapePtr theOldShape,
+ ListOfShape& theNewShapes)
+{
+ if (myModifHist) {
+ MapModified* aModified = (MapModified*)myModifHist;
+ int aShapeType = (int)theOldShape->impl<TopoDS_Shape>().ShapeType();
+ if (aModified->IsBound(aShapeType)) {
+ const NCollection_DataMap<TopoDS_Shape, ListOfShape, TopTools_ShapeMapHasher>& aM =
+ aModified->Find(aShapeType);
+ if (aM.IsBound(theOldShape->impl<TopoDS_Shape>())) {
+ theNewShapes = aM.Find(theOldShape->impl<TopoDS_Shape>());
+ }
+ }
+ }
+}
+
//==================================================================================================
bool GeomAlgoAPI_MakeShape::isDeleted(const GeomShapePtr theOldShape)
{
myMap->bind(aCurrentShape, aCurrentShape);
}
myHist = 0;
+ myModifHist = 0;
}
void GeomAlgoAPI_MakeShape::collectNewShapes(
GeomShapePtr theWholeOld, const int theShapeType)
{
+ if (!myModifHist)
+ myModifHist = new MapModified;
+ MapModified* aModified = (MapModified*)myModifHist;
+ if (!aModified->IsBound(theShapeType))
+ aModified->Bind(theShapeType,
+ NCollection_DataMap<TopoDS_Shape, ListOfShape, TopTools_ShapeMapHasher>());
+ NCollection_DataMap<TopoDS_Shape, ListOfShape, TopTools_ShapeMapHasher>& aM =
+ aModified->ChangeFind(theShapeType);
+
if (!myHist)
myHist = new HistoryMap;
HistoryMap* aHist = (HistoryMap*)myHist;
}
aCurrent.ChangeFind(aNewShape).Bind(anExp.current()->impl<TopoDS_Shape>(), anIndexInWholeOld);
}
+ aM.Bind(anExp.current()->impl<TopoDS_Shape>(), aNewList);
+ }
+}
+
+void GeomAlgoAPI_MakeShape::cleanNewShapes(
+ GeomShapePtr theWholeOld, const int theShapeType)
+{
+ if (myModifHist) {
+ MapModified* aModified = (MapModified*)myModifHist;
+ if (aModified->IsBound(theShapeType)) {
+ aModified->UnBind(theShapeType);
+ }
+ }
+ if (myHist) {
+ HistoryMap* aHist = (HistoryMap*)myHist;
+ if (aHist->IsBound(theShapeType)) {
+ if (aHist->Find(theShapeType).IsBound(theWholeOld->impl<TopoDS_Shape>())) {
+ aHist->ChangeFind(theShapeType).UnBind(theWholeOld->impl<TopoDS_Shape>());
+ }
+ }
}
}
GEOMALGOAPI_EXPORT virtual void generated(const GeomShapePtr theOldShape,
ListOfShape& theNewShapes);
- /// \return the list of shapes modified from the shape \a theShape.
+ /// Get a list of new shapes, modified from the given old shape.
+ /// \return the list of shapes modified from the shape \a theOldShape.
/// \param[in] theOldShape base shape.
- /// \param[out] theNewShapes shapes modified from \a theShape. Does not cleared!
+ /// \param[out] theNewShapes shapes modified from \a theOldShape. Does not cleared!
GEOMALGOAPI_EXPORT virtual void modified(const GeomShapePtr theOldShape,
ListOfShape& theNewShapes);
+ /// Get a list of new shapes, modified from the given old shape.
+ /// Works correctly only in case if the modifications are cached. Check this with isNewShapesCollected().
+ /// \return the list of shapes modified from the shape \a theOldShape.
+ /// \param[in] theOldShape base shape.
+ /// \param[out] theNewShapes shapes modified from \a theOldShape. Does not cleared!
+ GEOMALGOAPI_EXPORT void modifiedCached(const GeomShapePtr theOldShape,
+ ListOfShape& theNewShapes);
+
/// \return true if theShape was deleted.
/// \param[in] theOldShape base shape.
GEOMALGOAPI_EXPORT virtual bool isDeleted(const GeomShapePtr theOldShape);
GEOMALGOAPI_EXPORT void collectNewShapes(GeomShapePtr theWholeOld,
const int theShapeType);
+ /// Clean cached data, created by collectNewShapes() method, called with the same arguments.
+ /// \param theWholeOld the whole old shape
+ /// \param theShapeType type of the sub-shapes that is used for optimization
+ GEOMALGOAPI_EXPORT void cleanNewShapes(GeomShapePtr theWholeOld,
+ const int theShapeType);
+
/// Optimization of access the new shapes by old shapes for the limited set of needed new shapes.
/// \param theWholeOld the whole old shape
/// \param theNewShape the whole new shape
/// map that is used to keep the optimization structure for access to the history
/// kind of sub-shapes -> whole old shape -> new shape -> list of old shapes that create this new
void* myHist;
+
+ /// map that is used to keep the optimization structure for access to the history
+ /// kind of sub-shapes -> old shape -> list of new shapes modified from this old shape
+ void* myModifHist;
};
typedef std::shared_ptr<GeomAlgoAPI_MakeShape> GeomMakeShapePtr;
++aBuilderIt)
{
GeomMakeShapePtr aMakeShape = *aBuilderIt;
- ListOfShape aModifiedShapes;
aMakeShape->modified(theOldShape, theNewShapes);
}
}
{
GeomShapePtr aResultShape = shape();
GeomShapePtr aShapeToExplore = theOldShape;
- if (theAlgo->isNewShapesCollected(theOldShape, theShapeTypeToExplore)) {
+ bool isAlgoHistoryCollected = theAlgo->isNewShapesCollected(theOldShape, theShapeTypeToExplore);
+ if (isAlgoHistoryCollected) {
// use optimized set of old shapes for this
GeomShapePtr aCompound = theAlgo->oldShapesForNew(theOldShape,
aResultShape,
// Get new shapes.
ListOfShape aNewShapes;
- theAlgo->modified(anOldSubShape, aNewShapes);
+ if (isAlgoHistoryCollected) {
+ theAlgo->modifiedCached(anOldSubShape, aNewShapes);
+ }
+ else {
+ theAlgo->modified(anOldSubShape, aNewShapes);
+ }
for (ListOfShape::const_iterator aNewShapesIt = aNewShapes.cbegin();
aNewShapesIt != aNewShapes.cend();
++aNewShapesIt)
{
if (mySubs.size()) { // consists of subs
// optimization of getting of new shapes for specific sub-result
- if (!theAlgo->isNewShapesCollected(theOldShape, theShapeTypeToExplore))
+ bool isJustCollectedNS = false;
+ if (!theAlgo->isNewShapesCollected(theOldShape, theShapeTypeToExplore)) {
theAlgo->collectNewShapes(theOldShape, theShapeTypeToExplore);
+ isJustCollectedNS = true;
+ }
std::vector<ResultBodyPtr>::const_iterator aSubIter = mySubs.cbegin();
for(; aSubIter != mySubs.cend(); aSubIter++) {
(*aSubIter)->loadModifiedShapes(theAlgo, theOldShape, theShapeTypeToExplore, theName);
}
+ if (isJustCollectedNS) {
+ theAlgo->cleanNewShapes(theOldShape, theShapeTypeToExplore);
+ }
} else { // do for this directly
myBuilder->loadModifiedShapes(theAlgo, theOldShape, theShapeTypeToExplore, theName);
}