-#include <TDataStd_Integer.hxx>
-#include <TDataStd_ReferenceArray.hxx>
-#include <TDataStd_IntegerArray.hxx>
-#include <TDataStd_Name.hxx>
-
-#include <list>
-
-/// type of the selection, integerm keeps the Selector_Type value
-static const Standard_GUID kSEL_TYPE("db174d59-c2e3-4a90-955e-55544df090d6");
-/// type of the shape, stored in case it is intersection or container
-static const Standard_GUID kSHAPE_TYPE("864b3267-cb9d-4107-bf58-c3ce1775b171");
-// reference attribute that contains the reference to labels where the "from" or "base" shapes
-// of selection are located
-static const Standard_GUID kBASE_ARRAY("7c515b1a-9549-493d-9946-a4933a22f45f");
-// array of the neighbor levels
-static const Standard_GUID kLEVELS_ARRAY("ee4c4b45-e859-4e86-aa4f-6eac68e0ca1f");
-// weak index (integer) of the sub-shape
-static const Standard_GUID kWEAK_INDEX("e9373a61-cabc-4ee8-aabf-aea47c62ed87");
-
-Selector_Selector::Selector_Selector(TDF_Label theLab) : myLab(theLab)
-{
- myWeakIndex = -1;
-}
-
-TDF_Label Selector_Selector::label()
-{
- return myLab;
-}
-
-// adds to theResult all labels that contain initial shapes for theValue located in theFinal
-static void findBases(Handle(TNaming_NamedShape) theFinal, const TopoDS_Shape& theValue,
- bool aMustBeAtFinal, TDF_LabelList& theResult)
-{
- TNaming_SameShapeIterator aLabIter(theValue, theFinal->Label());
- for(; aLabIter.More(); aLabIter.Next()) {
- Handle(TNaming_NamedShape) aNS;
- aLabIter.Label().FindAttribute(TNaming_NamedShape::GetID(), aNS);
- if (aMustBeAtFinal && aNS != theFinal)
- continue; // looking for old at the same final label only
- TNaming_Evolution anEvolution = aNS->Evolution();
- if (anEvolution == TNaming_PRIMITIVE) {
- // check that this is not in the results already
- const TDF_Label aResult = aNS->Label();
- TDF_LabelList::Iterator aResIter(theResult);
- for(; aResIter.More(); aResIter.Next()) {
- if (aResIter.Value().IsEqual(aResult))
- break;
- }
- if (!aResIter.More()) // not found, so add this new
- theResult.Append(aResult);
- }
- if (anEvolution == TNaming_GENERATED || anEvolution == TNaming_MODIFY) {
- for(TNaming_Iterator aThisIter(aNS); aThisIter.More(); aThisIter.Next()) {
- if (aThisIter.NewShape().IsSame(theValue)) {
- // continue recursively, null NS means that any NS are ok
- findBases(theFinal, aThisIter.OldShape(), false, theResult);
- }
- }
- }
- }
-}
-
-// returns the sub-shapes of theSubType which belong to all theShapes (so, common or intersection)
-static void commonShapes(const TopoDS_ListOfShape& theShapes, TopAbs_ShapeEnum theSubType,
- TopoDS_ListOfShape& theResults)
-{
- TopoDS_ListOfShape::iterator aSubSel = theShapes.begin();
- for(; aSubSel != theShapes.end(); aSubSel++) {
- TopTools_MapOfShape aCurrentMap;
- for(TopExp_Explorer anExp(*aSubSel, theSubType); anExp.More(); anExp.Next()) {
- if (aCurrentMap.Add(anExp.Current()) && aSubSel == theShapes.begin())
- theResults.Append(anExp.Current());
- }
- if (aSubSel != theShapes.begin()) { // remove from common shapes not in aCurrentMap
- for(TopoDS_ListOfShape::Iterator aComIter(theResults); aComIter.More(); ) {
- if (aCurrentMap.Contains(aComIter.Value()))
- aComIter.Next();
- else
- theResults.Remove(aComIter);
- }
- }
- }
-}
-
-/// Searches neighbor of theLevel of neighborhood to theValue in theContex
-static void findNeighbors(const TopoDS_Shape theContext, const TopoDS_Shape theValue,
- const int theLevel, TopTools_MapOfShape& theResult)
-{
- TopAbs_ShapeEnum aConnectorType = TopAbs_VERTEX; // type of the connector sub-shapes
- if (theValue.ShapeType() == TopAbs_FACE)
- aConnectorType = TopAbs_EDGE;
- TopTools_MapOfShape aNBConnectors; // connector shapes that already belong to neighbors
- for(TopExp_Explorer aValExp(theValue, aConnectorType); aValExp.More(); aValExp.Next()) {
- aNBConnectors.Add(aValExp.Current());
- }
-
- TopTools_MapOfShape alreadyProcessed;
- alreadyProcessed.Add(theValue);
-
- for(int aLevel = 1; aLevel <= theLevel; aLevel++) {
- TopoDS_ListOfShape aGoodCandidates;
- TopExp_Explorer aCandidate(theContext, theValue.ShapeType());
- for(; aCandidate.More(); aCandidate.Next()) {
- if (alreadyProcessed.Contains(aCandidate.Current()))
- continue;
- TopExp_Explorer aCandConnector(aCandidate.Current(), aConnectorType);
- for(; aCandConnector.More(); aCandConnector.Next()) {
- if (aNBConnectors.Contains(aCandConnector.Current())) // candidate is neighbor
- break;
- }
- if (aCandConnector.More()) {
- if (aLevel == theLevel) { // add a NB into result: it is connected to other neighbors
- theResult.Add(aCandidate.Current());
- } else { // add to the NB of the current level
- aGoodCandidates.Append(aCandidate.Current());
- }
- }
- }
- if (aLevel != theLevel) { // good candidates are added to neighbor of this level by connectors
- for(TopoDS_ListOfShape::Iterator aGood(aGoodCandidates); aGood.More(); aGood.Next()) {
- TopExp_Explorer aGoodConnector(aGood.Value(), aConnectorType);
- for(; aGoodConnector.More(); aGoodConnector.Next()) {
- aNBConnectors.Add(aGoodConnector.Current());
- }
- alreadyProcessed.Add(aGood.Value());
- }
- }
- }
-}